pax_global_header00006660000000000000000000000064145704212440014515gustar00rootroot0000000000000052 comment=da2882ff2a1d4cfa0ff06ccc933942939bf65b6c py-scrypt-0.8.24/000077500000000000000000000000001457042124400135625ustar00rootroot00000000000000py-scrypt-0.8.24/.flake8000066400000000000000000000002721457042124400147360ustar00rootroot00000000000000[flake8] ignore = # indentation is not a multiple of four, E111,E114, # visually indented line with same indent as next logical line, E129, W503 max-line-length=100 py-scrypt-0.8.24/.github/000077500000000000000000000000001457042124400151225ustar00rootroot00000000000000py-scrypt-0.8.24/.github/pytest.ini000066400000000000000000000001051457042124400171470ustar00rootroot00000000000000[pytest] norecursedirs = .git .* *.egg* old dist build addopts = -rw py-scrypt-0.8.24/.github/workflows/000077500000000000000000000000001457042124400171575ustar00rootroot00000000000000py-scrypt-0.8.24/.github/workflows/pre-commit.yml000066400000000000000000000004061457042124400217560ustar00rootroot00000000000000name: pre-commit on: pull_request: push: jobs: pre-commit: runs-on: ubuntu-latest steps: - uses: actions/checkout@v2 - uses: actions/setup-python@v2 with: python-version: "3.9" - uses: pre-commit/action@v2.0.0 py-scrypt-0.8.24/.github/workflows/tests.yml000066400000000000000000000010071457042124400210420ustar00rootroot00000000000000name: Run tests on: [push] jobs: run: runs-on: ${{ matrix.os }} strategy: matrix: os: [ubuntu-latest, windows-2019, windows-latest, macos-latest] python-version: ["3.8", "3.9", "3.10", "3.11", "3.12"] steps: - uses: actions/checkout@master - name: Setup Python uses: actions/setup-python@master with: python-version: ${{ matrix.python-version }} - name: Install packages run: | pip install pytest pip install -e . pytest py-scrypt-0.8.24/.github/workflows/wheels_arm64.yml000066400000000000000000000030041457042124400221770ustar00rootroot00000000000000name: Build wheel on arm on: [push] env: CIBW_BUILD_VERBOSITY: 1 CIBW_ARCHS: "auto64" CIBW_TEST_REQUIRES: pytest CIBW_TEST_COMMAND: "pytest --pyargs scrypt" jobs: build_aarch64_wheels: name: Build wheels manylinux_aarch64 runs-on: ubuntu-latest strategy: matrix: python: [36, 37, 38, 39, 310, 311, 312] include: - os: ubuntu-latest arch: aarch64 platform_id: manylinux_aarch64 steps: - uses: actions/checkout@v4 - name: Set up QEMU uses: docker/setup-qemu-action@v3 - name: Install cibuildwheel run: python -m pip install cibuildwheel - name: Build wheels run: python -m cibuildwheel --output-dir wheelhouse env: CIBW_ARCHS_LINUX: ${{matrix.arch}} CIBW_BUILD: cp${{ matrix.python }}-${{ matrix.platform_id }} - uses: actions/upload-artifact@v4 with: name: artifact-${{ matrix.python }} path: wheelhouse/*.whl upload_pypi: name: Upload to PyPI (prod) needs: [build_aarch64_wheels] if: github.event_name == 'push' && startsWith(github.ref, 'refs/tags') runs-on: ubuntu-latest strategy: matrix: python: [36, 37, 38, 39, 310, 311, 312] steps: - uses: actions/download-artifact@v4 with: name: artifact-${{ matrix.python }} path: dist - uses: pypa/gh-action-pypi-publish@v1.5.0 with: user: __token__ password: ${{ secrets.PYPI_API_TOKEN }} py-scrypt-0.8.24/.github/workflows/wheels_linux.yml000066400000000000000000000022441457042124400224120ustar00rootroot00000000000000name: Build wheel on linux on: [push] env: CIBW_BUILD_VERBOSITY: 1 CIBW_TEST_REQUIRES: pytest CIBW_TEST_COMMAND: "pytest --pyargs scrypt" jobs: build_wheels: name: Build wheels on ubuntu-latest runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 # Used to host cibuildwheel - uses: actions/setup-python@v5 - name: Install cibuildwheel run: python -m pip install cibuildwheel - name: Build wheels run: python -m cibuildwheel --output-dir wheelhouse env: # Disable explicitly python 3.11 and building PyPy wheels CIBW_SKIP: pp* CIBW_PRERELEASE_PYTHONS: False - uses: actions/upload-artifact@v4 with: path: wheelhouse/*.whl upload_pypi: name: Upload to PyPI (prod) needs: [build_wheels] if: github.event_name == 'push' && startsWith(github.ref, 'refs/tags') runs-on: ubuntu-latest steps: - uses: actions/download-artifact@v4 with: name: artifact path: dist - uses: pypa/gh-action-pypi-publish@v1.5.0 with: user: __token__ password: ${{ secrets.PYPI_API_TOKEN }} py-scrypt-0.8.24/.github/workflows/wheels_osx.yml000066400000000000000000000024071457042124400220650ustar00rootroot00000000000000name: Build wheel on osx on: [push] env: CIBW_BUILD_VERBOSITY: 1 CIBW_TEST_REQUIRES: pytest CIBW_TEST_COMMAND: "pytest --pyargs scrypt" jobs: build_osx_wheels: name: Build wheels on macos-latest runs-on: macos-latest steps: - uses: actions/checkout@v4 # Used to host cibuildwheel - uses: actions/setup-python@v5 - name: Install cibuildwheel run: python -m pip install cibuildwheel - name: Build wheels run: python -m cibuildwheel --output-dir wheelhouse env: # Disable explicitly building PyPy wheels CFLAGS: "-I/usr/local/opt/openssl@1.1/include" LDFLAGS: "-L/usr/local/opt/openssl@1.1/lib" CIBW_SKIP: pp* CIBW_PRERELEASE_PYTHONS: False - uses: actions/upload-artifact@v4 with: path: wheelhouse/*.whl upload_pypi: name: Upload to PyPI (prod) needs: [build_osx_wheels] if: github.event_name == 'push' && startsWith(github.ref, 'refs/tags') runs-on: ubuntu-latest steps: - uses: actions/download-artifact@v4 with: name: artifact path: dist - uses: pypa/gh-action-pypi-publish@v1.5.0 with: user: __token__ password: ${{ secrets.PYPI_API_TOKEN }} py-scrypt-0.8.24/.github/workflows/wheels_sdist.yml000066400000000000000000000017071457042124400224040ustar00rootroot00000000000000name: Build sdist on: [push] env: CIBW_BUILD_VERBOSITY: 1 jobs: make_sdist: name: Make SDist runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - name: Setup Python uses: actions/setup-python@v5 with: python-version: '3.9' - name: Install deps run: python -m pip install build twine - name: Build SDist run: python -m build --sdist - uses: actions/upload-artifact@v4 with: path: dist/*.tar.gz - name: Check metadata run: twine check dist/* upload_pypi: name: Upload to PyPI (prod) needs: [make_sdist] if: github.event_name == 'push' && startsWith(github.ref, 'refs/tags') runs-on: ubuntu-latest steps: - uses: actions/download-artifact@v4 with: name: artifact path: dist - uses: pypa/gh-action-pypi-publish@v1.5.0 with: user: __token__ password: ${{ secrets.PYPI_API_TOKEN }} py-scrypt-0.8.24/.github/workflows/wheels_win_64.yml000066400000000000000000000025011457042124400223550ustar00rootroot00000000000000name: Build wheel on win64 on: [push] env: CIBW_BUILD_VERBOSITY: 1 CIBW_ARCHS: "auto64" # Run the package tests using `pytest` CIBW_TEST_REQUIRES: pytest CIBW_TEST_COMMAND: "pytest --pyargs scrypt" jobs: build_wheels_for_win: name: Build wheels on Win64 runs-on: windows-latest steps: - uses: actions/checkout@v4 # Used to host cibuildwheel - uses: actions/setup-python@v5 - name: Install cibuildwheel run: python -m pip install cibuildwheel - name: install openssl (64 bit) shell: pwsh run: choco install openssl --limitoutput - name: Build wheels run: python -m cibuildwheel --output-dir wheelhouse env: # Disable building PyPy wheels CIBW_SKIP: pp* CIBW_PRERELEASE_PYTHONS: False - uses: actions/upload-artifact@v4 with: path: wheelhouse/*.whl upload_pypi: name: Upload to PyPI (prod) needs: [build_wheels_for_win] if: github.event_name == 'push' && startsWith(github.ref, 'refs/tags') runs-on: ubuntu-latest steps: - uses: actions/download-artifact@v4 with: name: artifact path: dist - uses: pypa/gh-action-pypi-publish@v1.5.0 with: user: __token__ password: ${{ secrets.PYPI_API_TOKEN }} py-scrypt-0.8.24/.gitignore000066400000000000000000000021361457042124400155540ustar00rootroot00000000000000# Byte-compiled / optimized / DLL files __pycache__/ *.py[cod] *$py.class # C extensions *.so # Distribution / packaging .Python eggs/ .eggs/ wheels/ *.egg-info/ .installed.cfg *.egg dist/ # PyInstaller # Usually these files are written by a python script from a template # before PyInstaller builds the exe, so as to inject date/other infos into it. *.manifest *.spec # Installer logs pip-log.txt pip-delete-this-directory.txt # Unit test / coverage reports htmlcov/ .tox/ .coverage .coverage.* .cache nosetests.xml coverage.xml *.cover .hypothesis/ # Translations *.mo *.pot # Django stuff: *.log local_settings.py # Flask stuff: instance/ .webassets-cache # Scrapy stuff: .scrapy # Sphinx documentation docs/_build/ # PyBuilder target/ # Jupyter Notebook .ipynb_checkpoints # pyenv .python-version # celery beat schedule file celerybeat-schedule # SageMath parsed files *.sage.py # dotenv .env # virtualenv .venv venv/ ENV/ # Spyder project settings .spyderproject .spyproject # Rope project settings .ropeproject # mkdocs documentation /site /build # mypy .mypy_cache/ # wing *.wpr *.wpu py-scrypt-0.8.24/.pre-commit-config.yaml000066400000000000000000000034221457042124400200440ustar00rootroot00000000000000 default_language_version: python: python3 repos: - repo: https://github.com/psf/black rev: 24.2.0 hooks: - id: black exclude: ^(scrypt-1.2.1/) args: [--skip-string-normalization] - repo: https://github.com/myint/autoflake rev: v2.3.0 hooks: - id: autoflake exclude: ^(scrypt-1.2.1/) args: - --in-place - --ignore-init-module-imports - --remove-all-unused-imports - --remove-duplicate-keys - repo: https://github.com/pre-commit/pre-commit-hooks rev: v4.5.0 hooks: - id: check-toml - id: check-yaml - id: end-of-file-fixer exclude: ^(scrypt-1.2.1/) - id: trailing-whitespace exclude: ^(scrypt-1.2.1/) - repo: https://github.com/PyCQA/flake8 rev: "7.0.0" hooks: - id: flake8 name: flake8 except __init__.py exclude: (^(scrypt-1.2.1/)|/__init__\.py$) additional_dependencies: ["flake8-bugbear==23.1.20"] args: [--config, .flake8] - id: flake8 exclude: ^(scrypt-1.2.1/) name: flake8 only __init__.py args: [--config, .flake8, "--extend-ignore=F401"] # ignore unused imports in __init__.py files: /__init__\.py$ - repo: https://github.com/PyCQA/isort rev: 5.13.2 hooks: - id: isort args: ["--profile", "black"] name: isort except __init__.py exclude: (^(scrypt-1.2.1/)|/__init__\.py$) - repo: https://github.com/myint/docformatter rev: v1.7.5 hooks: - id: docformatter exclude: ^(scrypt-1.2.1/) args: ["--in-place", "--wrap-summaries=88"] - repo: https://github.com/asottile/pyupgrade rev: v3.15.1 hooks: - id: pyupgrade exclude: ^(scrypt-1.2.1/) args: ["--py37-plus"] py-scrypt-0.8.24/LICENSE000066400000000000000000000025321457042124400145710ustar00rootroot00000000000000BSD 2-Clause License Copyright (c) 2010-2016, Magnus Hallin 2018-2021, Holger Nahrstaedt All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. py-scrypt-0.8.24/MANIFEST.in000066400000000000000000000013121457042124400153150ustar00rootroot00000000000000recursive-include scrypt-1.2.1 *.h recursive-include scrypt-windows-stubs *.h include README.rst include LICENSE include setup.py include *.txt include tox.ini include src/*.c include scrypt-windows-stubs/*.c include MANIFEST.in include scrypt/__init__.py include scrypt/scrypt.py include scrypt/tests/__init__.py include scrypt/tests/ciphertexts.csv include scrypt/tests/hashvectors.csv include scrypt/tests/test_scrypt_c_module.py include scrypt/tests/test_scrypt.py include scrypt/tests/test_scrypt_py2x.py include scrypt/tests/test_scrypt_py3x.py # Exclude what we don't want to include prune build prune doc/build prune */__pycache__ global-exclude *.py[cod] *.egg *.egg-info global-exclude *~ *.bak *.swp py-scrypt-0.8.24/README.rst000066400000000000000000000162321457042124400152550ustar00rootroot00000000000000========================= Python scrypt_ bindings ========================= This is a set of Python_ bindings for the scrypt_ key derivation function. .. image:: https://img.shields.io/pypi/v/scrypt.svg :target: https://pypi.python.org/pypi/scrypt/ :alt: Latest Version .. image:: https://anaconda.org/conda-forge/scrypt/badges/version.svg :target: https://anaconda.org/conda-forge/scrypt .. image:: https://anaconda.org/conda-forge/scrypt/badges/downloads.svg :target: https://anaconda.org/conda-forge/scrypt Scrypt is useful when encrypting password as it is possible to specify a *minimum* amount of time to use when encrypting and decrypting. If, for example, a password takes 0.05 seconds to verify, a user won't notice the slight delay when signing in, but doing a brute force search of several billion passwords will take a considerable amount of time. This is in contrast to more traditional hash functions such as MD5 or the SHA family which can be implemented extremely fast on cheap hardware. Installation ============ For Debian and Ubuntu, please ensure that the following packages are installed: .. code:: bash $ sudo apt-get install build-essential libssl-dev python-dev For Fedora and RHEL-derivatives, please ensure that the following packages are installed: .. code:: bash $ sudo yum install gcc openssl-devel python-devel For OSX, please do the following:: $ brew install openssl $ export CFLAGS="-I$(brew --prefix openssl)/include $CFLAGS" $ export LDFLAGS="-L$(brew --prefix openssl)/lib $LDFLAGS" For OSX, you can also use the precompiled wheels. They are installed by:: $ pip install scrypt For Windows, please use the precompiled wheels. They are installed by:: $ pip install scrypt For Windows, when the package should be compiled, the development package from https://slproweb.com/products/Win32OpenSSL.html is needed. It needs to be installed to C:\OpenSSL-Win64. You can install py-scrypt from this repository if you want the latest but possibly non-compiling version:: $ git clone https://github.com/holgern/py-scrypt.git $ cd py-scrypt $ python setup.py build Become superuser (or use virtualenv): # python setup.py install Run tests after install: $ python setup.py test Or you can install the latest release from PyPi:: $ pip install scrypt Users of the Anaconda_ Python distribution can directly obtain pre-built Windows, Intel Linux or macOS / OSX binaries from the conda-forge channel. This can be done via:: $ conda install -c conda-forge scrypt If you want py-scrypt for your Python 3 environment, just run the above commands with your Python 3 interpreter. Py-scrypt supports both Python 2 and 3. From version 0.6.0 (not available on PyPi yet), py-scrypt supports PyPy as well. Changelog ========= 0.8.20 ------ * Fix #8 by adding missing gettimeofday.c to MANIFEST.in 0.8.19 ------ * Use RtlGenRandom instead of CryptGenRandom on windows (Thanks to https://github.com/veorq/cryptocoding/) * Add check for c:\Program Files\OpenSSL-Win64 and c:\Program Files\OpenSSL-Win32 0.8.18 ------ * add wheel for python 3.9 0.8.17 ------ * add_dll_directory for python 3.8 on windows, as importlib.util.find_spec does not search all paths anymore 0.8.16 ------ * Add additional test vector from RFC (thanks to @ChrisMacNaughton) 0.8.15 ------ * Fix missing import 0.8.14 ------ * fix imp deprecation warning 0.8.13 ------ * improve build for conda forge 0.8.12 ------ * Add SCRYPT_WINDOWS_LINK_LEGACY_OPENSSL environment variable, when set, openssl 1.0.2 is linked 0.8.11 ------ * fix build for conda feedstock 0.8.10 ------ * fix typo 0.8.9 ----- * use the static libcrypto_static for windows and openssl 1.1.1 0.8.8 ----- * setup.py for windows improved, works with openssl 1.0.2 and 1.1.1 0.8.7 ----- * setup.py for windows fixed 0.8.6 ----- * setup.py fixed, scrypt could not be imported in version 0.8.5 0.8.5 ----- * MANIFEST.in fixed * scrypt.py moved into own scrypt directory with __init__.py * openssl library path for osx wheel repaired 0.8.4 ----- * __version__ added to scrypt * missing void in sha256.c fixed 0.8.3 ----- * scrypt updated to 1.2.1 * Wheels are created for python 3.6 Usage ===== Fore encryption/decryption, the library exports two functions ``encrypt`` and ``decrypt``:: >>> import scrypt >>> data = scrypt.encrypt('a secret message', 'password', maxtime=0.1) # This will take at least 0.1 seconds >>> data[:20] 'scrypt\x00\r\x00\x00\x00\x08\x00\x00\x00\x01RX9H' >>> scrypt.decrypt(data, 'password', maxtime=0.1) # This will also take at least 0.1 seconds 'a secret message' >>> scrypt.decrypt(data, 'password', maxtime=0.05) # scrypt won't be able to decrypt this data fast enough Traceback (most recent call last): File "", line 1, in scrypt.error: decrypting file would take too long >>> scrypt.decrypt(data, 'wrong password', maxtime=0.1) # scrypt will throw an exception if the password is incorrect Traceback (most recent call last): File "", line 1, in scrypt.error: password is incorrect From these, one can make a simple password verifier using the following functions:: def hash_password(password, maxtime=0.5, datalength=64): return scrypt.encrypt(os.urandom(datalength), password, maxtime=maxtime) def verify_password(hashed_password, guessed_password, maxtime=0.5): try: scrypt.decrypt(hashed_password, guessed_password, maxtime) return True except scrypt.error: return False But, if you want output that is deterministic and constant in size, you can use the ``hash`` function:: >>> import scrypt >>> h1 = scrypt.hash('password', 'random salt') >>> len(h1) # The hash will be 64 bytes by default, but is overridable. 64 >>> h1[:10] '\xfe\x87\xf3hS\tUo\xcd\xc8' >>> h2 = scrypt.hash('password', 'random salt') >>> h1 == h2 # The hash function is deterministic True Acknowledgements ================ Scrypt_ was created by Colin Percival and is licensed as 2-clause BSD. Since scrypt does not normally build as a shared library, I have included the source for the currently latest version of the library in this repository. When a new version arrives, I will update these sources. `Kelvin Wong`_ on Bitbucket provided changes to make the library available on Mac OS X 10.6 and earlier, as well as changes to make the library work more like the command-line version of scrypt by default. Kelvin also contributed with the unit tests, lots of cross platform testing and work on the ``hash`` function. Burstaholic_ on Bitbucket provided the necessary changes to make the library build on Windows. The `python-appveyor-demo`_ repository for setting up automated Windows builds for a multitude of Python versions. License ======= This library is licensed under the same license as scrypt; 2-clause BSD. .. _scrypt: http://www.tarsnap.com/scrypt.html .. _Python: http://python.org .. _Burstaholic: https://bitbucket.org/Burstaholic .. _Kelvin Wong: https://bitbucket.org/kelvinwong_ca .. _python-appveyor-demo: https://github.com/ogrisel/python-appveyor-demo .. _Anaconda: https://www.continuum.io py-scrypt-0.8.24/dev-requirements.txt000066400000000000000000000000201457042124400176120ustar00rootroot00000000000000tox nose pytest py-scrypt-0.8.24/pyproject.toml000066400000000000000000000003451457042124400165000ustar00rootroot00000000000000[tool.cibuildwheel.linux] before-all = "yum install -y openssl-devel" [[tool.cibuildwheel.overrides]] select = "*-musllinux*" before-all = "apk add openssl-dev" [tool.cibuildwheel.macos] before-all = "brew install openssl@1.1" py-scrypt-0.8.24/scrypt-1.2.1/000077500000000000000000000000001457042124400155435ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/COPYRIGHT000066400000000000000000000027151457042124400170430ustar00rootroot00000000000000The included code and documentation ("scrypt") is distributed under the following terms: Copyright 2005-2016 Colin Percival. All rights reserved. Copyright 2005-2016 Tarsnap Backup Inc. All rights reserved. Copyright 2014 Sean Kelly. All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. py-scrypt-0.8.24/scrypt-1.2.1/FORMAT000066400000000000000000000012301457042124400164520ustar00rootroot00000000000000scrypt encrypted data format ---------------------------- offset length 0 6 "scrypt" 6 1 scrypt data file version number (== 0) 7 1 log2(N) (must be between 1 and 63 inclusive) 8 4 r (big-endian integer; must satisfy r * p < 2^30) 12 4 p (big-endian integer; must satisfy r * p < 2^30) 16 32 salt 48 16 first 16 bytes of SHA256(bytes 0 .. 47) 64 32 HMAC-SHA256(bytes 0 .. 63) 96 X data xor AES256-CTR key stream generated with nonce == 0 96+X 32 HMAC-SHA256(bytes 0 .. 96 + (X - 1)) AES256-CTR is computed with a 256-bit AES key key_enc, and HMAC-SHA256 is computed with a 256-bit key key_hmac, where scrypt(password, salt, N, r, p, 64) == [key_enc][key_hmac] py-scrypt-0.8.24/scrypt-1.2.1/README.md000066400000000000000000000134041457042124400170240ustar00rootroot00000000000000The scrypt key derivation function ---------------------------------- The scrypt key derivation function was originally developed for use in the [Tarsnap online backup system](http://www.tarsnap.com/index.html) and is designed to be far more secure against hardware brute-force attacks than alternative functions such as [PBKDF2](http://en.wikipedia.org/wiki/PBKDF2) or [bcrypt](http://www.openbsd.org/papers/bcrypt-paper.ps). We estimate that on modern (2009) hardware, if 5 seconds are spent computing a derived key, the cost of a hardware brute-force attack against `scrypt` is roughly 4000 times greater than the cost of a similar attack against bcrypt (to find the same password), and 20000 times greater than a similar attack against PBKDF2. Details of the `scrypt` key derivation function are given in a paper which was presented at the [BSDCan'09](http://www.bsdcan.org/2009/) conference: * Colin Percival, [Stronger Key Derivation via Sequential Memory-Hard Functions](http://www.tarsnap.com/scrypt/scrypt.pdf), presented at BSDCan'09, May 2009. * Conference presentation slides: [PDF](http://www.tarsnap.com/scrypt/scrypt-slides.pdf). More details are given in the Internet Engineering Task Force (IETF) [RFC 7914: The scrypt Password-Based Key Derivation Function](https://tools.ietf.org/html/rfc7914). It has been demonstrated that scrypt is maximally memory-hard: * J. Alwen, B. Chen, K. Pietrzak, L. Reyzin, S. Tessaro, [Scrypt is Maximally Memory-Hard](http://eprint.iacr.org/2016/989), Cryptology ePrint Archive: Report 2016/989. The scrypt encryption utility ----------------------------- A simple password-based encryption utility is available as a demonstration of the `scrypt` key derivation function. On modern hardware and with default parameters, the cost of cracking the password on a file encrypted by `scrypt enc` is approximately 100 billion times more than the cost of cracking the same password on a file encrypted by `openssl enc`; this means that a five-character password using `scrypt` is stronger than a ten-character password using `openssl`. The `scrypt` utility can be invoked as `scrypt enc infile [outfile]` to encrypt data (if `outfile` is not specified, the encrypted data is written to the standard output), or as `scrypt dec infile [outfile]` to decrypt data (if outfile is not specified, the decrypted data is written to the standard output). `scrypt` also supports three command-line options: * `-t maxtime` will instruct `scrypt` to spend at most maxtime seconds computing the derived encryption key from the password; for encryption, this value will determine how secure the encrypted data is, while for decryption this value is used as an upper limit (if `scrypt` detects that it would take too long to decrypt the data, it will exit with an error message). * `-m maxmemfrac` instructs `scrypt` to use at most the specified fraction of the available RAM for computing the derived encryption key. For encryption, increasing this value might increase the security of the encrypted data, depending on the `maxtime` value; for decryption, this value is used as an upper limit and may `cause` scrypt to exit with an error. * `-M maxmem` instructs `scrypt` to use at most the specified number of bytes of RAM when computing the derived encryption key. If the encrypted data is corrupt, `scrypt dec` will exit with a non-zero status. However, **`scrypt dec` may produce output before it determines that the encrypted data was corrupt**, so for applications which require data to be authenticated, you must store the output of `scrypt dec` in a temporary location and check `scrypt`'s exit code before using the decrypted data. The `scrypt` utility has been tested on FreeBSD, NetBSD, OpenBSD, Linux (Slackware, CentOS, Gentoo, Ubuntu), Solaris, OS X, Cygwin, and GNU Hurd. To build scrypt, extract the tarball and run `./configure` && `make`. * [scrypt version 1.2.0 source tarball](https://www.tarsnap.com/scrypt/scrypt-1.2.0.tgz) * [GPG-signed SHA256 for scrypt version 1.2.0](https://www.tarsnap.com/scrypt/scrypt-sigs-1.2.0.asc) (signature generated using Tarsnap [code signing key](https://www.tarsnap.com/tarsnap-signing-key.asc)) In addition, `scrypt` is available in the OpenBSD and FreeBSD ports trees and in NetBSD pkgsrc as `security/scrypt`. Using scrypt as a KDF --------------------- To use scrypt as a [key derivation function](https://en.wikipedia.org/wiki/Key_derivation_function) (KDF), take a look at the `lib/crypto/crypto_scrypt.h` header, which provides: ``` /** * crypto_scrypt(passwd, passwdlen, salt, saltlen, N, r, p, buf, buflen): * Compute scrypt(passwd[0 .. passwdlen - 1], salt[0 .. saltlen - 1], N, r, * p, buflen) and write the result into buf. The parameters r, p, and buflen * must satisfy r * p < 2^30 and buflen <= (2^32 - 1) * 32. The parameter N * must be a power of 2 greater than 1. * * Return 0 on success; or -1 on error. */ int crypto_scrypt(const uint8_t *, size_t, const uint8_t *, size_t, uint64_t, uint32_t, uint32_t, uint8_t *, size_t); ``` Building -------- :exclamation: We strongly recommend that people use the latest official release tarball on https://www.tarsnap.com/scrypt.html See the `BUILDING` file for more details (e.g., dealing with OpenSSL on OSX). Testing ------- A small test suite can be run with: make test Memory-testing normal operations with valgrind (takes approximately 4 times as long as no valgrind tests) can be enabled with: make test USE_VALGRIND=1 Memory-testing all tests with valgrind (requires over 1 GB memory, and takes approximately 4 times as long as `USE_VALGRIND=1`) can be enabled with: make test USE_VALGRIND=2 Mailing list ------------ The scrypt key derivation function and the scrypt encryption utility are discussed on the mailing list. py-scrypt-0.8.24/scrypt-1.2.1/config.h000066400000000000000000000055611457042124400171700ustar00rootroot00000000000000/* config.h. Generated from config.h.in by configure. */ /* config.h.in. Generated from configure.ac by autoheader. */ /* Define to 1 if you have the `clock_gettime' function. */ /* #undef HAVE_CLOCK_GETTIME */ /* Define to 1 if you have the declaration of `be64enc', and to 0 if you don't. */ #define HAVE_DECL_BE64ENC 0 /* Define to 1 if you have the header file. */ #define HAVE_ERR_H 1 /* Define to 1 if you have the header file. */ #define HAVE_INTTYPES_H 1 /* Define to 1 if you have the `rt' library (-lrt). */ /* #undef HAVE_LIBRT */ /* Define to 1 if you have the header file. */ #define HAVE_MEMORY_H 1 /* Define to 1 if you have the `posix_memalign' function. */ /* #undef HAVE_POSIX_MEMALIGN */ /* Define to 1 if you have the header file. */ #define HAVE_STDINT_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STDLIB_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STRINGS_H 1 /* Define to 1 if you have the header file. */ #define HAVE_STRING_H 1 /* Define to 1 if the system has the type `struct sysinfo'. */ /* #undef HAVE_STRUCT_SYSINFO */ /* Define to 1 if `mem_unit' is member of `struct sysinfo'. */ /* #undef HAVE_STRUCT_SYSINFO_MEM_UNIT */ /* Define to 1 if `totalram' is member of `struct sysinfo'. */ /* #undef HAVE_STRUCT_SYSINFO_TOTALRAM */ /* Define to 1 if the OS has a hw.usermem sysctl */ /* #undef HAVE_SYSCTL_HW_USERMEM */ /* Define to 1 if you have the `sysinfo' function. */ /* #undef HAVE_SYSINFO */ /* Define to 1 if you have the header file. */ /* #undef HAVE_SYS_ENDIAN_H */ /* Define to 1 if you have the header file. */ /* #define HAVE_SYS_PARAM_H */ /* Define to 1 if you have the header file. */ #define HAVE_SYS_STAT_H 1 /* Define to 1 if you have the header file. */ /* #undef HAVE_SYS_SYSINFO_H */ /* Define to 1 if you have the header file. */ #define HAVE_SYS_TYPES_H 1 /* Define to 1 if you have the header file. */ #define HAVE_UNISTD_H 1 /* Name of package */ #define PACKAGE "scrypt" /* Define to the address where bug reports for this package should be sent. */ #define PACKAGE_BUGREPORT "" /* Define to the full name of this package. */ #define PACKAGE_NAME "scrypt" /* Define to the full name and version of this package. */ #define PACKAGE_STRING "scrypt 1.2.1" /* Define to the one symbol short name of this package. */ #define PACKAGE_TARNAME "scrypt" /* Define to the version of this package. */ #define PACKAGE_VERSION "1.2.1" /* Define to 1 if you have the ANSI C header files. */ #define STDC_HEADERS 1 /* Version number of package */ #define VERSION "1.2.1" /* Number of bits in a file offset, on hosts where this is settable. */ /* #undef _FILE_OFFSET_BITS */ /* Define for large files, on AIX-style hosts. */ /* #undef _LARGE_FILES */ py-scrypt-0.8.24/scrypt-1.2.1/lib/000077500000000000000000000000001457042124400163115ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/lib/README000066400000000000000000000005611457042124400171730ustar00rootroot00000000000000The source code under this directory is taken from the client for the Tarsnap online backup system (and released under the 2-clause BSD license with permission of the author); keeping this code in sync with the Tarsnap code is highly desirable and explains why there is some functionality included here which is not actually used by the scrypt file encryption utility. py-scrypt-0.8.24/scrypt-1.2.1/lib/crypto/000077500000000000000000000000001457042124400176315ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/lib/crypto/crypto_scrypt-ref.c000066400000000000000000000165261457042124400235050ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #include "scrypt_platform.h" #include #include #include #include #include "sha256.h" #include "sysendian.h" #include "crypto_scrypt.h" static void blkcpy(uint8_t *, uint8_t *, size_t); static void blkxor(uint8_t *, uint8_t *, size_t); static void salsa20_8(uint8_t[64]); static void blockmix_salsa8(uint8_t *, uint8_t *, size_t); static uint64_t integerify(uint8_t *, size_t); static void smix(uint8_t *, size_t, uint64_t, uint8_t *, uint8_t *); static void blkcpy(uint8_t * dest, uint8_t * src, size_t len) { size_t i; for (i = 0; i < len; i++) dest[i] = src[i]; } static void blkxor(uint8_t * dest, uint8_t * src, size_t len) { size_t i; for (i = 0; i < len; i++) dest[i] ^= src[i]; } /** * salsa20_8(B): * Apply the salsa20/8 core to the provided block. */ static void salsa20_8(uint8_t B[64]) { uint32_t B32[16]; uint32_t x[16]; size_t i; /* Convert little-endian values in. */ for (i = 0; i < 16; i++) B32[i] = le32dec(&B[i * 4]); /* Compute x = doubleround^4(B32). */ for (i = 0; i < 16; i++) x[i] = B32[i]; for (i = 0; i < 8; i += 2) { #define R(a,b) (((a) << (b)) | ((a) >> (32 - (b)))) /* Operate on columns. */ x[ 4] ^= R(x[ 0]+x[12], 7); x[ 8] ^= R(x[ 4]+x[ 0], 9); x[12] ^= R(x[ 8]+x[ 4],13); x[ 0] ^= R(x[12]+x[ 8],18); x[ 9] ^= R(x[ 5]+x[ 1], 7); x[13] ^= R(x[ 9]+x[ 5], 9); x[ 1] ^= R(x[13]+x[ 9],13); x[ 5] ^= R(x[ 1]+x[13],18); x[14] ^= R(x[10]+x[ 6], 7); x[ 2] ^= R(x[14]+x[10], 9); x[ 6] ^= R(x[ 2]+x[14],13); x[10] ^= R(x[ 6]+x[ 2],18); x[ 3] ^= R(x[15]+x[11], 7); x[ 7] ^= R(x[ 3]+x[15], 9); x[11] ^= R(x[ 7]+x[ 3],13); x[15] ^= R(x[11]+x[ 7],18); /* Operate on rows. */ x[ 1] ^= R(x[ 0]+x[ 3], 7); x[ 2] ^= R(x[ 1]+x[ 0], 9); x[ 3] ^= R(x[ 2]+x[ 1],13); x[ 0] ^= R(x[ 3]+x[ 2],18); x[ 6] ^= R(x[ 5]+x[ 4], 7); x[ 7] ^= R(x[ 6]+x[ 5], 9); x[ 4] ^= R(x[ 7]+x[ 6],13); x[ 5] ^= R(x[ 4]+x[ 7],18); x[11] ^= R(x[10]+x[ 9], 7); x[ 8] ^= R(x[11]+x[10], 9); x[ 9] ^= R(x[ 8]+x[11],13); x[10] ^= R(x[ 9]+x[ 8],18); x[12] ^= R(x[15]+x[14], 7); x[13] ^= R(x[12]+x[15], 9); x[14] ^= R(x[13]+x[12],13); x[15] ^= R(x[14]+x[13],18); #undef R } /* Compute B32 = B32 + x. */ for (i = 0; i < 16; i++) B32[i] += x[i]; /* Convert little-endian values out. */ for (i = 0; i < 16; i++) le32enc(&B[4 * i], B32[i]); } /** * blockmix_salsa8(B, Y, r): * Compute B = BlockMix_{salsa20/8, r}(B). The input B must be 128r bytes in * length; the temporary space Y must also be the same size. */ static void blockmix_salsa8(uint8_t * B, uint8_t * Y, size_t r) { uint8_t X[64]; size_t i; /* 1: X <-- B_{2r - 1} */ blkcpy(X, &B[(2 * r - 1) * 64], 64); /* 2: for i = 0 to 2r - 1 do */ for (i = 0; i < 2 * r; i++) { /* 3: X <-- H(X \xor B_i) */ blkxor(X, &B[i * 64], 64); salsa20_8(X); /* 4: Y_i <-- X */ blkcpy(&Y[i * 64], X, 64); } /* 6: B' <-- (Y_0, Y_2 ... Y_{2r-2}, Y_1, Y_3 ... Y_{2r-1}) */ for (i = 0; i < r; i++) blkcpy(&B[i * 64], &Y[(i * 2) * 64], 64); for (i = 0; i < r; i++) blkcpy(&B[(i + r) * 64], &Y[(i * 2 + 1) * 64], 64); } /** * integerify(B, r): * Return the result of parsing B_{2r-1} as a little-endian integer. */ static uint64_t integerify(uint8_t * B, size_t r) { uint8_t * X = &B[(2 * r - 1) * 64]; return (le64dec(X)); } /** * smix(B, r, N, V, XY): * Compute B = SMix_r(B, N). The input B must be 128r bytes in length; the * temporary storage V must be 128rN bytes in length; the temporary storage * XY must be 256r bytes in length. The value N must be a power of 2. */ static void smix(uint8_t * B, size_t r, uint64_t N, uint8_t * V, uint8_t * XY) { uint8_t * X = XY; uint8_t * Y = &XY[128 * r]; uint64_t i; uint64_t j; /* 1: X <-- B */ blkcpy(X, B, 128 * r); /* 2: for i = 0 to N - 1 do */ for (i = 0; i < N; i++) { /* 3: V_i <-- X */ blkcpy(&V[i * (128 * r)], X, 128 * r); /* 4: X <-- H(X) */ blockmix_salsa8(X, Y, r); } /* 6: for i = 0 to N - 1 do */ for (i = 0; i < N; i++) { /* 7: j <-- Integerify(X) mod N */ j = integerify(X, r) & (N - 1); /* 8: X <-- H(X \xor V_j) */ blkxor(X, &V[j * (128 * r)], 128 * r); blockmix_salsa8(X, Y, r); } /* 10: B' <-- X */ blkcpy(B, X, 128 * r); } /** * crypto_scrypt(passwd, passwdlen, salt, saltlen, N, r, p, buf, buflen): * Compute scrypt(passwd[0 .. passwdlen - 1], salt[0 .. saltlen - 1], N, r, * p, buflen) and write the result into buf. The parameters r, p, and buflen * must satisfy r * p < 2^30 and buflen <= (2^32 - 1) * 32. The parameter N * must be a power of 2. * * Return 0 on success; or -1 on error. */ int crypto_scrypt(const uint8_t * passwd, size_t passwdlen, const uint8_t * salt, size_t saltlen, uint64_t N, uint32_t _r, uint32_t _p, uint8_t * buf, size_t buflen) { uint8_t * B; uint8_t * V; uint8_t * XY; size_t r = _r, p = _p; uint32_t i; /* Sanity-check parameters. */ #if SIZE_MAX > UINT32_MAX if (buflen > (((uint64_t)(1) << 32) - 1) * 32) { errno = EFBIG; goto err0; } #endif if ((uint64_t)(r) * (uint64_t)(p) >= (1 << 30)) { errno = EFBIG; goto err0; } if (((N & (N - 1)) != 0) || (N == 0)) { errno = EINVAL; goto err0; } if ((r > SIZE_MAX / 128 / p) || #if SIZE_MAX / 256 <= UINT32_MAX (r > SIZE_MAX / 256) || #endif (N > SIZE_MAX / 128 / r)) { errno = ENOMEM; goto err0; } /* Allocate memory. */ if ((B = malloc(128 * r * p)) == NULL) goto err0; if ((XY = malloc(256 * r)) == NULL) goto err1; if ((V = malloc(128 * r * N)) == NULL) goto err2; /* 1: (B_0 ... B_{p-1}) <-- PBKDF2(P, S, 1, p * MFLen) */ PBKDF2_SHA256(passwd, passwdlen, salt, saltlen, 1, B, p * 128 * r); /* 2: for i = 0 to p - 1 do */ for (i = 0; i < p; i++) { /* 3: B_i <-- MF(B_i, N) */ smix(&B[i * 128 * r], r, N, V, XY); } /* 5: DK <-- PBKDF2(P, B, 1, dkLen) */ PBKDF2_SHA256(passwd, passwdlen, B, p * 128 * r, 1, buf, buflen); /* Free memory. */ free(V); free(XY); free(B); /* Success! */ return (0); err2: free(XY); err1: free(B); err0: /* Failure! */ return (-1); } py-scrypt-0.8.24/scrypt-1.2.1/lib/crypto/crypto_scrypt.c000066400000000000000000000155671457042124400227370ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #include "scrypt_platform.h" #include #ifndef _WIN32 #include #endif #include #include #include #include #include "cpusupport.h" #include "sha256.h" #include "warnp.h" #include "crypto_scrypt_smix.h" #include "crypto_scrypt_smix_sse2.h" #include "crypto_scrypt.h" static void (*smix_func)(uint8_t *, size_t, uint64_t, void *, void *) = NULL; /** * _crypto_scrypt(passwd, passwdlen, salt, saltlen, N, r, p, buf, buflen, smix): * Perform the requested scrypt computation, using ${smix} as the smix routine. */ static int _crypto_scrypt(const uint8_t * passwd, size_t passwdlen, const uint8_t * salt, size_t saltlen, uint64_t N, uint32_t _r, uint32_t _p, uint8_t * buf, size_t buflen, void (*smix)(uint8_t *, size_t, uint64_t, void *, void *)) { void * B0, * V0, * XY0; uint8_t * B; uint32_t * V; uint32_t * XY; size_t r = _r, p = _p; uint32_t i; /* Sanity-check parameters. */ #if SIZE_MAX > UINT32_MAX if (buflen > (((uint64_t)(1) << 32) - 1) * 32) { errno = EFBIG; goto err0; } #endif if ((uint64_t)(r) * (uint64_t)(p) >= (1 << 30)) { errno = EFBIG; goto err0; } if (((N & (N - 1)) != 0) || (N < 2)) { errno = EINVAL; goto err0; } if ((r > SIZE_MAX / 128 / p) || #if SIZE_MAX / 256 <= UINT32_MAX (r > (SIZE_MAX - 64) / 256) || #endif (N > SIZE_MAX / 128 / r)) { errno = ENOMEM; goto err0; } /* Allocate memory. */ #ifdef HAVE_POSIX_MEMALIGN if ((errno = posix_memalign(&B0, 64, 128 * r * p)) != 0) goto err0; B = (uint8_t *)(B0); if ((errno = posix_memalign(&XY0, 64, 256 * r + 64)) != 0) goto err1; XY = (uint32_t *)(XY0); #if !defined(MAP_ANON) || !defined(HAVE_MMAP) if ((errno = posix_memalign(&V0, 64, (size_t)(128 * r * N))) != 0) goto err2; V = (uint32_t *)(V0); #endif #else if ((B0 = malloc(128 * r * p + 63)) == NULL) goto err0; B = (uint8_t *)(((uintptr_t)(B0) + 63) & ~ (uintptr_t)(63)); if ((XY0 = malloc(256 * r + 64 + 63)) == NULL) goto err1; XY = (uint32_t *)(((uintptr_t)(XY0) + 63) & ~ (uintptr_t)(63)); #if !defined(MAP_ANON) || !defined(HAVE_MMAP) if ((V0 = malloc(128 * r * N + 63)) == NULL) goto err2; V = (uint32_t *)(((uintptr_t)(V0) + 63) & ~ (uintptr_t)(63)); #endif #endif #if defined(MAP_ANON) && defined(HAVE_MMAP) if ((V0 = mmap(NULL, 128 * r * N, PROT_READ | PROT_WRITE, #ifdef MAP_NOCORE MAP_ANON | MAP_PRIVATE | MAP_NOCORE, #else MAP_ANON | MAP_PRIVATE, #endif -1, 0)) == MAP_FAILED) goto err2; V = (uint32_t *)(V0); #endif /* 1: (B_0 ... B_{p-1}) <-- PBKDF2(P, S, 1, p * MFLen) */ PBKDF2_SHA256(passwd, passwdlen, salt, saltlen, 1, B, p * 128 * r); /* 2: for i = 0 to p - 1 do */ for (i = 0; i < p; i++) { /* 3: B_i <-- MF(B_i, N) */ (smix)(&B[i * 128 * r], r, N, V, XY); } /* 5: DK <-- PBKDF2(P, B, 1, dkLen) */ PBKDF2_SHA256(passwd, passwdlen, B, p * 128 * r, 1, buf, buflen); /* Free memory. */ #if defined(MAP_ANON) && defined(HAVE_MMAP) if (munmap(V0, 128 * r * N)) goto err2; #else free(V0); #endif free(XY0); free(B0); /* Success! */ return (0); err2: free(XY0); err1: free(B0); err0: /* Failure! */ return (-1); } #define TESTLEN 64 static struct scrypt_test { const char * passwd; const char * salt; uint64_t N; uint32_t r; uint32_t p; uint8_t result[TESTLEN]; } testcase = { "pleaseletmein", "SodiumChloride", 16, 8, 1, { 0x25, 0xa9, 0xfa, 0x20, 0x7f, 0x87, 0xca, 0x09, 0xa4, 0xef, 0x8b, 0x9f, 0x77, 0x7a, 0xca, 0x16, 0xbe, 0xb7, 0x84, 0xae, 0x18, 0x30, 0xbf, 0xbf, 0xd3, 0x83, 0x25, 0xaa, 0xbb, 0x93, 0x77, 0xdf, 0x1b, 0xa7, 0x84, 0xd7, 0x46, 0xea, 0x27, 0x3b, 0xf5, 0x16, 0xa4, 0x6f, 0xbf, 0xac, 0xf5, 0x11, 0xc5, 0xbe, 0xba, 0x4c, 0x4a, 0xb3, 0xac, 0xc7, 0xfa, 0x6f, 0x46, 0x0b, 0x6c, 0x0f, 0x47, 0x7b, } }; static int testsmix(void (*smix)(uint8_t *, size_t, uint64_t, void *, void *)) { uint8_t hbuf[TESTLEN]; /* Perform the computation. */ if (_crypto_scrypt( (const uint8_t *)testcase.passwd, strlen(testcase.passwd), (const uint8_t *)testcase.salt, strlen(testcase.salt), testcase.N, testcase.r, testcase.p, hbuf, TESTLEN, smix)) return (-1); /* Does it match? */ return (memcmp(testcase.result, hbuf, TESTLEN)); } static void selectsmix(void) { #ifdef CPUSUPPORT_X86_SSE2 /* If we're running on an SSE2-capable CPU, try that code. */ if (cpusupport_x86_sse2()) { /* If SSE2ized smix works, use it. */ if (!testsmix(crypto_scrypt_smix_sse2)) { smix_func = crypto_scrypt_smix_sse2; return; } warn0("Disabling broken SSE2 scrypt support - please report bug!"); } #endif /* If generic smix works, use it. */ if (!testsmix(crypto_scrypt_smix)) { smix_func = crypto_scrypt_smix; return; } warn0("Generic scrypt code is broken - please report bug!"); /* If we get here, something really bad happened. */ abort(); } /** * crypto_scrypt(passwd, passwdlen, salt, saltlen, N, r, p, buf, buflen): * Compute scrypt(passwd[0 .. passwdlen - 1], salt[0 .. saltlen - 1], N, r, * p, buflen) and write the result into buf. The parameters r, p, and buflen * must satisfy r * p < 2^30 and buflen <= (2^32 - 1) * 32. The parameter N * must be a power of 2 greater than 1. * * Return 0 on success; or -1 on error. */ int crypto_scrypt(const uint8_t * passwd, size_t passwdlen, const uint8_t * salt, size_t saltlen, uint64_t N, uint32_t _r, uint32_t _p, uint8_t * buf, size_t buflen) { if (smix_func == NULL) selectsmix(); return (_crypto_scrypt(passwd, passwdlen, salt, saltlen, N, _r, _p, buf, buflen, smix_func)); } py-scrypt-0.8.24/scrypt-1.2.1/lib/crypto/crypto_scrypt.h000066400000000000000000000040661457042124400227340ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #ifndef _CRYPTO_SCRYPT_H_ #define _CRYPTO_SCRYPT_H_ #include #include /** * crypto_scrypt(passwd, passwdlen, salt, saltlen, N, r, p, buf, buflen): * Compute scrypt(passwd[0 .. passwdlen - 1], salt[0 .. saltlen - 1], N, r, * p, buflen) and write the result into buf. The parameters r, p, and buflen * must satisfy r * p < 2^30 and buflen <= (2^32 - 1) * 32. The parameter N * must be a power of 2 greater than 1. * * Return 0 on success; or -1 on error. */ int crypto_scrypt(const uint8_t *, size_t, const uint8_t *, size_t, uint64_t, uint32_t, uint32_t, uint8_t *, size_t); #endif /* !_CRYPTO_SCRYPT_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/lib/crypto/crypto_scrypt_smix.c000066400000000000000000000140301457042124400237570ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #include #include "sysendian.h" #include "crypto_scrypt_smix.h" static void blkcpy(void *, const void *, size_t); static void blkxor(void *, const void *, size_t); static void salsa20_8(uint32_t[16]); static void blockmix_salsa8(const uint32_t *, uint32_t *, uint32_t *, size_t); static uint64_t integerify(const void *, size_t); static void blkcpy(void * dest, const void * src, size_t len) { size_t * D = dest; const size_t * S = src; size_t L = len / sizeof(size_t); size_t i; for (i = 0; i < L; i++) D[i] = S[i]; } static void blkxor(void * dest, const void * src, size_t len) { size_t * D = dest; const size_t * S = src; size_t L = len / sizeof(size_t); size_t i; for (i = 0; i < L; i++) D[i] ^= S[i]; } /** * salsa20_8(B): * Apply the salsa20/8 core to the provided block. */ static void salsa20_8(uint32_t B[16]) { uint32_t x[16]; size_t i; blkcpy(x, B, 64); for (i = 0; i < 8; i += 2) { #define R(a,b) (((a) << (b)) | ((a) >> (32 - (b)))) /* Operate on columns. */ x[ 4] ^= R(x[ 0]+x[12], 7); x[ 8] ^= R(x[ 4]+x[ 0], 9); x[12] ^= R(x[ 8]+x[ 4],13); x[ 0] ^= R(x[12]+x[ 8],18); x[ 9] ^= R(x[ 5]+x[ 1], 7); x[13] ^= R(x[ 9]+x[ 5], 9); x[ 1] ^= R(x[13]+x[ 9],13); x[ 5] ^= R(x[ 1]+x[13],18); x[14] ^= R(x[10]+x[ 6], 7); x[ 2] ^= R(x[14]+x[10], 9); x[ 6] ^= R(x[ 2]+x[14],13); x[10] ^= R(x[ 6]+x[ 2],18); x[ 3] ^= R(x[15]+x[11], 7); x[ 7] ^= R(x[ 3]+x[15], 9); x[11] ^= R(x[ 7]+x[ 3],13); x[15] ^= R(x[11]+x[ 7],18); /* Operate on rows. */ x[ 1] ^= R(x[ 0]+x[ 3], 7); x[ 2] ^= R(x[ 1]+x[ 0], 9); x[ 3] ^= R(x[ 2]+x[ 1],13); x[ 0] ^= R(x[ 3]+x[ 2],18); x[ 6] ^= R(x[ 5]+x[ 4], 7); x[ 7] ^= R(x[ 6]+x[ 5], 9); x[ 4] ^= R(x[ 7]+x[ 6],13); x[ 5] ^= R(x[ 4]+x[ 7],18); x[11] ^= R(x[10]+x[ 9], 7); x[ 8] ^= R(x[11]+x[10], 9); x[ 9] ^= R(x[ 8]+x[11],13); x[10] ^= R(x[ 9]+x[ 8],18); x[12] ^= R(x[15]+x[14], 7); x[13] ^= R(x[12]+x[15], 9); x[14] ^= R(x[13]+x[12],13); x[15] ^= R(x[14]+x[13],18); #undef R } for (i = 0; i < 16; i++) B[i] += x[i]; } /** * blockmix_salsa8(Bin, Bout, X, r): * Compute Bout = BlockMix_{salsa20/8, r}(Bin). The input Bin must be 128r * bytes in length; the output Bout must also be the same size. The * temporary space X must be 64 bytes. */ static void blockmix_salsa8(const uint32_t * Bin, uint32_t * Bout, uint32_t * X, size_t r) { size_t i; /* 1: X <-- B_{2r - 1} */ blkcpy(X, &Bin[(2 * r - 1) * 16], 64); /* 2: for i = 0 to 2r - 1 do */ for (i = 0; i < 2 * r; i += 2) { /* 3: X <-- H(X \xor B_i) */ blkxor(X, &Bin[i * 16], 64); salsa20_8(X); /* 4: Y_i <-- X */ /* 6: B' <-- (Y_0, Y_2 ... Y_{2r-2}, Y_1, Y_3 ... Y_{2r-1}) */ blkcpy(&Bout[i * 8], X, 64); /* 3: X <-- H(X \xor B_i) */ blkxor(X, &Bin[i * 16 + 16], 64); salsa20_8(X); /* 4: Y_i <-- X */ /* 6: B' <-- (Y_0, Y_2 ... Y_{2r-2}, Y_1, Y_3 ... Y_{2r-1}) */ blkcpy(&Bout[i * 8 + r * 16], X, 64); } } /** * integerify(B, r): * Return the result of parsing B_{2r-1} as a little-endian integer. */ static uint64_t integerify(const void * B, size_t r) { const uint32_t * X = (const void *)((uintptr_t)(B) + (2 * r - 1) * 64); return (((uint64_t)(X[1]) << 32) + X[0]); } /** * crypto_scrypt_smix(B, r, N, V, XY): * Compute B = SMix_r(B, N). The input B must be 128r bytes in length; * the temporary storage V must be 128rN bytes in length; the temporary * storage XY must be 256r + 64 bytes in length. The value N must be a * power of 2 greater than 1. The arrays B, V, and XY must be aligned to a * multiple of 64 bytes. */ void crypto_scrypt_smix(uint8_t * B, size_t r, uint64_t N, void * _V, void * XY) { uint32_t * X = XY; uint32_t * Y = (void *)((uint8_t *)(XY) + 128 * r); uint32_t * Z = (void *)((uint8_t *)(XY) + 256 * r); uint32_t * V = _V; uint64_t i; uint64_t j; size_t k; /* 1: X <-- B */ for (k = 0; k < 32 * r; k++) X[k] = le32dec(&B[4 * k]); /* 2: for i = 0 to N - 1 do */ for (i = 0; i < N; i += 2) { /* 3: V_i <-- X */ blkcpy(&V[i * (32 * r)], X, 128 * r); /* 4: X <-- H(X) */ blockmix_salsa8(X, Y, Z, r); /* 3: V_i <-- X */ blkcpy(&V[(i + 1) * (32 * r)], Y, 128 * r); /* 4: X <-- H(X) */ blockmix_salsa8(Y, X, Z, r); } /* 6: for i = 0 to N - 1 do */ for (i = 0; i < N; i += 2) { /* 7: j <-- Integerify(X) mod N */ j = integerify(X, r) & (N - 1); /* 8: X <-- H(X \xor V_j) */ blkxor(X, &V[j * (32 * r)], 128 * r); blockmix_salsa8(X, Y, Z, r); /* 7: j <-- Integerify(X) mod N */ j = integerify(Y, r) & (N - 1); /* 8: X <-- H(X \xor V_j) */ blkxor(Y, &V[j * (32 * r)], 128 * r); blockmix_salsa8(Y, X, Z, r); } /* 10: B' <-- X */ for (k = 0; k < 32 * r; k++) le32enc(&B[4 * k], X[k]); } py-scrypt-0.8.24/scrypt-1.2.1/lib/crypto/crypto_scrypt_smix.h000066400000000000000000000011001457042124400237560ustar00rootroot00000000000000#ifndef _CRYPTO_SCRYPT_SMIX_H_ #define _CRYPTO_SCRYPT_SMIX_H_ #include #include /** * crypto_scrypt_smix(B, r, N, V, XY): * Compute B = SMix_r(B, N). The input B must be 128r bytes in length; * the temporary storage V must be 128rN bytes in length; the temporary * storage XY must be 256r + 64 bytes in length. The value N must be a * power of 2 greater than 1. The arrays B, V, and XY must be aligned to a * multiple of 64 bytes. */ void crypto_scrypt_smix(uint8_t *, size_t, uint64_t, void *, void *); #endif /* !_CRYPTO_SCRYPT_SMIX_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/lib/crypto/crypto_scrypt_smix_sse2.c000066400000000000000000000155601457042124400247240ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #include "cpusupport.h" #ifdef CPUSUPPORT_X86_SSE2 #include #include #include "sysendian.h" #include "crypto_scrypt_smix_sse2.h" static void blkcpy(void *, const void *, size_t); static void blkxor(void *, const void *, size_t); static void salsa20_8(__m128i *); static void blockmix_salsa8(const __m128i *, __m128i *, __m128i *, size_t); static uint64_t integerify(const void *, size_t); static void blkcpy(void * dest, const void * src, size_t len) { __m128i * D = dest; const __m128i * S = src; size_t L = len / 16; size_t i; for (i = 0; i < L; i++) D[i] = S[i]; } static void blkxor(void * dest, const void * src, size_t len) { __m128i * D = dest; const __m128i * S = src; size_t L = len / 16; size_t i; for (i = 0; i < L; i++) D[i] = _mm_xor_si128(D[i], S[i]); } /** * salsa20_8(B): * Apply the salsa20/8 core to the provided block. */ static void salsa20_8(__m128i B[4]) { __m128i X0, X1, X2, X3; __m128i T; size_t i; X0 = B[0]; X1 = B[1]; X2 = B[2]; X3 = B[3]; for (i = 0; i < 8; i += 2) { /* Operate on "columns". */ T = _mm_add_epi32(X0, X3); X1 = _mm_xor_si128(X1, _mm_slli_epi32(T, 7)); X1 = _mm_xor_si128(X1, _mm_srli_epi32(T, 25)); T = _mm_add_epi32(X1, X0); X2 = _mm_xor_si128(X2, _mm_slli_epi32(T, 9)); X2 = _mm_xor_si128(X2, _mm_srli_epi32(T, 23)); T = _mm_add_epi32(X2, X1); X3 = _mm_xor_si128(X3, _mm_slli_epi32(T, 13)); X3 = _mm_xor_si128(X3, _mm_srli_epi32(T, 19)); T = _mm_add_epi32(X3, X2); X0 = _mm_xor_si128(X0, _mm_slli_epi32(T, 18)); X0 = _mm_xor_si128(X0, _mm_srli_epi32(T, 14)); /* Rearrange data. */ X1 = _mm_shuffle_epi32(X1, 0x93); X2 = _mm_shuffle_epi32(X2, 0x4E); X3 = _mm_shuffle_epi32(X3, 0x39); /* Operate on "rows". */ T = _mm_add_epi32(X0, X1); X3 = _mm_xor_si128(X3, _mm_slli_epi32(T, 7)); X3 = _mm_xor_si128(X3, _mm_srli_epi32(T, 25)); T = _mm_add_epi32(X3, X0); X2 = _mm_xor_si128(X2, _mm_slli_epi32(T, 9)); X2 = _mm_xor_si128(X2, _mm_srli_epi32(T, 23)); T = _mm_add_epi32(X2, X3); X1 = _mm_xor_si128(X1, _mm_slli_epi32(T, 13)); X1 = _mm_xor_si128(X1, _mm_srli_epi32(T, 19)); T = _mm_add_epi32(X1, X2); X0 = _mm_xor_si128(X0, _mm_slli_epi32(T, 18)); X0 = _mm_xor_si128(X0, _mm_srli_epi32(T, 14)); /* Rearrange data. */ X1 = _mm_shuffle_epi32(X1, 0x39); X2 = _mm_shuffle_epi32(X2, 0x4E); X3 = _mm_shuffle_epi32(X3, 0x93); } B[0] = _mm_add_epi32(B[0], X0); B[1] = _mm_add_epi32(B[1], X1); B[2] = _mm_add_epi32(B[2], X2); B[3] = _mm_add_epi32(B[3], X3); } /** * blockmix_salsa8(Bin, Bout, X, r): * Compute Bout = BlockMix_{salsa20/8, r}(Bin). The input Bin must be 128r * bytes in length; the output Bout must also be the same size. The * temporary space X must be 64 bytes. */ static void blockmix_salsa8(const __m128i * Bin, __m128i * Bout, __m128i * X, size_t r) { size_t i; /* 1: X <-- B_{2r - 1} */ blkcpy(X, &Bin[8 * r - 4], 64); /* 2: for i = 0 to 2r - 1 do */ for (i = 0; i < r; i++) { /* 3: X <-- H(X \xor B_i) */ blkxor(X, &Bin[i * 8], 64); salsa20_8(X); /* 4: Y_i <-- X */ /* 6: B' <-- (Y_0, Y_2 ... Y_{2r-2}, Y_1, Y_3 ... Y_{2r-1}) */ blkcpy(&Bout[i * 4], X, 64); /* 3: X <-- H(X \xor B_i) */ blkxor(X, &Bin[i * 8 + 4], 64); salsa20_8(X); /* 4: Y_i <-- X */ /* 6: B' <-- (Y_0, Y_2 ... Y_{2r-2}, Y_1, Y_3 ... Y_{2r-1}) */ blkcpy(&Bout[(r + i) * 4], X, 64); } } /** * integerify(B, r): * Return the result of parsing B_{2r-1} as a little-endian integer. * Note that B's layout is permuted compared to the generic implementation. */ static uint64_t integerify(const void * B, size_t r) { const uint32_t * X = (const void *)((uintptr_t)(B) + (2 * r - 1) * 64); return (((uint64_t)(X[13]) << 32) + X[0]); } /** * crypto_scrypt_smix_sse2(B, r, N, V, XY): * Compute B = SMix_r(B, N). The input B must be 128r bytes in length; * the temporary storage V must be 128rN bytes in length; the temporary * storage XY must be 256r + 64 bytes in length. The value N must be a * power of 2 greater than 1. The arrays B, V, and XY must be aligned to a * multiple of 64 bytes. * * Use SSE2 instructions. */ void crypto_scrypt_smix_sse2(uint8_t * B, size_t r, uint64_t N, void * V, void * XY) { __m128i * X = XY; __m128i * Y = (void *)((uintptr_t)(XY) + 128 * r); __m128i * Z = (void *)((uintptr_t)(XY) + 256 * r); uint32_t * X32 = (void *)X; uint64_t i, j; size_t k; /* 1: X <-- B */ for (k = 0; k < 2 * r; k++) { for (i = 0; i < 16; i++) { X32[k * 16 + i] = le32dec(&B[(k * 16 + (i * 5 % 16)) * 4]); } } /* 2: for i = 0 to N - 1 do */ for (i = 0; i < N; i += 2) { /* 3: V_i <-- X */ blkcpy((void *)((uintptr_t)(V) + i * 128 * r), X, 128 * r); /* 4: X <-- H(X) */ blockmix_salsa8(X, Y, Z, r); /* 3: V_i <-- X */ blkcpy((void *)((uintptr_t)(V) + (i + 1) * 128 * r), Y, 128 * r); /* 4: X <-- H(X) */ blockmix_salsa8(Y, X, Z, r); } /* 6: for i = 0 to N - 1 do */ for (i = 0; i < N; i += 2) { /* 7: j <-- Integerify(X) mod N */ j = integerify(X, r) & (N - 1); /* 8: X <-- H(X \xor V_j) */ blkxor(X, (void *)((uintptr_t)(V) + j * 128 * r), 128 * r); blockmix_salsa8(X, Y, Z, r); /* 7: j <-- Integerify(X) mod N */ j = integerify(Y, r) & (N - 1); /* 8: X <-- H(X \xor V_j) */ blkxor(Y, (void *)((uintptr_t)(V) + j * 128 * r), 128 * r); blockmix_salsa8(Y, X, Z, r); } /* 10: B' <-- X */ for (k = 0; k < 2 * r; k++) { for (i = 0; i < 16; i++) { le32enc(&B[(k * 16 + (i * 5 % 16)) * 4], X32[k * 16 + i]); } } } #endif /* CPUSUPPORT_X86_SSE2 */ py-scrypt-0.8.24/scrypt-1.2.1/lib/crypto/crypto_scrypt_smix_sse2.h000066400000000000000000000011661457042124400247260ustar00rootroot00000000000000#ifndef _CRYPTO_SCRYPT_SMIX_SSE2_H_ #define _CRYPTO_SCRYPT_SMIX_SSE2_H_ #include #include /** * crypto_scrypt_smix_sse2(B, r, N, V, XY): * Compute B = SMix_r(B, N). The input B must be 128r bytes in length; * the temporary storage V must be 128rN bytes in length; the temporary * storage XY must be 256r + 64 bytes in length. The value N must be a * power of 2 greater than 1. The arrays B, V, and XY must be aligned to a * multiple of 64 bytes. * * Use SSE2 instructions. */ void crypto_scrypt_smix_sse2(uint8_t *, size_t, uint64_t, void *, void *); #endif /* !_CRYPTO_SCRYPT_SMIX_SSE2_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/lib/scryptenc/000077500000000000000000000000001457042124400203235ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/lib/scryptenc/scryptenc.c000066400000000000000000000401531457042124400225040ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #include "scrypt_platform.h" #include #include #include #include #include #include #include "crypto_aes.h" #include "crypto_aesctr.h" #include "crypto_entropy.h" #include "humansize.h" #include "insecure_memzero.h" #include "sha256.h" #include "sysendian.h" #include "crypto_scrypt.h" #include "memlimit.h" #include "scryptenc_cpuperf.h" #include "scryptenc.h" #define ENCBLOCK 65536 static int pickparams(size_t, double, double, int *, uint32_t *, uint32_t *, int); static int checkparams(size_t, double, double, int, uint32_t, uint32_t, int, int); static void display_params(int logN, uint32_t r, uint32_t p, size_t memlimit, double opps, double maxtime) { uint64_t N = (uint64_t)(1) << logN; uint64_t mem_minimum = 128 * r * N; double expected_seconds = 4 * N * p / opps; char * human_memlimit = humansize(memlimit); char * human_mem_minimum = humansize(mem_minimum); fprintf(stderr, "Parameters used: N = %" PRIu64 "; r = %" PRIu32 "; p = %" PRIu32 ";\n", N, r, p); fprintf(stderr, " This requires at least %s bytes of memory " "(%s available),\n", human_mem_minimum, human_memlimit); fprintf(stderr, " and will take approximately %.1f seconds " "(limit: %.1f seconds).\n", expected_seconds, maxtime); free(human_memlimit); free(human_mem_minimum); } static int pickparams(size_t maxmem, double maxmemfrac, double maxtime, int * logN, uint32_t * r, uint32_t * p, int verbose) { size_t memlimit; double opps; double opslimit; double maxN, maxrp; int rc; /* Figure out how much memory to use. */ if (memtouse(maxmem, maxmemfrac, &memlimit)) return (1); /* Figure out how fast the CPU is. */ if ((rc = scryptenc_cpuperf(&opps)) != 0) return (rc); opslimit = opps * maxtime; /* Allow a minimum of 2^15 salsa20/8 cores. */ if (opslimit < 32768) opslimit = 32768; /* Fix r = 8 for now. */ *r = 8; /* * The memory limit requires that 128Nr <= memlimit, while the CPU * limit requires that 4Nrp <= opslimit. If opslimit < memlimit/32, * opslimit imposes the stronger limit on N. */ #ifdef DEBUG fprintf(stderr, "Requiring 128Nr <= %zu, 4Nrp <= %f\n", memlimit, opslimit); #endif if (opslimit < (double)memlimit / 32) { /* Set p = 1 and choose N based on the CPU limit. */ *p = 1; maxN = opslimit / (*r * 4); for (*logN = 1; *logN < 63; *logN += 1) { if ((uint64_t)(1) << *logN > maxN / 2) break; } } else { /* Set N based on the memory limit. */ maxN = memlimit / (*r * 128); for (*logN = 1; *logN < 63; *logN += 1) { if ((uint64_t)(1) << *logN > maxN / 2) break; } /* Choose p based on the CPU limit. */ maxrp = (opslimit / 4) / ((uint64_t)(1) << *logN); if (maxrp > 0x3fffffff) maxrp = 0x3fffffff; *p = (uint32_t)(maxrp) / *r; } if (verbose) display_params(*logN, *r, *p, memlimit, opps, maxtime); /* Success! */ return (0); } static int checkparams(size_t maxmem, double maxmemfrac, double maxtime, int logN, uint32_t r, uint32_t p, int verbose, int force) { size_t memlimit; double opps; double opslimit; uint64_t N; int rc; /* Sanity-check values. */ if ((logN < 1) || (logN > 63)) return (7); if ((uint64_t)(r) * (uint64_t)(p) >= 0x40000000) return (7); /* Are we forcing decryption, regardless of resource limits? */ if (!force) { /* Figure out the maximum amount of memory we can use. */ if (memtouse(maxmem, maxmemfrac, &memlimit)) return (1); /* Figure out how fast the CPU is. */ if ((rc = scryptenc_cpuperf(&opps)) != 0) return (rc); opslimit = opps * maxtime; /* Check limits. */ N = (uint64_t)(1) << logN; if ((memlimit / N) / r < 128) return (9); if ((opslimit / N) / (r * p) < 4) return (10); } else { /* We have no limit. */ memlimit = 0; opps = 0; } if (verbose) display_params(logN, r, p, memlimit, opps, maxtime); /* Success! */ return (0); } static int scryptenc_setup(uint8_t header[96], uint8_t dk[64], const uint8_t * passwd, size_t passwdlen, size_t maxmem, double maxmemfrac, double maxtime, int verbose) { uint8_t salt[32]; uint8_t hbuf[32]; int logN; uint64_t N; uint32_t r; uint32_t p; SHA256_CTX ctx; uint8_t * key_hmac = &dk[32]; HMAC_SHA256_CTX hctx; int rc; /* Pick values for N, r, p. */ if ((rc = pickparams(maxmem, maxmemfrac, maxtime, &logN, &r, &p, verbose)) != 0) return (rc); N = (uint64_t)(1) << logN; /* Sanity check. */ assert((logN > 0) && (logN < 256)); /* Get some salt. */ if (crypto_entropy_read(salt, 32)) return (4); /* Generate the derived keys. */ if (crypto_scrypt(passwd, passwdlen, salt, 32, N, r, p, dk, 64)) return (3); /* Construct the file header. */ memcpy(header, "scrypt", 6); header[6] = 0; header[7] = logN & 0xff; be32enc(&header[8], r); be32enc(&header[12], p); memcpy(&header[16], salt, 32); /* Add header checksum. */ SHA256_Init(&ctx); SHA256_Update(&ctx, header, 48); SHA256_Final(hbuf, &ctx); memcpy(&header[48], hbuf, 16); /* Add header signature (used for verifying password). */ HMAC_SHA256_Init(&hctx, key_hmac, 32); HMAC_SHA256_Update(&hctx, header, 64); HMAC_SHA256_Final(hbuf, &hctx); memcpy(&header[64], hbuf, 32); /* Success! */ return (0); } static int scryptdec_setup(const uint8_t header[96], uint8_t dk[64], const uint8_t * passwd, size_t passwdlen, size_t maxmem, double maxmemfrac, double maxtime, int verbose, int force) { uint8_t salt[32]; uint8_t hbuf[32]; int logN; uint32_t r; uint32_t p; uint64_t N; SHA256_CTX ctx; uint8_t * key_hmac = &dk[32]; HMAC_SHA256_CTX hctx; int rc; /* Parse N, r, p, salt. */ logN = header[7]; r = be32dec(&header[8]); p = be32dec(&header[12]); memcpy(salt, &header[16], 32); /* Verify header checksum. */ SHA256_Init(&ctx); SHA256_Update(&ctx, header, 48); SHA256_Final(hbuf, &ctx); if (memcmp(&header[48], hbuf, 16)) return (7); /* * Check whether the provided parameters are valid and whether the * key derivation function can be computed within the allowed memory * and CPU time, unless the user chose to disable this test. */ if ((rc = checkparams(maxmem, maxmemfrac, maxtime, logN, r, p, verbose, force)) != 0) return (rc); /* Compute the derived keys. */ N = (uint64_t)(1) << logN; if (crypto_scrypt(passwd, passwdlen, salt, 32, N, r, p, dk, 64)) return (3); /* Check header signature (i.e., verify password). */ HMAC_SHA256_Init(&hctx, key_hmac, 32); HMAC_SHA256_Update(&hctx, header, 64); HMAC_SHA256_Final(hbuf, &hctx); if (memcmp(hbuf, &header[64], 32)) return (11); /* Success! */ return (0); } /** * scryptenc_buf(inbuf, inbuflen, outbuf, passwd, passwdlen, * maxmem, maxmemfrac, maxtime, verbose): * Encrypt inbuflen bytes from inbuf, writing the resulting inbuflen + 128 * bytes to outbuf. */ int scryptenc_buf(const uint8_t * inbuf, size_t inbuflen, uint8_t * outbuf, const uint8_t * passwd, size_t passwdlen, size_t maxmem, double maxmemfrac, double maxtime, int verbose) { uint8_t dk[64]; uint8_t hbuf[32]; uint8_t header[96]; uint8_t * key_enc = dk; uint8_t * key_hmac = &dk[32]; int rc; HMAC_SHA256_CTX hctx; struct crypto_aes_key * key_enc_exp; struct crypto_aesctr * AES; /* Generate the header and derived key. */ if ((rc = scryptenc_setup(header, dk, passwd, passwdlen, maxmem, maxmemfrac, maxtime, verbose)) != 0) return (rc); /* Copy header into output buffer. */ memcpy(outbuf, header, 96); /* Encrypt data. */ if ((key_enc_exp = crypto_aes_key_expand(key_enc, 32)) == NULL) return (5); if ((AES = crypto_aesctr_init(key_enc_exp, 0)) == NULL) return (6); crypto_aesctr_stream(AES, inbuf, &outbuf[96], inbuflen); crypto_aesctr_free(AES); crypto_aes_key_free(key_enc_exp); /* Add signature. */ HMAC_SHA256_Init(&hctx, key_hmac, 32); HMAC_SHA256_Update(&hctx, outbuf, 96 + inbuflen); HMAC_SHA256_Final(hbuf, &hctx); memcpy(&outbuf[96 + inbuflen], hbuf, 32); /* Zero sensitive data. */ insecure_memzero(dk, 64); /* Success! */ return (0); } /** * scryptdec_buf(inbuf, inbuflen, outbuf, outlen, passwd, passwdlen, * maxmem, maxmemfrac, maxtime, verbose, force): * Decrypt inbuflen bytes from inbuf, writing the result into outbuf and the * decrypted data length to outlen. The allocated length of outbuf must * be at least inbuflen. If ${force} is 1, do not check whether * decryption will exceed the estimated available memory or time. */ int scryptdec_buf(const uint8_t * inbuf, size_t inbuflen, uint8_t * outbuf, size_t * outlen, const uint8_t * passwd, size_t passwdlen, size_t maxmem, double maxmemfrac, double maxtime, int verbose, int force) { uint8_t hbuf[32]; uint8_t dk[64]; uint8_t * key_enc = dk; uint8_t * key_hmac = &dk[32]; int rc; HMAC_SHA256_CTX hctx; struct crypto_aes_key * key_enc_exp; struct crypto_aesctr * AES; /* * All versions of the scrypt format will start with "scrypt" and * have at least 7 bytes of header. */ if ((inbuflen < 7) || (memcmp(inbuf, "scrypt", 6) != 0)) return (7); /* Check the format. */ if (inbuf[6] != 0) return (8); /* We must have at least 128 bytes. */ if (inbuflen < 128) return (7); /* Parse the header and generate derived keys. */ if ((rc = scryptdec_setup(inbuf, dk, passwd, passwdlen, maxmem, maxmemfrac, maxtime, verbose, force)) != 0) return (rc); /* Decrypt data. */ if ((key_enc_exp = crypto_aes_key_expand(key_enc, 32)) == NULL) return (5); if ((AES = crypto_aesctr_init(key_enc_exp, 0)) == NULL) return (6); crypto_aesctr_stream(AES, &inbuf[96], outbuf, inbuflen - 128); crypto_aesctr_free(AES); crypto_aes_key_free(key_enc_exp); *outlen = inbuflen - 128; /* Verify signature. */ HMAC_SHA256_Init(&hctx, key_hmac, 32); HMAC_SHA256_Update(&hctx, inbuf, inbuflen - 32); HMAC_SHA256_Final(hbuf, &hctx); if (memcmp(hbuf, &inbuf[inbuflen - 32], 32)) return (7); /* Zero sensitive data. */ insecure_memzero(dk, 64); /* Success! */ return (0); } /** * scryptenc_file(infile, outfile, passwd, passwdlen, * maxmem, maxmemfrac, maxtime, verbose): * Read a stream from infile and encrypt it, writing the resulting stream to * outfile. */ int scryptenc_file(FILE * infile, FILE * outfile, const uint8_t * passwd, size_t passwdlen, size_t maxmem, double maxmemfrac, double maxtime, int verbose) { uint8_t buf[ENCBLOCK]; uint8_t dk[64]; uint8_t hbuf[32]; uint8_t header[96]; uint8_t * key_enc = dk; uint8_t * key_hmac = &dk[32]; size_t readlen; HMAC_SHA256_CTX hctx; struct crypto_aes_key * key_enc_exp; struct crypto_aesctr * AES; int rc; /* Generate the header and derived key. */ if ((rc = scryptenc_setup(header, dk, passwd, passwdlen, maxmem, maxmemfrac, maxtime, verbose)) != 0) return (rc); /* Hash and write the header. */ HMAC_SHA256_Init(&hctx, key_hmac, 32); HMAC_SHA256_Update(&hctx, header, 96); if (fwrite(header, 96, 1, outfile) != 1) return (12); /* * Read blocks of data, encrypt them, and write them out; hash the * data as it is produced. */ if ((key_enc_exp = crypto_aes_key_expand(key_enc, 32)) == NULL) return (5); if ((AES = crypto_aesctr_init(key_enc_exp, 0)) == NULL) return (6); do { if ((readlen = fread(buf, 1, ENCBLOCK, infile)) == 0) break; crypto_aesctr_stream(AES, buf, buf, readlen); HMAC_SHA256_Update(&hctx, buf, readlen); if (fwrite(buf, 1, readlen, outfile) < readlen) { crypto_aesctr_free(AES); return (12); } } while (1); crypto_aesctr_free(AES); crypto_aes_key_free(key_enc_exp); /* Did we exit the loop due to a read error? */ if (ferror(infile)) return (13); /* Compute the final HMAC and output it. */ HMAC_SHA256_Final(hbuf, &hctx); if (fwrite(hbuf, 32, 1, outfile) != 1) return (12); /* Zero sensitive data. */ insecure_memzero(dk, 64); /* Success! */ return (0); } /** * scryptdec_file(infile, outfile, passwd, passwdlen, * maxmem, maxmemfrac, maxtime, verbose, force): * Read a stream from infile and decrypt it, writing the resulting stream to * outfile. If ${force} is 1, do not check whether decryption * will exceed the estimated available memory or time. */ int scryptdec_file(FILE * infile, FILE * outfile, const uint8_t * passwd, size_t passwdlen, size_t maxmem, double maxmemfrac, double maxtime, int verbose, int force) { uint8_t buf[ENCBLOCK + 32]; uint8_t header[96]; uint8_t hbuf[32]; uint8_t dk[64]; uint8_t * key_enc = dk; uint8_t * key_hmac = &dk[32]; size_t buflen = 0; size_t readlen; HMAC_SHA256_CTX hctx; struct crypto_aes_key * key_enc_exp; struct crypto_aesctr * AES; int rc; /* * Read the first 7 bytes of the file; all future versions of scrypt * are guaranteed to have at least 7 bytes of header. */ if (fread(header, 7, 1, infile) < 1) { if (ferror(infile)) return (13); else return (7); } /* Do we have the right magic? */ if (memcmp(header, "scrypt", 6)) return (7); if (header[6] != 0) return (8); /* * Read another 89 bytes of the file; version 0 of the scrypt file * format has a 96-byte header. */ if (fread(&header[7], 89, 1, infile) < 1) { if (ferror(infile)) return (13); else return (7); } /* Parse the header and generate derived keys. */ if ((rc = scryptdec_setup(header, dk, passwd, passwdlen, maxmem, maxmemfrac, maxtime, verbose, force)) != 0) return (rc); /* Start hashing with the header. */ HMAC_SHA256_Init(&hctx, key_hmac, 32); HMAC_SHA256_Update(&hctx, header, 96); /* * We don't know how long the encrypted data block is (we can't know, * since data can be streamed into 'scrypt enc') so we need to read * data and decrypt all of it except the final 32 bytes, then check * if that final 32 bytes is the correct signature. */ if ((key_enc_exp = crypto_aes_key_expand(key_enc, 32)) == NULL) return (5); if ((AES = crypto_aesctr_init(key_enc_exp, 0)) == NULL) return (6); do { /* Read data until we have more than 32 bytes of it. */ if ((readlen = fread(&buf[buflen], 1, ENCBLOCK + 32 - buflen, infile)) == 0) break; buflen += readlen; if (buflen <= 32) continue; /* * Decrypt, hash, and output everything except the last 32 * bytes out of what we have in our buffer. */ HMAC_SHA256_Update(&hctx, buf, buflen - 32); crypto_aesctr_stream(AES, buf, buf, buflen - 32); if (fwrite(buf, 1, buflen - 32, outfile) < buflen - 32) { crypto_aesctr_free(AES); return (12); } /* Move the last 32 bytes to the start of the buffer. */ memmove(buf, &buf[buflen - 32], 32); buflen = 32; } while (1); crypto_aesctr_free(AES); crypto_aes_key_free(key_enc_exp); /* Did we exit the loop due to a read error? */ if (ferror(infile)) return (13); /* Did we read enough data that we *might* have a valid signature? */ if (buflen < 32) return (7); /* Verify signature. */ HMAC_SHA256_Final(hbuf, &hctx); if (memcmp(hbuf, buf, 32)) return (7); /* Zero sensitive data. */ insecure_memzero(dk, 64); return (0); } py-scrypt-0.8.24/scrypt-1.2.1/lib/scryptenc/scryptenc.h000066400000000000000000000123501457042124400225070ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #ifndef _SCRYPTENC_H_ #define _SCRYPTENC_H_ #include #include /** * NOTE: This file provides prototypes for routines which encrypt/decrypt data * using a key derived from a password by using the scrypt key derivation * function. If you are just trying to "hash" a password for user logins, * this is not the code you are looking for. You want to use the crypto_scrypt * function directly. */ /** * The parameters maxmem, maxmemfrac, and maxtime used by all of these * functions are defined as follows: * maxmem - maximum number of bytes of storage to use for V array (which is * by far the largest consumer of memory). If this value is set to 0, no * maximum will be enforced; any other value less than 1 MiB will be * treated as 1 MiB. * maxmemfrac - maximum fraction of available storage to use for the V array, * where "available storage" is defined as the minimum out of the * RLIMIT_AS, RLIMIT_DATA. and RLIMIT_RSS resource limits (if any are * set). If this value is set to 0 or more than 0.5 it will be treated * as 0.5; and this value will never cause a limit of less than 1 MiB to * be enforced. * maxtime - maximum amount of CPU time to spend computing the derived keys, * in seconds. This limit is only approximately enforced; the CPU * performance is estimated and parameter limits are chosen accordingly. * For the encryption functions, the parameters to the scrypt key derivation * function are chosen to make the key as strong as possible subject to the * specified limits; for the decryption functions, the parameters used are * compared to the computed limits and an error is returned if decrypting * the data would take too much memory or CPU time. */ /** * Return codes from scrypt(enc|dec)_(buf|file): * 0 success * 1 getrlimit or sysctl(hw.usermem) failed * 2 clock_getres or clock_gettime failed * 3 error computing derived key * 4 could not read salt from /dev/urandom * 5 error in OpenSSL * 6 malloc failed * 7 data is not a valid scrypt-encrypted block * 8 unrecognized scrypt format * 9 decrypting file would take too much memory * 10 decrypting file would take too long * 11 password is incorrect * 12 error writing output file * 13 error reading input file */ /** * scryptenc_buf(inbuf, inbuflen, outbuf, passwd, passwdlen, * maxmem, maxmemfrac, maxtime, verbose): * Encrypt inbuflen bytes from inbuf, writing the resulting inbuflen + 128 * bytes to outbuf. */ int scryptenc_buf(const uint8_t *, size_t, uint8_t *, const uint8_t *, size_t, size_t, double, double, int); /** * scryptdec_buf(inbuf, inbuflen, outbuf, outlen, passwd, passwdlen, * maxmem, maxmemfrac, maxtime, verbose, force): * Decrypt inbuflen bytes from inbuf, writing the result into outbuf and the * decrypted data length to outlen. The allocated length of outbuf must * be at least inbuflen. If ${force} is 1, do not check whether * decryption will exceed the estimated available memory or time. */ int scryptdec_buf(const uint8_t *, size_t, uint8_t *, size_t *, const uint8_t *, size_t, size_t, double, double, int, int); /** * scryptenc_file(infile, outfile, passwd, passwdlen, * maxmem, maxmemfrac, maxtime, verbose): * Read a stream from infile and encrypt it, writing the resulting stream to * outfile. */ int scryptenc_file(FILE *, FILE *, const uint8_t *, size_t, size_t, double, double, int); /** * scryptdec_file(infile, outfile, passwd, passwdlen, * maxmem, maxmemfrac, maxtime, verbose, force): * Read a stream from infile and decrypt it, writing the resulting stream to * outfile. If ${force} is 1, do not check whether decryption * will exceed the estimated available memory or time. */ int scryptdec_file(FILE *, FILE *, const uint8_t *, size_t, size_t, double, double, int, int); #endif /* !_SCRYPTENC_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/lib/scryptenc/scryptenc_cpuperf.c000066400000000000000000000104731457042124400242320ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #include "scrypt_platform.h" #include #include #include #include #include "crypto_scrypt.h" #include "scryptenc_cpuperf.h" #ifdef HAVE_CLOCK_GETTIME static clockid_t clocktouse; static int getclockres(double * resd) { struct timespec res; /* * Try clocks in order of preference until we find one which works. * (We assume that if clock_getres works, clock_gettime will, too.) * The use of if/else/if/else/if/else rather than if/elif/elif/else * is ugly but legal, and allows us to #ifdef things appropriately. */ #ifdef CLOCK_VIRTUAL if (clock_getres(CLOCK_VIRTUAL, &res) == 0) clocktouse = CLOCK_VIRTUAL; else #endif #ifdef CLOCK_MONOTONIC if (clock_getres(CLOCK_MONOTONIC, &res) == 0) clocktouse = CLOCK_MONOTONIC; else #endif if (clock_getres(CLOCK_REALTIME, &res) == 0) clocktouse = CLOCK_REALTIME; else return (-1); /* Convert clock resolution to a double. */ *resd = res.tv_sec + res.tv_nsec * 0.000000001; return (0); } static int getclocktime(struct timespec * ts) { if (clock_gettime(clocktouse, ts)) return (-1); return (0); } #else static int getclockres(double * resd) { *resd = 1.0 / CLOCKS_PER_SEC; return (0); } static int getclocktime(struct timespec * ts) { struct timeval tv; if (gettimeofday(&tv, NULL)) return (-1); ts->tv_sec = tv.tv_sec; ts->tv_nsec = tv.tv_usec * 1000; return (0); } #endif static int getclockdiff(struct timespec * st, double * diffd) { struct timespec en; if (getclocktime(&en)) return (1); *diffd = (en.tv_nsec - st->tv_nsec) * 0.000000001 + (en.tv_sec - st->tv_sec); return (0); } /** * scryptenc_cpuperf(opps): * Estimate the number of salsa20/8 cores which can be executed per second, * and return the value via opps. */ int scryptenc_cpuperf(double * opps) { struct timespec st; double resd, diffd; uint64_t i = 0; /* Get the clock resolution. */ if (getclockres(&resd)) return (2); #ifdef DEBUG fprintf(stderr, "Clock resolution is %f\n", resd); #endif /* Loop until the clock ticks. */ if (getclocktime(&st)) return (2); do { /* Do an scrypt. */ if (crypto_scrypt(NULL, 0, NULL, 0, 16, 1, 1, NULL, 0)) return (3); /* Has the clock ticked? */ if (getclockdiff(&st, &diffd)) return (2); if (diffd > 0) break; } while (1); /* Count how many scrypts we can do before the next tick. */ if (getclocktime(&st)) return (2); do { /* Do an scrypt. */ if (crypto_scrypt(NULL, 0, NULL, 0, 128, 1, 1, NULL, 0)) return (3); /* We invoked the salsa20/8 core 512 times. */ i += 512; /* Check if we have looped for long enough. */ if (getclockdiff(&st, &diffd)) return (2); if (diffd > resd) break; } while (1); #ifdef DEBUG fprintf(stderr, "%ju salsa20/8 cores performed in %f seconds\n", (uintmax_t)i, diffd); #endif /* We can do approximately i salsa20/8 cores per diffd seconds. */ *opps = i / diffd; return (0); } py-scrypt-0.8.24/scrypt-1.2.1/lib/scryptenc/scryptenc_cpuperf.h000066400000000000000000000033061457042124400242340ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #ifndef _SCRYPTENC_CPUPERF_H_ #define _SCRYPTENC_CPUPERF_H_ /** * scryptenc_cpuperf(opps): * Estimate the number of salsa20/8 cores which can be executed per second, * and return the value via opps. */ int scryptenc_cpuperf(double *); #endif /* !_SCRYPTENC_CPUPERF_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/lib/util/000077500000000000000000000000001457042124400172665ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/lib/util/memlimit.c000066400000000000000000000207161457042124400212550ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ /* We use non-POSIX functionality in this file. */ #undef _POSIX_C_SOURCE #include "scrypt_platform.h" #include #ifndef _WIN32 #include #else #define _WIN32_WINNT 0x0502 #include #include #endif #ifdef HAVE_SYS_PARAM_H #include #endif #ifdef HAVE_SYS_SYSCTL_H #include #endif #ifdef HAVE_SYS_SYSINFO_H #include #endif #include #include #include #include #include #ifdef DEBUG #include #endif #include "memlimit.h" /* If we don't have CTL_HW, we can't use HW_USERMEM. */ #ifndef CTL_HW #undef HW_USERMEM #endif #ifdef CTL_HW static int memlimit_sysctl_hw(size_t * memlimit, int mibleaf) { int mib[2]; uint8_t sysctlbuf[8]; size_t sysctlbuflen = 8; uint64_t sysctlval; /* Ask the kernel how much RAM we have. */ mib[0] = CTL_HW; mib[1] = mibleaf; if (sysctl(mib, 2, sysctlbuf, &sysctlbuflen, NULL, 0)) return (1); /* * If we read 8 bytes out, assume this is a system-endian uint64_t. * If we only read 4 bytes out, the OS is trying to give us a * uint32_t answer -- but given how many systems now have 4GB+ of RAM, * it's probably truncating, and we really can't trust the value we * have returned to us. */ if (sysctlbuflen == sizeof(uint64_t)) memcpy(&sysctlval, sysctlbuf, sizeof(uint64_t)); else if (sysctlbuflen == sizeof(uint32_t)) sysctlval = SIZE_MAX; else return (1); /* Return the sysctl value, but clamp to SIZE_MAX if necessary. */ #if UINT64_MAX > SIZE_MAX if (sysctlval > SIZE_MAX) *memlimit = SIZE_MAX; else *memlimit = (size_t)sysctlval; #else *memlimit = sysctlval; #endif /* Success! */ return (0); } #endif /* If we don't HAVE_STRUCT_SYSINFO, we can't use sysinfo. */ #ifndef HAVE_STRUCT_SYSINFO #undef HAVE_SYSINFO #endif /* If we don't HAVE_STRUCT_SYSINFO_TOTALRAM, we can't use sysinfo. */ #ifndef HAVE_STRUCT_SYSINFO_TOTALRAM #undef HAVE_SYSINFO #endif #ifdef HAVE_SYSINFO static int memlimit_sysinfo(size_t * memlimit) { struct sysinfo info; uint64_t totalmem; /* Get information from the kernel. */ if (sysinfo(&info)) return (1); totalmem = info.totalram; /* If we're on a modern kernel, adjust based on mem_unit. */ #ifdef HAVE_STRUCT_SYSINFO_MEM_UNIT totalmem = totalmem * info.mem_unit; #endif /* Return the value, but clamp to SIZE_MAX if necessary. */ #if UINT64_MAX > SIZE_MAX if (totalmem > SIZE_MAX) *memlimit = SIZE_MAX; else *memlimit = (size_t)totalmem; #else *memlimit = totalmem; #endif /* Success! */ return (0); } #endif /* HAVE_SYSINFO */ #ifndef _WIN32 static int memlimit_rlimit(size_t * memlimit) { struct rlimit rl; uint64_t memrlimit; /* Find the least of... */ memrlimit = (uint64_t)(-1); /* ... RLIMIT_AS... */ #ifdef RLIMIT_AS if (getrlimit(RLIMIT_AS, &rl)) return (1); if ((rl.rlim_cur != RLIM_INFINITY) && ((uint64_t)rl.rlim_cur < memrlimit)) memrlimit = (uint64_t)rl.rlim_cur; #endif /* ... RLIMIT_DATA... */ if (getrlimit(RLIMIT_DATA, &rl)) return (1); if ((rl.rlim_cur != RLIM_INFINITY) && ((uint64_t)rl.rlim_cur < memrlimit)) memrlimit = (uint64_t)rl.rlim_cur; /* ... and RLIMIT_RSS. */ #ifdef RLIMIT_RSS if (getrlimit(RLIMIT_RSS, &rl)) return (1); if ((rl.rlim_cur != RLIM_INFINITY) && ((uint64_t)rl.rlim_cur < memrlimit)) memrlimit = (uint64_t)rl.rlim_cur; #endif /* Return the value, but clamp to SIZE_MAX if necessary. */ #if UINT64_MAX > SIZE_MAX if (memrlimit > SIZE_MAX) *memlimit = SIZE_MAX; else *memlimit = (size_t)memrlimit; #else *memlimit = memrlimit; #endif /* Success! */ return (0); } #endif #ifdef _SC_PHYS_PAGES /* Some systems define _SC_PAGESIZE instead of _SC_PAGE_SIZE. */ #ifndef _SC_PAGE_SIZE #define _SC_PAGE_SIZE _SC_PAGESIZE #endif static int memlimit_sysconf(size_t * memlimit) { long pagesize; long physpages; uint64_t totalmem; /* Set errno to 0 in order to distinguish "no limit" from "error". */ errno = 0; /* Read the two limits. */ if (((pagesize = sysconf(_SC_PAGE_SIZE)) == -1) || ((physpages = sysconf(_SC_PHYS_PAGES)) == -1)) { /* * Did an error occur? OS X may return EINVAL due to not * supporting _SC_PHYS_PAGES in spite of defining it. */ if (errno != 0 && errno != EINVAL) return (1); /* If not, there is no limit. */ totalmem = (uint64_t)(-1); } else { /* Compute the limit. */ totalmem = (uint64_t)(pagesize) * (uint64_t)(physpages); } /* Return the value, but clamp to SIZE_MAX if necessary. */ #if UINT64_MAX > SIZE_MAX if (totalmem > SIZE_MAX) *memlimit = SIZE_MAX; else *memlimit = (size_t)totalmem; #else *memlimit = totalmem; #endif /* Success! */ return (0); } #endif #ifdef _WIN32 static int memlimit_windows(size_t * memlimit) { MEMORYSTATUSEX state; state.dwLength = sizeof(state); if(!GlobalMemoryStatusEx (&state)) return (1); *memlimit = state.ullTotalPhys; return (0); } #endif int memtouse(size_t maxmem, double maxmemfrac, size_t * memlimit) { size_t usermem_memlimit, memsize_memlimit; size_t sysinfo_memlimit, rlimit_memlimit; size_t sysconf_memlimit, windows_memlimit; size_t memlimit_min; size_t memavail; /* Get memory limits. */ #ifdef HW_USERMEM if (memlimit_sysctl_hw(&usermem_memlimit, HW_USERMEM)) return (1); #else usermem_memlimit = SIZE_MAX; #endif #ifdef HW_MEMSIZE if (memlimit_sysctl_hw(&memsize_memlimit, HW_MEMSIZE)) return (1); #else memsize_memlimit = SIZE_MAX; #endif #ifdef HAVE_SYSINFO if (memlimit_sysinfo(&sysinfo_memlimit)) return (1); #else sysinfo_memlimit = SIZE_MAX; #endif #ifndef _WIN32 if (memlimit_rlimit(&rlimit_memlimit)) return (1); #else rlimit_memlimit = SIZE_MAX; #endif #ifdef _SC_PHYS_PAGES if (memlimit_sysconf(&sysconf_memlimit)) return (1); #else sysconf_memlimit = SIZE_MAX; #endif #ifdef _WIN32 if (memlimit_windows(&windows_memlimit)) return (1); #else windows_memlimit = SIZE_MAX; #endif #ifdef DEBUG fprintf(stderr, "Memory limits are %zu %zu %zu %zu %zu\n", usermem_memlimit, memsize_memlimit, sysinfo_memlimit, rlimit_memlimit, sysconf_memlimit); #endif /* Find the smallest of them. */ memlimit_min = SIZE_MAX; if (memlimit_min > usermem_memlimit) memlimit_min = usermem_memlimit; if (memlimit_min > memsize_memlimit) memlimit_min = memsize_memlimit; if (memlimit_min > sysinfo_memlimit) memlimit_min = sysinfo_memlimit; if (memlimit_min > rlimit_memlimit) memlimit_min = rlimit_memlimit; if (memlimit_min > sysconf_memlimit) memlimit_min = sysconf_memlimit; if (memlimit_min > windows_memlimit) memlimit_min = windows_memlimit; /* Only use the specified fraction of the available memory. */ if ((maxmemfrac > 0.5) || (maxmemfrac == 0.0)) maxmemfrac = 0.5; memavail = (size_t)(maxmemfrac * memlimit_min); /* Don't use more than the specified maximum. */ if ((maxmem > 0) && (memavail > maxmem)) memavail = maxmem; /* But always allow at least 1 MiB. */ if (memavail < 1048576) memavail = 1048576; #ifdef DEBUG fprintf(stderr, "Allowing up to %zu memory to be used\n", memavail); #endif /* Return limit via the provided pointer. */ *memlimit = memavail; return (0); } py-scrypt-0.8.24/scrypt-1.2.1/lib/util/memlimit.h000066400000000000000000000034431457042124400212600ustar00rootroot00000000000000/*- * Copyright 2009 Colin Percival * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * * This file was originally written by Colin Percival as part of the Tarsnap * online backup system. */ #ifndef _MEMLIMIT_H_ #define _MEMLIMIT_H_ #include /** * memtouse(maxmem, maxmemfrac, memlimit): * Examine the system and return via memlimit the amount of RAM which should * be used -- the specified fraction of the available RAM, but no more than * maxmem, and no less than 1MiB. */ int memtouse(size_t, double, size_t *); #endif /* !_MEMLIMIT_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/000077500000000000000000000000001457042124400200265ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/alg/000077500000000000000000000000001457042124400205715ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/alg/sha256.c000066400000000000000000000341451457042124400217540ustar00rootroot00000000000000#include #include #include #include "insecure_memzero.h" #include "sysendian.h" #include "sha256.h" #define _USE_RESTRICT 0 /* * Encode a length len/4 vector of (uint32_t) into a length len vector of * (uint8_t) in big-endian form. Assumes len is a multiple of 4. */ static void be32enc_vect(uint8_t * dst, const uint32_t * src, size_t len) { size_t i; /* Sanity-check. */ assert(len % 4 == 0); /* Encode vector, one word at a time. */ for (i = 0; i < len / 4; i++) be32enc(dst + i * 4, src[i]); } /* * Decode a big-endian length len vector of (uint8_t) into a length * len/4 vector of (uint32_t). Assumes len is a multiple of 4. */ static void be32dec_vect(uint32_t * dst, const uint8_t * src, size_t len) { size_t i; /* Sanity-check. */ assert(len % 4 == 0); /* Decode vector, one word at a time. */ for (i = 0; i < len / 4; i++) dst[i] = be32dec(src + i * 4); } /* SHA256 round constants. */ static const uint32_t Krnd[64] = { 0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5, 0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5, 0xd807aa98, 0x12835b01, 0x243185be, 0x550c7dc3, 0x72be5d74, 0x80deb1fe, 0x9bdc06a7, 0xc19bf174, 0xe49b69c1, 0xefbe4786, 0x0fc19dc6, 0x240ca1cc, 0x2de92c6f, 0x4a7484aa, 0x5cb0a9dc, 0x76f988da, 0x983e5152, 0xa831c66d, 0xb00327c8, 0xbf597fc7, 0xc6e00bf3, 0xd5a79147, 0x06ca6351, 0x14292967, 0x27b70a85, 0x2e1b2138, 0x4d2c6dfc, 0x53380d13, 0x650a7354, 0x766a0abb, 0x81c2c92e, 0x92722c85, 0xa2bfe8a1, 0xa81a664b, 0xc24b8b70, 0xc76c51a3, 0xd192e819, 0xd6990624, 0xf40e3585, 0x106aa070, 0x19a4c116, 0x1e376c08, 0x2748774c, 0x34b0bcb5, 0x391c0cb3, 0x4ed8aa4a, 0x5b9cca4f, 0x682e6ff3, 0x748f82ee, 0x78a5636f, 0x84c87814, 0x8cc70208, 0x90befffa, 0xa4506ceb, 0xbef9a3f7, 0xc67178f2 }; /* Elementary functions used by SHA256 */ #define Ch(x, y, z) ((x & (y ^ z)) ^ z) #define Maj(x, y, z) ((x & (y | z)) | (y & z)) #define SHR(x, n) (x >> n) #define ROTR(x, n) ((x >> n) | (x << (32 - n))) #define S0(x) (ROTR(x, 2) ^ ROTR(x, 13) ^ ROTR(x, 22)) #define S1(x) (ROTR(x, 6) ^ ROTR(x, 11) ^ ROTR(x, 25)) #define s0(x) (ROTR(x, 7) ^ ROTR(x, 18) ^ SHR(x, 3)) #define s1(x) (ROTR(x, 17) ^ ROTR(x, 19) ^ SHR(x, 10)) /* SHA256 round function */ #define RND(a, b, c, d, e, f, g, h, k) \ h += S1(e) + Ch(e, f, g) + k; \ d += h; \ h += S0(a) + Maj(a, b, c); /* Adjusted round function for rotating state */ #define RNDr(S, W, i, ii) \ RND(S[(64 - i) % 8], S[(65 - i) % 8], \ S[(66 - i) % 8], S[(67 - i) % 8], \ S[(68 - i) % 8], S[(69 - i) % 8], \ S[(70 - i) % 8], S[(71 - i) % 8], \ W[i + ii] + Krnd[i + ii]) /* Message schedule computation */ #define MSCH(W, ii, i) \ W[i + ii + 16] = s1(W[i + ii + 14]) + W[i + ii + 9] + s0(W[i + ii + 1]) + W[i + ii] /* * SHA256 block compression function. The 256-bit state is transformed via * the 512-bit input block to produce a new state. */ #if _USE_RESTRICT static void SHA256_Transform(uint32_t state[static restrict 8], const uint8_t block[static restrict 64], uint32_t W[static restrict 64], uint32_t S[static restrict 8]) #else static void SHA256_Transform(uint32_t state[8], const uint8_t block[64], uint32_t W[64], uint32_t S[8]) #endif { int i; /* 1. Prepare the first part of the message schedule W. */ be32dec_vect(W, block, 64); /* 2. Initialize working variables. */ memcpy(S, state, 32); /* 3. Mix. */ for (i = 0; i < 64; i += 16) { RNDr(S, W, 0, i); RNDr(S, W, 1, i); RNDr(S, W, 2, i); RNDr(S, W, 3, i); RNDr(S, W, 4, i); RNDr(S, W, 5, i); RNDr(S, W, 6, i); RNDr(S, W, 7, i); RNDr(S, W, 8, i); RNDr(S, W, 9, i); RNDr(S, W, 10, i); RNDr(S, W, 11, i); RNDr(S, W, 12, i); RNDr(S, W, 13, i); RNDr(S, W, 14, i); RNDr(S, W, 15, i); if (i == 48) break; MSCH(W, 0, i); MSCH(W, 1, i); MSCH(W, 2, i); MSCH(W, 3, i); MSCH(W, 4, i); MSCH(W, 5, i); MSCH(W, 6, i); MSCH(W, 7, i); MSCH(W, 8, i); MSCH(W, 9, i); MSCH(W, 10, i); MSCH(W, 11, i); MSCH(W, 12, i); MSCH(W, 13, i); MSCH(W, 14, i); MSCH(W, 15, i); } /* 4. Mix local working variables into global state. */ for (i = 0; i < 8; i++) state[i] += S[i]; } static const uint8_t PAD[64] = { 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; /* Add padding and terminating bit-count. */ #if _USE_RESTRICT static void SHA256_Pad(SHA256_CTX * ctx, uint32_t tmp32[static restrict 72]) #else static void SHA256_Pad(SHA256_CTX * ctx, uint32_t tmp32[72]) #endif { size_t r; /* Figure out how many bytes we have buffered. */ r = (ctx->count >> 3) & 0x3f; /* Pad to 56 mod 64, transforming if we finish a block en route. */ if (r < 56) { /* Pad to 56 mod 64. */ memcpy(&ctx->buf[r], PAD, 56 - r); } else { /* Finish the current block and mix. */ memcpy(&ctx->buf[r], PAD, 64 - r); SHA256_Transform(ctx->state, ctx->buf, &tmp32[0], &tmp32[64]); /* The start of the final block is all zeroes. */ memset(&ctx->buf[0], 0, 56); } /* Add the terminating bit-count. */ be64enc(&ctx->buf[56], ctx->count); /* Mix in the final block. */ SHA256_Transform(ctx->state, ctx->buf, &tmp32[0], &tmp32[64]); } /* Magic initialization constants. */ static const uint32_t initial_state[8] = { 0x6A09E667, 0xBB67AE85, 0x3C6EF372, 0xA54FF53A, 0x510E527F, 0x9B05688C, 0x1F83D9AB, 0x5BE0CD19 }; /** * SHA256_Init(ctx): * Initialize the SHA256 context ${ctx}. */ void SHA256_Init(SHA256_CTX * ctx) { /* Zero bits processed so far. */ ctx->count = 0; /* Initialize state. */ memcpy(ctx->state, initial_state, sizeof(initial_state)); } /** * SHA256_Update(ctx, in, len): * Input ${len} bytes from ${in} into the SHA256 context ${ctx}. */ #if _USE_RESTRICT static void _SHA256_Update(SHA256_CTX * ctx, const void * in, size_t len, uint32_t tmp32[static restrict 72]) #else static void _SHA256_Update(SHA256_CTX * ctx, const void * in, size_t len, uint32_t tmp32[72]) #endif { uint32_t r; const uint8_t * src = in; /* Return immediately if we have nothing to do. */ if (len == 0) return; /* Number of bytes left in the buffer from previous updates. */ r = (ctx->count >> 3) & 0x3f; /* Update number of bits. */ ctx->count += (uint64_t)(len) << 3; /* Handle the case where we don't need to perform any transforms. */ if (len < 64 - r) { memcpy(&ctx->buf[r], src, len); return; } /* Finish the current block. */ memcpy(&ctx->buf[r], src, 64 - r); SHA256_Transform(ctx->state, ctx->buf, &tmp32[0], &tmp32[64]); src += 64 - r; len -= 64 - r; /* Perform complete blocks. */ while (len >= 64) { SHA256_Transform(ctx->state, src, &tmp32[0], &tmp32[64]); src += 64; len -= 64; } /* Copy left over data into buffer. */ memcpy(ctx->buf, src, len); } /* Wrapper function for intermediate-values sanitization. */ void SHA256_Update(SHA256_CTX * ctx, const void * in, size_t len) { uint32_t tmp32[72]; /* Call the real function. */ _SHA256_Update(ctx, in, len, tmp32); /* Clean the stack. */ insecure_memzero(tmp32, 288); } /** * SHA256_Final(digest, ctx): * Output the SHA256 hash of the data input to the context ${ctx} into the * buffer ${digest}. */ #if _USE_RESTRICT static void _SHA256_Final(uint8_t digest[32], SHA256_CTX * ctx, uint32_t tmp32[static restrict 72]) #else static void _SHA256_Final(uint8_t digest[32], SHA256_CTX * ctx, uint32_t tmp32[72]) #endif { /* Add padding. */ SHA256_Pad(ctx, tmp32); /* Write the hash. */ be32enc_vect(digest, ctx->state, 32); } /* Wrapper function for intermediate-values sanitization. */ void SHA256_Final(uint8_t digest[32], SHA256_CTX * ctx) { uint32_t tmp32[72]; /* Call the real function. */ _SHA256_Final(digest, ctx, tmp32); /* Clear the context state. */ insecure_memzero(ctx, sizeof(SHA256_CTX)); /* Clean the stack. */ insecure_memzero(tmp32, 288); } /** * SHA256_Buf(in, len, digest): * Compute the SHA256 hash of ${len} bytes from ${in} and write it to ${digest}. */ void SHA256_Buf(const void * in, size_t len, uint8_t digest[32]) { SHA256_CTX ctx; uint32_t tmp32[72]; SHA256_Init(&ctx); _SHA256_Update(&ctx, in, len, tmp32); _SHA256_Final(digest, &ctx, tmp32); /* Clean the stack. */ insecure_memzero(&ctx, sizeof(SHA256_CTX)); insecure_memzero(tmp32, 288); } /** * HMAC_SHA256_Init(ctx, K, Klen): * Initialize the HMAC-SHA256 context ${ctx} with ${Klen} bytes of key from * ${K}. */ #if _USE_RESTRICT static void _HMAC_SHA256_Init(HMAC_SHA256_CTX * ctx, const void * _K, size_t Klen, uint32_t tmp32[static restrict 72], uint8_t pad[static restrict 64], uint8_t khash[static restrict 32]) #else static void _HMAC_SHA256_Init(HMAC_SHA256_CTX * ctx, const void * _K, size_t Klen, uint32_t tmp32[72], uint8_t pad[64], uint8_t khash[32]) #endif { const uint8_t * K = _K; size_t i; /* If Klen > 64, the key is really SHA256(K). */ if (Klen > 64) { SHA256_Init(&ctx->ictx); _SHA256_Update(&ctx->ictx, K, Klen, tmp32); _SHA256_Final(khash, &ctx->ictx, tmp32); K = khash; Klen = 32; } /* Inner SHA256 operation is SHA256(K xor [block of 0x36] || data). */ SHA256_Init(&ctx->ictx); memset(pad, 0x36, 64); for (i = 0; i < Klen; i++) pad[i] ^= K[i]; _SHA256_Update(&ctx->ictx, pad, 64, tmp32); /* Outer SHA256 operation is SHA256(K xor [block of 0x5c] || hash). */ SHA256_Init(&ctx->octx); memset(pad, 0x5c, 64); for (i = 0; i < Klen; i++) pad[i] ^= K[i]; _SHA256_Update(&ctx->octx, pad, 64, tmp32); } /* Wrapper function for intermediate-values sanitization. */ void HMAC_SHA256_Init(HMAC_SHA256_CTX * ctx, const void * _K, size_t Klen) { uint32_t tmp32[72]; uint8_t pad[64]; uint8_t khash[32]; /* Call the real function. */ _HMAC_SHA256_Init(ctx, _K, Klen, tmp32, pad, khash); /* Clean the stack. */ insecure_memzero(tmp32, 288); insecure_memzero(khash, 32); insecure_memzero(pad, 64); } /** * HMAC_SHA256_Update(ctx, in, len): * Input ${len} bytes from ${in} into the HMAC-SHA256 context ${ctx}. */ #if _USE_RESTRICT static void _HMAC_SHA256_Update(HMAC_SHA256_CTX * ctx, const void * in, size_t len, uint32_t tmp32[static restrict 72]) #else static void _HMAC_SHA256_Update(HMAC_SHA256_CTX * ctx, const void * in, size_t len, uint32_t tmp32[72]) #endif { /* Feed data to the inner SHA256 operation. */ _SHA256_Update(&ctx->ictx, in, len, tmp32); } /* Wrapper function for intermediate-values sanitization. */ void HMAC_SHA256_Update(HMAC_SHA256_CTX * ctx, const void * in, size_t len) { uint32_t tmp32[72]; /* Call the real function. */ _HMAC_SHA256_Update(ctx, in, len, tmp32); /* Clean the stack. */ insecure_memzero(tmp32, 288); } /** * HMAC_SHA256_Final(digest, ctx): * Output the HMAC-SHA256 of the data input to the context ${ctx} into the * buffer ${digest}. */ #if _USE_RESTRICT static void _HMAC_SHA256_Final(uint8_t digest[32], HMAC_SHA256_CTX * ctx, uint32_t tmp32[static restrict 72], uint8_t ihash[static restrict 32]) #else static void _HMAC_SHA256_Final(uint8_t digest[32], HMAC_SHA256_CTX * ctx, uint32_t tmp32[72], uint8_t ihash[32]) #endif { /* Finish the inner SHA256 operation. */ _SHA256_Final(ihash, &ctx->ictx, tmp32); /* Feed the inner hash to the outer SHA256 operation. */ _SHA256_Update(&ctx->octx, ihash, 32, tmp32); /* Finish the outer SHA256 operation. */ _SHA256_Final(digest, &ctx->octx, tmp32); } /* Wrapper function for intermediate-values sanitization. */ void HMAC_SHA256_Final(uint8_t digest[32], HMAC_SHA256_CTX * ctx) { uint32_t tmp32[72]; uint8_t ihash[32]; /* Call the real function. */ _HMAC_SHA256_Final(digest, ctx, tmp32, ihash); /* Clean the stack. */ insecure_memzero(tmp32, 288); insecure_memzero(ihash, 32); } /** * HMAC_SHA256_Buf(K, Klen, in, len, digest): * Compute the HMAC-SHA256 of ${len} bytes from ${in} using the key ${K} of * length ${Klen}, and write the result to ${digest}. */ void HMAC_SHA256_Buf(const void * K, size_t Klen, const void * in, size_t len, uint8_t digest[32]) { HMAC_SHA256_CTX ctx; uint32_t tmp32[72]; uint8_t tmp8[96]; _HMAC_SHA256_Init(&ctx, K, Klen, tmp32, &tmp8[0], &tmp8[64]); _HMAC_SHA256_Update(&ctx, in, len, tmp32); _HMAC_SHA256_Final(digest, &ctx, tmp32, &tmp8[0]); /* Clean the stack. */ insecure_memzero(&ctx, sizeof(HMAC_SHA256_CTX)); insecure_memzero(tmp32, 288); insecure_memzero(tmp8, 96); } /** * PBKDF2_SHA256(passwd, passwdlen, salt, saltlen, c, buf, dkLen): * Compute PBKDF2(passwd, salt, c, dkLen) using HMAC-SHA256 as the PRF, and * write the output to buf. The value dkLen must be at most 32 * (2^32 - 1). */ void PBKDF2_SHA256(const uint8_t * passwd, size_t passwdlen, const uint8_t * salt, size_t saltlen, uint64_t c, uint8_t * buf, size_t dkLen) { HMAC_SHA256_CTX Phctx, PShctx, hctx; uint32_t tmp32[72]; uint8_t tmp8[96]; size_t i; uint8_t ivec[4]; uint8_t U[32]; uint8_t T[32]; uint64_t j; int k; size_t clen; /* Sanity-check. */ assert(dkLen <= 32 * (size_t)(UINT32_MAX)); /* Compute HMAC state after processing P. */ _HMAC_SHA256_Init(&Phctx, passwd, passwdlen, tmp32, &tmp8[0], &tmp8[64]); /* Compute HMAC state after processing P and S. */ memcpy(&PShctx, &Phctx, sizeof(HMAC_SHA256_CTX)); _HMAC_SHA256_Update(&PShctx, salt, saltlen, tmp32); /* Iterate through the blocks. */ for (i = 0; i * 32 < dkLen; i++) { /* Generate INT(i + 1). */ be32enc(ivec, (uint32_t)(i + 1)); /* Compute U_1 = PRF(P, S || INT(i)). */ memcpy(&hctx, &PShctx, sizeof(HMAC_SHA256_CTX)); _HMAC_SHA256_Update(&hctx, ivec, 4, tmp32); _HMAC_SHA256_Final(U, &hctx, tmp32, tmp8); /* T_i = U_1 ... */ memcpy(T, U, 32); for (j = 2; j <= c; j++) { /* Compute U_j. */ memcpy(&hctx, &Phctx, sizeof(HMAC_SHA256_CTX)); _HMAC_SHA256_Update(&hctx, U, 32, tmp32); _HMAC_SHA256_Final(U, &hctx, tmp32, tmp8); /* ... xor U_j ... */ for (k = 0; k < 32; k++) T[k] ^= U[k]; } /* Copy as many bytes as necessary into buf. */ clen = dkLen - i * 32; if (clen > 32) clen = 32; memcpy(&buf[i * 32], T, clen); } /* Clean the stack. */ insecure_memzero(&Phctx, sizeof(HMAC_SHA256_CTX)); insecure_memzero(&PShctx, sizeof(HMAC_SHA256_CTX)); insecure_memzero(&hctx, sizeof(HMAC_SHA256_CTX)); insecure_memzero(tmp32, 288); insecure_memzero(tmp8, 96); insecure_memzero(U, 32); insecure_memzero(T, 32); } py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/alg/sha256.h000066400000000000000000000053241457042124400217560ustar00rootroot00000000000000#ifndef _SHA256_H_ #define _SHA256_H_ #include #include /* * Use #defines in order to avoid namespace collisions with anyone else's * SHA256 code (e.g., the code in OpenSSL). */ #define SHA256_Init libcperciva_SHA256_Init #define SHA256_Update libcperciva_SHA256_Update #define SHA256_Final libcperciva_SHA256_Final #define SHA256_Buf libcperciva_SHA256_Buf #define SHA256_CTX libcperciva_SHA256_CTX #define HMAC_SHA256_Init libcperciva_HMAC_SHA256_Init #define HMAC_SHA256_Update libcperciva_HMAC_SHA256_Update #define HMAC_SHA256_Final libcperciva_HMAC_SHA256_Final #define HMAC_SHA256_Buf libcperciva_HMAC_SHA256_Buf #define HMAC_SHA256_CTX libcperciva_HMAC_SHA256_CTX /* Context structure for SHA256 operations. */ typedef struct { uint32_t state[8]; uint64_t count; uint8_t buf[64]; } SHA256_CTX; /** * SHA256_Init(ctx): * Initialize the SHA256 context ${ctx}. */ void SHA256_Init(SHA256_CTX *); /** * SHA256_Update(ctx, in, len): * Input ${len} bytes from ${in} into the SHA256 context ${ctx}. */ void SHA256_Update(SHA256_CTX *, const void *, size_t); /** * SHA256_Final(digest, ctx): * Output the SHA256 hash of the data input to the context ${ctx} into the * buffer ${digest}. */ void SHA256_Final(uint8_t[32], SHA256_CTX *); /** * SHA256_Buf(in, len, digest): * Compute the SHA256 hash of ${len} bytes from ${in} and write it to ${digest}. */ void SHA256_Buf(const void *, size_t, uint8_t[32]); /* Context structure for HMAC-SHA256 operations. */ typedef struct { SHA256_CTX ictx; SHA256_CTX octx; } HMAC_SHA256_CTX; /** * HMAC_SHA256_Init(ctx, K, Klen): * Initialize the HMAC-SHA256 context ${ctx} with ${Klen} bytes of key from * ${K}. */ void HMAC_SHA256_Init(HMAC_SHA256_CTX *, const void *, size_t); /** * HMAC_SHA256_Update(ctx, in, len): * Input ${len} bytes from ${in} into the HMAC-SHA256 context ${ctx}. */ void HMAC_SHA256_Update(HMAC_SHA256_CTX *, const void *, size_t); /** * HMAC_SHA256_Final(digest, ctx): * Output the HMAC-SHA256 of the data input to the context ${ctx} into the * buffer ${digest}. */ void HMAC_SHA256_Final(uint8_t[32], HMAC_SHA256_CTX *); /** * HMAC_SHA256_Buf(K, Klen, in, len, digest): * Compute the HMAC-SHA256 of ${len} bytes from ${in} using the key ${K} of * length ${Klen}, and write the result to ${digest}. */ void HMAC_SHA256_Buf(const void *, size_t, const void *, size_t, uint8_t[32]); /** * PBKDF2_SHA256(passwd, passwdlen, salt, saltlen, c, buf, dkLen): * Compute PBKDF2(passwd, salt, c, dkLen) using HMAC-SHA256 as the PRF, and * write the output to buf. The value dkLen must be at most 32 * (2^32 - 1). */ void PBKDF2_SHA256(const uint8_t *, size_t, const uint8_t *, size_t, uint64_t, uint8_t *, size_t); #endif /* !_SHA256_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/cpusupport/000077500000000000000000000000001457042124400222525ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/cpusupport/cpusupport.h000066400000000000000000000123051457042124400246500ustar00rootroot00000000000000#ifndef _CPUSUPPORT_H_ #define _CPUSUPPORT_H_ /* * To enable support for non-portable CPU features at compile time, one or * more CPUSUPPORT_ARCH_FEATURE macros should be defined. This can be done * directly on the compiler command line via -D CPUSUPPORT_ARCH_FEATURE or * -D CPUSUPPORT_ARCH_FEATURE=1; or a file can be created with the * necessary #define lines and then -D CPUSUPPORT_CONFIG_FILE=cpuconfig.h * (or similar) can be provided to include that file here. */ #ifdef CPUSUPPORT_CONFIG_FILE #include CPUSUPPORT_CONFIG_FILE #endif /** * The CPUSUPPORT_FEATURE macro declares the necessary variables and * functions for detecting CPU feature support at run time. The function * defined in the macro acts to cache the result of the ..._detect function * using the ..._present and ..._init variables. The _detect function and the * _present and _init variables are turn defined by CPUSUPPORT_FEATURE_DECL in * appropriate cpusupport_foo_bar.c file. * * In order to allow CPUSUPPORT_FEATURE to be used for features which do not * have corresponding CPUSUPPORT_FEATURE_DECL blocks in another source file, * we abuse the C preprocessor: If CPUSUPPORT_${enabler} is defined to 1, then * we access _present_1, _init_1, and _detect_1; but if it is not defined, we * access _present_CPUSUPPORT_${enabler} etc., which we define as static, thus * preventing the compiler from emitting a reference to an external symbol. * * In this way, it becomes possible to issue CPUSUPPORT_FEATURE invocations * for nonexistent features without running afoul of the requirement that * "If an identifier declared with external linkage is used... in the entire * program there shall be exactly one external definition" (C99 standard, 6.9 * paragraph 5). In practice, this means that users of the cpusupport code * can omit build and runtime detection files without changing the framework * code. */ #define CPUSUPPORT_FEATURE__(arch_feature, enabler, enabled) \ static int cpusupport_ ## arch_feature ## _present ## _CPUSUPPORT_ ## enabler; \ static int cpusupport_ ## arch_feature ## _init ## _CPUSUPPORT_ ## enabler; \ static inline int cpusupport_ ## arch_feature ## _detect ## _CPUSUPPORT_ ## enabler(void) { return (0); } \ extern int cpusupport_ ## arch_feature ## _present_ ## enabled; \ extern int cpusupport_ ## arch_feature ## _init_ ## enabled; \ int cpusupport_ ## arch_feature ## _detect_ ## enabled(void); \ \ static inline int \ cpusupport_ ## arch_feature(void) \ { \ \ if (cpusupport_ ## arch_feature ## _present_ ## enabled) \ return (1); \ else if (cpusupport_ ## arch_feature ## _init_ ## enabled) \ return (0); \ cpusupport_ ## arch_feature ## _present_ ## enabled = \ cpusupport_ ## arch_feature ## _detect_ ## enabled(); \ cpusupport_ ## arch_feature ## _init_ ## enabled = 1; \ return (cpusupport_ ## arch_feature ## _present_ ## enabled); \ } \ static void (* cpusupport_ ## arch_feature ## _dummyptr)(void); \ static inline void \ cpusupport_ ## arch_feature ## _dummyfunc(void) \ { \ \ (void)cpusupport_ ## arch_feature ## _present ## _CPUSUPPORT_ ## enabler; \ (void)cpusupport_ ## arch_feature ## _init ## _CPUSUPPORT_ ## enabler; \ (void)cpusupport_ ## arch_feature ## _detect ## _CPUSUPPORT_ ## enabler; \ (void)cpusupport_ ## arch_feature ## _present_ ## enabled; \ (void)cpusupport_ ## arch_feature ## _init_ ## enabled; \ (void)cpusupport_ ## arch_feature ## _detect_ ## enabled; \ (void)cpusupport_ ## arch_feature ## _dummyptr; \ } \ static void (* cpusupport_ ## arch_feature ## _dummyptr)(void) = cpusupport_ ## arch_feature ## _dummyfunc; \ struct cpusupport_ ## arch_feature ## _dummy #define CPUSUPPORT_FEATURE_(arch_feature, enabler, enabled) \ CPUSUPPORT_FEATURE__(arch_feature, enabler, enabled) #define CPUSUPPORT_FEATURE(arch, feature, enabler) \ CPUSUPPORT_FEATURE_(arch ## _ ## feature, enabler, CPUSUPPORT_ ## enabler) /* * CPUSUPPORT_FEATURE_DECL(arch, feature): * Macro which defines variables and provides a function declaration for * detecting the presence of "feature" on the "arch" architecture. The * function body following this macro expansion must return nonzero if the * feature is present, or zero if the feature is not present or the detection * fails for any reason. */ #define CPUSUPPORT_FEATURE_DECL(arch, feature) \ int cpusupport_ ## arch ## _ ## feature ## _present_1 = 0; \ int cpusupport_ ## arch ## _ ## feature ## _init_1 = 0; \ int cpusupport_ ## arch ## _ ## feature ## _detect_1(void); \ int \ cpusupport_ ## arch ## _ ## feature ## _detect_1(void) /* * List of features. If a feature here is not enabled by the appropriate * CPUSUPPORT_ARCH_FEATURE macro being defined, it has no effect; but if the * relevant macro may be defined (e.g., by Build/cpusupport.sh successfully * compiling Build/cpusupport-ARCH-FEATURE.c) then the C file containing the * corresponding run-time detection code (cpusupport_arch_feature.c) must be * compiled and linked in. */ CPUSUPPORT_FEATURE(x86, aesni, X86_AESNI); CPUSUPPORT_FEATURE(x86, sse2, X86_SSE2); #endif /* !_CPUSUPPORT_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/000077500000000000000000000000001457042124400213465ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/crypto_aes.c000066400000000000000000000074101457042124400236640ustar00rootroot00000000000000#include #include #include #include #include #include "cpusupport.h" #include "crypto_aes_aesni.h" #include "insecure_memzero.h" #include "warnp.h" #include "crypto_aes.h" /** * This represents either an AES_KEY or a struct crypto_aes_key_aesni; we * know which it is based on whether we're using AESNI code or not. As such, * it's just an opaque pointer; but declaring it as a named structure type * prevents type-mismatch bugs in upstream code. */ struct crypto_aes_key; #ifdef CPUSUPPORT_X86_AESNI /* Test whether OpenSSL and AESNI code produce the same AES ciphertext. */ static int aesnitest(uint8_t ptext[16], uint8_t * key, size_t len) { AES_KEY kexp_openssl; void * kexp_aesni; uint8_t ctext_openssl[16]; uint8_t ctext_aesni[16]; /* Sanity-check. */ assert((len == 16) || (len == 32)); /* Expand the key. */ AES_set_encrypt_key(key, (int)(len * 8), &kexp_openssl); if ((kexp_aesni = crypto_aes_key_expand_aesni(key, len)) == NULL) goto err0; /* Encrypt the block. */ AES_encrypt(ptext, ctext_openssl, &kexp_openssl); crypto_aes_encrypt_block_aesni(ptext, ctext_aesni, kexp_aesni); /* Free the AESNI expanded key. */ crypto_aes_key_free_aesni(kexp_aesni); /* Do the outputs match? */ return (memcmp(ctext_openssl, ctext_aesni, 16)); err0: /* Failure! */ return (-1); } /* Should we use AESNI? */ static int useaesni(void) { static int aesnigood = -1; uint8_t key[32]; uint8_t ptext[16]; size_t i; /* If we haven't decided which code to use yet, decide now. */ while (aesnigood == -1) { /* Default to OpenSSL. */ aesnigood = 0; /* If the CPU doesn't claim to support AESNI, stop here. */ if (!cpusupport_x86_aesni()) break; /* Test cases: key is 0x00010203..., ptext is 0x00112233... */ for (i = 0; i < 16; i++) ptext[i] = (0x11 * i) & 0xff; for (i = 0; i < 32; i++) key[i] = i & 0xff; /* Test that AESNI and OpenSSL produce the same results. */ if (aesnitest(ptext, key, 16) || aesnitest(ptext, key, 32)) { warn0("Disabling AESNI due to failed self-test"); break; } /* AESNI works; use it. */ aesnigood = 1; } return (aesnigood); } #endif /* CPUSUPPORT_X86_AESNI */ /** * crypto_aes_key_expand(key, len): * Expand the ${len}-byte AES key ${key} into a structure which can be passed * to crypto_aes_encrypt_block. The length must be 16 or 32. */ struct crypto_aes_key * crypto_aes_key_expand(const uint8_t * key, size_t len) { AES_KEY * kexp; /* Sanity-check. */ assert((len == 16) || (len == 32)); #ifdef CPUSUPPORT_X86_AESNI /* Use AESNI if we can. */ if (useaesni()) return (crypto_aes_key_expand_aesni(key, len)); #endif /* Allocate structure. */ if ((kexp = malloc(sizeof(AES_KEY))) == NULL) goto err0; /* Expand the key. */ AES_set_encrypt_key(key, (int)(len * 8), kexp); /* Success! */ return ((void *)kexp); err0: /* Failure! */ return (NULL); } /** * crypto_aes_encrypt_block(in, out, key): * Using the expanded AES key ${key}, encrypt the block ${in} and write the * resulting ciphertext to ${out}. */ void crypto_aes_encrypt_block(const uint8_t * in, uint8_t * out, const struct crypto_aes_key * key) { #ifdef CPUSUPPORT_X86_AESNI if (useaesni()) { crypto_aes_encrypt_block_aesni(in, out, (const void *)key); return; } #endif /* Get AES to do the work. */ AES_encrypt(in, out, (const void *)key); } /** * crypto_aes_key_free(key): * Free the expanded AES key ${key}. */ void crypto_aes_key_free(struct crypto_aes_key * key) { #ifdef CPUSUPPORT_X86_AESNI if (useaesni()) { crypto_aes_key_free_aesni((void *)key); return; } #endif /* Behave consistently with free(NULL). */ if (key == NULL) return; /* Attempt to zero the expanded key. */ insecure_memzero(key, sizeof(AES_KEY)); /* Free the key. */ free(key); } py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/crypto_aes.h000066400000000000000000000014451457042124400236730ustar00rootroot00000000000000#ifndef _CRYPTO_AES_H_ #define _CRYPTO_AES_H_ #include #include /* Opaque structure. */ struct crypto_aes_key; /** * crypto_aes_key_expand(key, len): * Expand the ${len}-byte AES key ${key} into a structure which can be passed * to crypto_aes_encrypt_block. The length must be 16 or 32. */ struct crypto_aes_key * crypto_aes_key_expand(const uint8_t *, size_t); /** * crypto_aes_encrypt_block(in, out, key): * Using the expanded AES key ${key}, encrypt the block ${in} and write the * resulting ciphertext to ${out}. */ void crypto_aes_encrypt_block(const uint8_t *, uint8_t *, const struct crypto_aes_key *); /** * crypto_aes_key_free(key): * Free the expanded AES key ${key}. */ void crypto_aes_key_free(struct crypto_aes_key *); #endif /* !_CRYPTO_AES_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/crypto_aes_aesni.c000066400000000000000000000173371457042124400250540ustar00rootroot00000000000000#include "cpusupport.h" #ifdef CPUSUPPORT_X86_AESNI #include #include #include #include "insecure_memzero.h" #include "warnp.h" #include "crypto_aes_aesni.h" /* Expanded-key structure. */ struct crypto_aes_key_aesni { uint8_t rkeys_buf[15 * sizeof(__m128i) + (sizeof(__m128i) - 1)]; __m128i * rkeys; size_t nr; }; /* Compute an AES-128 round key. */ #define MKRKEY128(rkeys, i, rcon) do { \ __m128i _s = rkeys[i - 1]; \ __m128i _t = rkeys[i - 1]; \ _s = _mm_xor_si128(_s, _mm_slli_si128(_s, 4)); \ _s = _mm_xor_si128(_s, _mm_slli_si128(_s, 8)); \ _t = _mm_aeskeygenassist_si128(_t, rcon); \ _t = _mm_shuffle_epi32(_t, 0xff); \ rkeys[i] = _mm_xor_si128(_s, _t); \ } while (0) /** * crypto_aes_key_expand_128_aesni(key, rkeys): * Expand the 128-bit AES key ${key} into the 11 round keys ${rkeys}. This * implementation uses x86 AESNI instructions, and should only be used if * CPUSUPPORT_X86_AESNI is defined and cpusupport_x86_aesni() returns nonzero. */ static void crypto_aes_key_expand_128_aesni(const uint8_t key[16], __m128i rkeys[11]) { /* The first round key is just the key. */ /** * XXX Compiler breakage: * The intrinsic defined by Intel for _mm_loadu_si128 defines it as * taking a (const __m128i *) parameter. This forces us to write a * bug: The cast to (const __m128i *) is invalid since it increases * the alignment requirement of the pointer. Alas, until compilers * get fixed intrinsics, all we can do is code the bug and require * that alignment-requirement-increasing compiler warnings get * disabled. */ rkeys[0] = _mm_loadu_si128((const __m128i *)&key[0]); /* * Each of the remaining round keys are computed from the preceding * round key: rotword+subword+rcon (provided as aeskeygenassist) to * compute the 'temp' value, then xor with 1, 2, 3, or all 4 of the * 32-bit words from the preceding round key. Unfortunately, 'rcon' * is encoded as an immediate value, so we need to write the loop out * ourselves rather than allowing the compiler to expand it. */ MKRKEY128(rkeys, 1, 0x01); MKRKEY128(rkeys, 2, 0x02); MKRKEY128(rkeys, 3, 0x04); MKRKEY128(rkeys, 4, 0x08); MKRKEY128(rkeys, 5, 0x10); MKRKEY128(rkeys, 6, 0x20); MKRKEY128(rkeys, 7, 0x40); MKRKEY128(rkeys, 8, 0x80); MKRKEY128(rkeys, 9, 0x1b); MKRKEY128(rkeys, 10, 0x36); } /* Compute an AES-256 round key. */ #define MKRKEY256(rkeys, i, shuffle, rcon) do { \ __m128i _s = rkeys[i - 2]; \ __m128i _t = rkeys[i - 1]; \ _s = _mm_xor_si128(_s, _mm_slli_si128(_s, 4)); \ _s = _mm_xor_si128(_s, _mm_slli_si128(_s, 8)); \ _t = _mm_aeskeygenassist_si128(_t, rcon); \ _t = _mm_shuffle_epi32(_t, shuffle); \ rkeys[i] = _mm_xor_si128(_s, _t); \ } while (0) /** * crypto_aes_key_expand_256_aesni(key, rkeys): * Expand the 256-bit AES key ${key} into the 15 round keys ${rkeys}. This * implementation uses x86 AESNI instructions, and should only be used if * CPUSUPPORT_X86_AESNI is defined and cpusupport_x86_aesni() returns nonzero. */ static void crypto_aes_key_expand_256_aesni(const uint8_t key[32], __m128i rkeys[15]) { /* The first two round keys are just the key. */ /** * XXX Compiler breakage: * The intrinsic defined by Intel for _mm_loadu_si128 defines it as * taking a (const __m128i *) parameter. This forces us to write a * bug: The cast to (const __m128i *) is invalid since it increases * the alignment requirement of the pointer. Alas, until compilers * get fixed intrinsics, all we can do is code the bug and require * that alignment-requirement-increasing compiler warnings get * disabled. */ rkeys[0] = _mm_loadu_si128((const __m128i *)&key[0]); rkeys[1] = _mm_loadu_si128((const __m128i *)&key[16]); /* * Each of the remaining round keys are computed from the preceding * pair of keys. Even rounds use rotword+subword+rcon, while odd * rounds just use subword; the aeskeygenassist instruction computes * both, and we use 0xff or 0xaa to select the one we need. The rcon * value used is irrelevant for odd rounds since we ignore the value * which it feeds into. Unfortunately, the 'shuffle' and 'rcon' * values are encoded into the instructions as immediates, so we need * to write the loop out ourselves rather than allowing the compiler * to expand it. */ MKRKEY256(rkeys, 2, 0xff, 0x01); MKRKEY256(rkeys, 3, 0xaa, 0x00); MKRKEY256(rkeys, 4, 0xff, 0x02); MKRKEY256(rkeys, 5, 0xaa, 0x00); MKRKEY256(rkeys, 6, 0xff, 0x04); MKRKEY256(rkeys, 7, 0xaa, 0x00); MKRKEY256(rkeys, 8, 0xff, 0x08); MKRKEY256(rkeys, 9, 0xaa, 0x00); MKRKEY256(rkeys, 10, 0xff, 0x10); MKRKEY256(rkeys, 11, 0xaa, 0x00); MKRKEY256(rkeys, 12, 0xff, 0x20); MKRKEY256(rkeys, 13, 0xaa, 0x00); MKRKEY256(rkeys, 14, 0xff, 0x40); } /** * crypto_aes_key_expand_aesni(key, len): * Expand the ${len}-byte AES key ${key} into a structure which can be passed * to crypto_aes_encrypt_block_aesni. The length must be 16 or 32. This * implementation uses x86 AESNI instructions, and should only be used if * CPUSUPPORT_X86_AESNI is defined and cpusupport_x86_aesni() returns nonzero. */ void * crypto_aes_key_expand_aesni(const uint8_t * key, size_t len) { struct crypto_aes_key_aesni * kexp; size_t rkey_offset; /* Allocate structure. */ if ((kexp = malloc(sizeof(struct crypto_aes_key_aesni))) == NULL) goto err0; /* Figure out where to put the round keys. */ rkey_offset = (uintptr_t)(&kexp->rkeys_buf[0]) % sizeof(__m128i); rkey_offset = (sizeof(__m128i) - rkey_offset) % sizeof(__m128i); kexp->rkeys = (void *)&kexp->rkeys_buf[rkey_offset]; /* Compute round keys. */ if (len == 16) { kexp->nr = 10; crypto_aes_key_expand_128_aesni(key, kexp->rkeys); } else if (len == 32) { kexp->nr = 14; crypto_aes_key_expand_256_aesni(key, kexp->rkeys); } else { warn0("Unsupported AES key length: %zu bytes", len); goto err1; } /* Success! */ return (kexp); err1: free(kexp); err0: /* Failure! */ return (NULL); } /** * crypto_aes_encrypt_block_aesni(in, out, key): * Using the expanded AES key ${key}, encrypt the block ${in} and write the * resulting ciphertext to ${out}. This implementation uses x86 AESNI * instructions, and should only be used if CPUSUPPORT_X86_AESNI is defined * and cpusupport_x86_aesni() returns nonzero. */ void crypto_aes_encrypt_block_aesni(const uint8_t * in, uint8_t * out, const void * key) { const struct crypto_aes_key_aesni * _key = key; const __m128i * aes_key = _key->rkeys; __m128i aes_state; size_t nr = _key->nr; aes_state = _mm_loadu_si128((const __m128i *)in); aes_state = _mm_xor_si128(aes_state, aes_key[0]); aes_state = _mm_aesenc_si128(aes_state, aes_key[1]); aes_state = _mm_aesenc_si128(aes_state, aes_key[2]); aes_state = _mm_aesenc_si128(aes_state, aes_key[3]); aes_state = _mm_aesenc_si128(aes_state, aes_key[4]); aes_state = _mm_aesenc_si128(aes_state, aes_key[5]); aes_state = _mm_aesenc_si128(aes_state, aes_key[6]); aes_state = _mm_aesenc_si128(aes_state, aes_key[7]); aes_state = _mm_aesenc_si128(aes_state, aes_key[8]); aes_state = _mm_aesenc_si128(aes_state, aes_key[9]); if (nr > 10) { aes_state = _mm_aesenc_si128(aes_state, aes_key[10]); aes_state = _mm_aesenc_si128(aes_state, aes_key[11]); if (nr > 12) { aes_state = _mm_aesenc_si128(aes_state, aes_key[12]); aes_state = _mm_aesenc_si128(aes_state, aes_key[13]); } } aes_state = _mm_aesenclast_si128(aes_state, aes_key[nr]); _mm_storeu_si128((__m128i *)out, aes_state); } /** * crypto_aes_key_free_aesni(key): * Free the expanded AES key ${key}. */ void crypto_aes_key_free_aesni(void * key) { /* Behave consistently with free(NULL). */ if (key == NULL) return; /* Attempt to zero the expanded key. */ insecure_memzero(key, sizeof(struct crypto_aes_key_aesni)); /* Free the key. */ free(key); } #endif /* CPUSUPPORT_X86_AESNI */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/crypto_aes_aesni.h000066400000000000000000000020701457042124400250450ustar00rootroot00000000000000#ifndef _CRYPTO_AES_AESNI_H_ #define _CRYPTO_AES_AESNI_H_ #include #include /** * crypto_aes_key_expand_aesni(key, len): * Expand the ${len}-byte AES key ${key} into a structure which can be passed * to crypto_aes_encrypt_block_aesni. The length must be 16 or 32. This * implementation uses x86 AESNI instructions, and should only be used if * CPUSUPPORT_X86_AESNI is defined and cpusupport_x86_aesni() returns nonzero. */ void * crypto_aes_key_expand_aesni(const uint8_t *, size_t); /** * crypto_aes_encrypt_block_aesni(in, out, key): * Using the expanded AES key ${key}, encrypt the block ${in} and write the * resulting ciphertext to ${out}. This implementation uses x86 AESNI * instructions, and should only be used if CPUSUPPORT_X86_AESNI is defined * and cpusupport_x86_aesni() returns nonzero. */ void crypto_aes_encrypt_block_aesni(const uint8_t *, uint8_t *, const void *); /** * crypto_aes_key_free_aesni(key): * Free the expanded AES key ${key}. */ void crypto_aes_key_free_aesni(void *); #endif /* !_CRYPTO_AES_AESNI_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/crypto_aesctr.c000066400000000000000000000053741457042124400244040ustar00rootroot00000000000000#include #include #include "crypto_aes.h" #include "insecure_memzero.h" #include "sysendian.h" #include "crypto_aesctr.h" struct crypto_aesctr { const struct crypto_aes_key * key; uint64_t nonce; uint64_t bytectr; uint8_t buf[16]; }; /** * crypto_aesctr_init(key, nonce): * Prepare to encrypt/decrypt data with AES in CTR mode, using the provided * expanded key and nonce. The key provided must remain valid for the * lifetime of the stream. */ struct crypto_aesctr * crypto_aesctr_init(const struct crypto_aes_key * key, uint64_t nonce) { struct crypto_aesctr * stream; /* Allocate memory. */ if ((stream = malloc(sizeof(struct crypto_aesctr))) == NULL) goto err0; /* Initialize values. */ stream->key = key; stream->nonce = nonce; stream->bytectr = 0; /* Success! */ return (stream); err0: /* Failure! */ return (NULL); } /** * crypto_aesctr_stream(stream, inbuf, outbuf, buflen): * Generate the next ${buflen} bytes of the AES-CTR stream and xor them with * bytes from ${inbuf}, writing the result into ${outbuf}. If the buffers * ${inbuf} and ${outbuf} overlap, they must be identical. */ void crypto_aesctr_stream(struct crypto_aesctr * stream, const uint8_t * inbuf, uint8_t * outbuf, size_t buflen) { uint8_t pblk[16]; size_t pos; int bytemod; for (pos = 0; pos < buflen; pos++) { /* How far through the buffer are we? */ bytemod = stream->bytectr % 16; /* Generate a block of cipherstream if needed. */ if (bytemod == 0) { be64enc(pblk, stream->nonce); be64enc(pblk + 8, stream->bytectr / 16); crypto_aes_encrypt_block(pblk, stream->buf, stream->key); } /* Encrypt a byte. */ outbuf[pos] = inbuf[pos] ^ stream->buf[bytemod]; /* Move to the next byte of cipherstream. */ stream->bytectr += 1; } } /** * crypto_aesctr_free(stream): * Free the provided stream object. */ void crypto_aesctr_free(struct crypto_aesctr * stream) { /* Behave consistently with free(NULL). */ if (stream == NULL) return; /* Zero potentially sensitive information. */ insecure_memzero(stream, sizeof(struct crypto_aesctr)); /* Free the stream. */ free(stream); } /** * crypto_aesctr_buf(key, nonce, inbuf, outbuf, buflen): * Equivalent to _init(key, nonce); _stream(inbuf, outbuf, buflen); _free(). */ void crypto_aesctr_buf(const struct crypto_aes_key * key, uint64_t nonce, const uint8_t * inbuf, uint8_t * outbuf, size_t buflen) { struct crypto_aesctr stream_rec; struct crypto_aesctr * stream = &stream_rec; /* Initialize values. */ stream->key = key; stream->nonce = nonce; stream->bytectr = 0; /* Perform the encryption. */ crypto_aesctr_stream(stream, inbuf, outbuf, buflen); /* Zero potentially sensitive information. */ insecure_memzero(stream, sizeof(struct crypto_aesctr)); } py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/crypto_aesctr.h000066400000000000000000000023261457042124400244030ustar00rootroot00000000000000#ifndef _CRYPTO_AESCTR_H_ #define _CRYPTO_AESCTR_H_ #include #include /* Opaque types. */ struct crypto_aes_key; struct crypto_aesctr; /** * crypto_aesctr_init(key, nonce): * Prepare to encrypt/decrypt data with AES in CTR mode, using the provided * expanded key and nonce. The key provided must remain valid for the * lifetime of the stream. */ struct crypto_aesctr * crypto_aesctr_init(const struct crypto_aes_key *, uint64_t); /** * crypto_aesctr_stream(stream, inbuf, outbuf, buflen): * Generate the next ${buflen} bytes of the AES-CTR stream and xor them with * bytes from ${inbuf}, writing the result into ${outbuf}. If the buffers * ${inbuf} and ${outbuf} overlap, they must be identical. */ void crypto_aesctr_stream(struct crypto_aesctr *, const uint8_t *, uint8_t *, size_t); /** * crypto_aesctr_free(stream): * Free the provided stream object. */ void crypto_aesctr_free(struct crypto_aesctr *); /** * crypto_aesctr_buf(key, nonce, inbuf, outbuf, buflen): * Equivalent to _init(key, nonce); _stream(inbuf, outbuf, buflen); _free(). */ void crypto_aesctr_buf(const struct crypto_aes_key *, uint64_t, const uint8_t *, uint8_t *, size_t); #endif /* !_CRYPTO_AESCTR_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/crypto_entropy.c000066400000000000000000000113531457042124400246150ustar00rootroot00000000000000#include #include #include #include "entropy.h" #include "insecure_memzero.h" #include "sha256.h" #include "crypto_entropy.h" /** * This system implements the HMAC_DRBG pseudo-random number generator as * specified in section 10.1.2 of the NIST SP 800-90 standard. In this * implementation, the optional personalization_string and additional_input * specified in the standard are not implemented. */ /* Internal HMAC_DRBG state. */ static struct { uint8_t Key[32]; uint8_t V[32]; uint32_t reseed_counter; } drbg; /* Set to non-zero once the PRNG has been instantiated. */ static int instantiated = 0; /* Could be as high as 2^48 if we wanted... */ #define RESEED_INTERVAL 256 /* Limited to 2^16 by specification. */ #define GENERATE_MAXLEN 65536 static int instantiate(void); static void update(uint8_t *, size_t); static int reseed(void); static void generate(uint8_t *, size_t); /** * instantiate(void): * Initialize the DRBG state. (Section 10.1.2.3) */ static int instantiate(void) { uint8_t seed_material[48]; /* Obtain random seed_material = (entropy_input || nonce). */ if (entropy_read(seed_material, 48)) return (-1); /* Initialize Key, V, and reseed_counter. */ memset(drbg.Key, 0x00, 32); memset(drbg.V, 0x01, 32); drbg.reseed_counter = 1; /* Mix the random seed into the state. */ update(seed_material, 48); /* Clean the stack. */ insecure_memzero(seed_material, 48); /* Success! */ return (0); } /** * update(data, datalen): * Update the DRBG state using the provided data. (Section 10.1.2.2) */ static void update(uint8_t * data, size_t datalen) { HMAC_SHA256_CTX ctx; uint8_t K[32]; uint8_t Vx[33]; /* Load (Key, V) into (K, Vx). */ memcpy(K, drbg.Key, 32); memcpy(Vx, drbg.V, 32); /* K <- HMAC(K, V || 0x00 || data). */ Vx[32] = 0x00; HMAC_SHA256_Init(&ctx, K, 32); HMAC_SHA256_Update(&ctx, Vx, 33); HMAC_SHA256_Update(&ctx, data, datalen); HMAC_SHA256_Final(K, &ctx); /* V <- HMAC(K, V). */ HMAC_SHA256_Buf(K, 32, Vx, 32, Vx); /* If the provided data is non-Null, perform another mixing stage. */ if (datalen != 0) { /* K <- HMAC(K, V || 0x01 || data). */ Vx[32] = 0x01; HMAC_SHA256_Init(&ctx, K, 32); HMAC_SHA256_Update(&ctx, Vx, 33); HMAC_SHA256_Update(&ctx, data, datalen); HMAC_SHA256_Final(K, &ctx); /* V <- HMAC(K, V). */ HMAC_SHA256_Buf(K, 32, Vx, 32, Vx); } /* Copy (K, Vx) back to (Key, V). */ memcpy(drbg.Key, K, 32); memcpy(drbg.V, Vx, 32); /* Clean the stack. */ insecure_memzero(K, 32); insecure_memzero(Vx, 33); } /** * reseed(void): * Reseed the DRBG state (mix in new entropy). (Section 10.1.2.4) */ static int reseed(void) { uint8_t seed_material[32]; /* Obtain random seed_material = entropy_input. */ if (entropy_read(seed_material, 32)) return (-1); /* Mix the random seed into the state. */ update(seed_material, 32); /* Reset the reseed_counter. */ drbg.reseed_counter = 1; /* Clean the stack. */ insecure_memzero(seed_material, 32); /* Success! */ return (0); } /** * generate(buf, buflen): * Fill the provided buffer with random bits, assuming that reseed_counter * is less than RESEED_INTERVAL (the caller is responsible for calling * reseed() as needed) and ${buflen} is less than 2^16 (the caller is * responsible for splitting up larger requests). (Section 10.1.2.5) */ static void generate(uint8_t * buf, size_t buflen) { size_t bufpos; assert(buflen <= GENERATE_MAXLEN); assert(drbg.reseed_counter <= RESEED_INTERVAL); /* Iterate until we've filled the buffer. */ for (bufpos = 0; bufpos < buflen; bufpos += 32) { HMAC_SHA256_Buf(drbg.Key, 32, drbg.V, 32, drbg.V); if (buflen - bufpos >= 32) memcpy(&buf[bufpos], drbg.V, 32); else memcpy(&buf[bufpos], drbg.V, buflen - bufpos); } /* Mix up state. */ update(NULL, 0); /* We're one data-generation step closer to needing a reseed. */ drbg.reseed_counter += 1; } /** * crypto_entropy_read(buf, buflen): * Fill the buffer with unpredictable bits. */ int crypto_entropy_read(uint8_t * buf, size_t buflen) { size_t bytes_to_provide; /* Instantiate if needed. */ if (instantiated == 0) { /* Try to instantiate the PRNG. */ if (instantiate()) return (-1); /* We have instantiated the PRNG. */ instantiated = 1; } /* Loop until we've filled the buffer. */ while (buflen > 0) { /* Do we need to reseed? */ if (drbg.reseed_counter > RESEED_INTERVAL) { if (reseed()) return (-1); } /* How much data are we generating in this step? */ if (buflen > GENERATE_MAXLEN) bytes_to_provide = GENERATE_MAXLEN; else bytes_to_provide = buflen; /* Generate bytes. */ generate(buf, bytes_to_provide); /* We've done part of the buffer. */ buf += bytes_to_provide; buflen -= bytes_to_provide; } /* Success! */ return (0); } py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/crypto/crypto_entropy.h000066400000000000000000000004671457042124400246260ustar00rootroot00000000000000#ifndef _CRYPTO_ENTROPY_H_ #define _CRYPTO_ENTROPY_H_ #include #include /** * crypto_entropy_read(buf, buflen): * Fill the buffer with unpredictable bits. The value ${buflen} must be * less than 2^16. */ int crypto_entropy_read(uint8_t *, size_t); #endif /* !_CRYPTO_ENTROPY_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/util/000077500000000000000000000000001457042124400210035ustar00rootroot00000000000000py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/util/asprintf.c000066400000000000000000000014261457042124400230000ustar00rootroot00000000000000#include #include #include #include "asprintf.h" /** * asprintf(ret, format, ...): * Do asprintf(3) like GNU and BSD do. */ int asprintf(char ** ret, const char * format, ...) { va_list ap; int len; size_t buflen; /* Figure out how long the string needs to be. */ va_start(ap, format); len = vsnprintf(NULL, 0, format, ap); va_end(ap); /* Did we fail? */ if (len < 0) goto err0; buflen = (size_t)(len) + 1; /* Allocate memory. */ if ((*ret = malloc(buflen)) == NULL) goto err0; /* Actually generate the string. */ va_start(ap, format); len = vsnprintf(*ret, buflen, format, ap); va_end(ap); /* Did we fail? */ if (len < 0) goto err1; /* Success! */ return (len); err1: free(*ret); err0: /* Failure! */ return (-1); } py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/util/asprintf.h000066400000000000000000000005051457042124400230020ustar00rootroot00000000000000#ifndef _ASPRINTF_H_ #define _ASPRINTF_H_ /* Avoid namespace collisions with BSD/GNU asprintf. */ #ifdef asprintf #undef asprintf #endif #define asprintf libcperciva_asprintf /** * asprintf(ret, format, ...): * Do asprintf(3) like GNU and BSD do. */ int asprintf(char **, const char *, ...); #endif /* !_ASPRINTF_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/util/entropy.c000066400000000000000000000035421457042124400226530ustar00rootroot00000000000000#include #include #include #include #include #include "warnp.h" #include "entropy.h" #ifdef _WIN32 #include #include #define RtlGenRandom SystemFunction036 BOOLEAN NTAPI RtlGenRandom(PVOID RandomBuffer, ULONG RandomBufferLength); #endif /** * XXX Portability * XXX We obtain random bytes from the operating system by opening * XXX /dev/urandom and reading them from that device; this works on * XXX modern UNIX-like operating systems but not on systems like * XXX win32 where there is no concept of /dev/urandom. */ /** * entropy_read(buf, buflen): * Fill the given buffer with random bytes provided by the operating system. */ int entropy_read(uint8_t * buf, size_t buflen) { int fd; ssize_t lenread; #ifndef _WIN32 /* Sanity-check the buffer size. */ if (buflen > SSIZE_MAX) { warn0("Programmer error: " "Trying to read insane amount of random data: %zu", buflen); goto err0; } /* Open /dev/urandom. */ if ((fd = open("/dev/urandom", O_RDONLY)) == -1) { warnp("open(/dev/urandom)"); goto err0; } /* Read bytes until we have filled the buffer. */ while (buflen > 0) { if ((lenread = read(fd, buf, buflen)) == -1) { warnp("read(/dev/urandom)"); goto err1; } /* The random device should never EOF. */ if (lenread == 0) { warn0("EOF on /dev/urandom?"); goto err1; } /* We've filled a portion of the buffer. */ buf += (size_t)lenread; buflen -= (size_t)lenread; } /* Close the device. */ while (close(fd) == -1) { if (errno != EINTR) { warnp("close(/dev/urandom)"); goto err0; } } /* Success! */ return (0); err1: close(fd); err0: /* Failure! */ return (-1); #else // _WIN32 if(FALSE == RtlGenRandom(buf, buflen)) { return (-1); } else{ buf += buflen; return(0); } #endif // _WIN32 } py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/util/entropy.h000066400000000000000000000004051457042124400226530ustar00rootroot00000000000000#ifndef _ENTROPY_H_ #define _ENTROPY_H_ #include #include /** * entropy_read(buf, buflen): * Fill the given buffer with random bytes provided by the operating system. */ int entropy_read(uint8_t *, size_t); #endif /* !_ENTROPY_H_ */ py-scrypt-0.8.24/scrypt-1.2.1/libcperciva/util/getopt.c000066400000000000000000000200311457042124400224450ustar00rootroot00000000000000#include #include #include #include #include "getopt.h" /* * Standard getopt global variables. optreset starts as non-zero in order to * trigger initialization behaviour. */ const char * optarg = NULL; int optind = 1; int opterr = 1; int optreset = 1; /* * Quasi-internal global variables -- these are used via GETOPT macros. */ const char * getopt_dummy = "(dummy)"; int getopt_initialized = 0; /* * Internal variables. */ static const char * cmdname = NULL; static struct opt { const char * os; size_t olen; int hasarg; } * opts = NULL; static size_t nopts; static size_t opt_missing; static size_t opt_default; static size_t opt_found; static const char * packedopts; static char popt[3]; static int atexit_registered = 0; /* Print a message. */ #define PRINTMSG(...) do { \ if (cmdname != NULL) \ fprintf(stderr, "%s: ", cmdname); \ fprintf(stderr, __VA_ARGS__); \ fprintf(stderr, "\n"); \ } while (0) /* Print an error message and die. */ #define DIE(...) do { \ PRINTMSG(__VA_ARGS__); \ abort(); \ } while (0) /* Print a warning, if warnings are enabled. */ #define WARN(...) do { \ if (opterr == 0) \ break; \ if (opt_missing != opt_default) \ break; \ PRINTMSG(__VA_ARGS__); \ } while (0) /* Free allocated options array. */ static void atexit_handler(void) { free(opts); opts = NULL; } /* Reset internal state. */ static void reset(int argc, char * const argv[]) { const char * p; /* If we have arguments, stash argv[0] for error messages. */ if (argc > 0) { /* Find the basename, without leading directories. */ for (p = cmdname = argv[0]; *p != '\0'; p++) { if (*p == '/') cmdname = p + 1; } } /* Discard any registered command-line options. */ free(opts); opts = NULL; /* Register atexit handler if we haven't done so already. */ if (!atexit_registered) { atexit(atexit_handler); atexit_registered = 1; } /* We will start scanning from the first option. */ optind = 1; /* We're not in the middle of any packed options. */ packedopts = NULL; /* We haven't found any option yet. */ opt_found = (size_t)(-1); /* We're not initialized yet. */ getopt_initialized = 0; /* Finished resetting state. */ optreset = 0; } /* Search for an option string. */ static size_t searchopt(const char * os) { size_t i; /* Scan the array of options. */ for (i = 0; i < nopts; i++) { /* Is there an option in this slot? */ if (opts[i].os == NULL) continue; /* Does this match up to the length of the option string? */ if (strncmp(opts[i].os, os, opts[i].olen)) continue; /* Do we have