### Compile and Install PyCryptodome on Windows Source: https://github.com/legrandin/pycryptodome/blob/master/INSTALL.rst Compile and install PyCryptodome on Windows from source. This involves installing Visual Studio Build Tools, then using pip with the '--no-binary :all:' flag. Finally, run the test suite to verify. ```bash > pip install pycryptodomex --no-binary :all: > pip install pycryptodome-test-vectors > python -m Cryptodome.SelfTest ``` -------------------------------- ### Install PyCryptodome as Drop-in Replacement Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/introduction.md Use this command to install PyCryptodome as a replacement for the old PyCrypto library. Ensure no other crypto libraries are installed to avoid conflicts. ```default pip install pycryptodome ``` -------------------------------- ### Test PyCryptodome Installation (PyCrypto Replacement) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md After installing PyCryptodome as a PyCrypto replacement, run these commands to install test vectors and execute the self-test suite for the 'Crypto' package. ```bash pip install pycryptodome-test-vectors python -m Crypto.SelfTest ``` -------------------------------- ### DSA Key Generation, Signing, and Verification Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/public_key/dsa.md This example demonstrates how to generate a new DSA key pair, save the public key, sign a message, and then verify the signature using the public key. ```APIDOC ## DSA Key Generation, Signing, and Verification Example This example demonstrates how to generate a new DSA key pair, save the public key, sign a message, and then verify the signature using the public key. ```python >>> from Crypto.PublicKey import DSA >>> from Crypto.Signature import DSS >>> from Crypto.Hash import SHA256 >>> >>> # Create a new DSA key >>> key = DSA.generate(2048) >>> f = open("public_key.pem", "w") >>> f.write(key.publickey().export_key()) >>> f.close() >>> >>> # Sign a message >>> message = b"Hello" >>> hash_obj = SHA256.new(message) >>> signer = DSS.new(key, 'fips-186-3') >>> signature = signer.sign(hash_obj) >>> >>> # Load the public key >>> f = open("public_key.pem", "r") >>> hash_obj = SHA256.new(message) >>> pub_key = DSA.import_key(f.read()) >>> verifier = DSS.new(pub_key, 'fips-186-3') >>> >>> # Verify the authenticity of the message >>> try: >>> verifier.verify(hash_obj, signature) >>> print "The message is authentic." >>> except ValueError: >>> print "The message is not authentic." ``` ``` -------------------------------- ### SHA3-384 Hashing Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/sha3_384.md Demonstrates how to create a SHA3-384 hash object, update it with data, and get the hexadecimal digest. ```APIDOC ## SHA3-384 Hashing SHA3-384 belongs to the SHA-3 family of cryptographic hashes, as specified in [FIPS 202](http://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.202.pdf). The hash function produces the 384 bit digest of a message: ```default >>> from Crypto.Hash import SHA3_384 >>> >>> h_obj = SHA3_384.new() >>> h_obj.update(b'Some data') >>> print h_obj.hexdigest() ``` *SHA* stands for Secure Hash Algorithm. ``` -------------------------------- ### Compile PyCryptodome on Windows (from sources) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md Install PyCryptodome from source on Windows using pip with the '--no-binary :all:' flag. Ensure C++ build tools and necessary SDKs are installed first. ```bash > pip install pycryptodomex --no-binary :all: ``` -------------------------------- ### Test PyCryptodome Installation on Windows Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md After compiling PyCryptodome from source on Windows, install test vectors and run the self-test suite. ```bash > pip install pycryptodome-test-vectors > python -m Cryptodome.SelfTest ``` -------------------------------- ### Test PyCryptodome Installation (Independent Library) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md After installing PyCryptodome as an independent library, run these commands to install test vectors and execute the self-test suite for the 'Cryptodome' package. ```bash pip install pycryptodome-test-vectors python -m Cryptodome.SelfTest ``` -------------------------------- ### Install PyCryptodome as Independent Library Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/introduction.md Use this command to install PyCryptodome as a standalone library. This allows PyCrypto and PyCryptodome to coexist without interference. ```default pip install pycryptodomex ``` -------------------------------- ### Compile PyCryptodome on Ubuntu (PyPy) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md Install build tools and PyCryptodome for PyPy on Ubuntu. Replace 'pycryptodomex' with 'pycryptodome' if installing under the 'Crypto' package. ```bash $ sudo apt-get install build-essential pypy-dev $ pip install pycryptodomex $ pip install pycryptodome-test-vectors $ pypy -m Cryptodome.SelfTest ``` -------------------------------- ### Salsa20 Encryption Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/cipher/salsa20.md Example demonstrating how to encrypt plaintext using the Salsa20 cipher. It shows the creation of a cipher object with a key and nonce, followed by encryption. ```APIDOC ## Salsa20 Encryption ### Description Encrypt a piece of data using the Salsa20 stream cipher. ### Method `Salsa20.new(key, nonce).encrypt(plaintext)` ### Parameters * **key** (bytes) - The secret key (16 or 32 bytes). * **nonce** (bytes) - An 8-byte value that must not be reused for the same key. * **plaintext** (bytes/bytearray/memoryview) - The data to encrypt. ### Request Example ```pycon from Crypto.Cipher import Salsa20 plaintext = b'Attack at dawn' secret = b'*Thirty-two byte (256 bits) key*' cipher = Salsa20.new(key=secret) msg = cipher.nonce + cipher.encrypt(plaintext) ``` ### Response * **ciphertext** (bytes) - The encrypted data, prefixed with the nonce. ``` -------------------------------- ### MD5 Hashing Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/md5.md Demonstrates how to create a new MD5 hash object, update it with data, and retrieve the hexadecimal digest. ```APIDOC ## MD5 Hashing Example ### Description This example shows how to use the MD5 module to hash a message. ### Usage ```pycon >>> from Crypto.Hash import MD5 >>> h = MD5.new() >>> h.update(b'Hello') >>> print h.hexdigest() ``` ``` -------------------------------- ### Compile PyCryptodome on Fedora (PyPy) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md Install build tools and PyCryptodome for PyPy on Fedora. Replace 'pycryptodomex' with 'pycryptodome' if installing under the 'Crypto' package. ```bash $ sudo yum install gcc gmp pypy-devel $ pip install pycryptodomex $ pip install pycryptodome-test-vectors $ pypy -m Cryptodome.SelfTest ``` -------------------------------- ### TupleHash128 Hashing Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/tuplehash128.md This example demonstrates how to create a TupleHash128 object, update it with multiple byte strings, and retrieve the hexadecimal digest. ```APIDOC ## TupleHash128 Hashing ### Description This example shows how to generate a TupleHash128 for multiple byte strings. ### Method `Crypto.Hash.TupleHash128.new()` ### Parameters * `digest_bytes` (integer) - Optional. The size of the digest, in bytes. Default is 64. Minimum is 8. * `digest_bits` (integer) - Optional and alternative to `digest_bytes`. The size of the digest, in bits (and in steps of 8). Default is 512. Minimum is 64. * `custom` (bytes) - Optional. A customization bytestring. ### Usage ```python from Crypto.Hash import TupleHash128 hd = TupleHash128.new(digest_bytes=16) hd.update(b'deposit') hd.update(b'100') hd.update(b'joe') print(hd.hexdigest()) ``` ### Example Output ``` 4c095be894c21cfe7076a7d0fe3f70ed ``` ## Multiple Updates ### Description Demonstrates updating the hash object with multiple byte strings in a single call. ### Method `TupleHash.update(*data)` ### Usage ```python from Crypto.Hash import TupleHash128 hd = TupleHash128.new(digest_bytes=16) hd.update(b'deposit', b'100', b'joe') print(hd.hexdigest()) ``` ### Example Output ``` 4c095be894c21cfe7076a7d0fe3f70ed ``` ## Variable Digest Size ### Description Shows how to create a TupleHash128 with a different digest size (e.g., 33 bytes). ### Method `Crypto.Hash.TupleHash128.new(digest_bytes=33)` ### Usage ```python from Crypto.Hash import TupleHash128 hd = TupleHash128.new(digest_bytes=33) hd.update(b'deposit') hd.update(b'100') hd.update(b'joe') print(hd.hexdigest()) ``` ### Example Output ``` 23339e4f61527ade355f11e0496766bf929435eaff1ad20ad9bf9e01fddbe307 ``` ## TupleHash Object Methods ### Description Details on the methods available for a TupleHash object. ### Methods #### `digest()` * **Description:** Returns the **binary** (non-printable) digest of the tuple of byte strings. * **Return type:** byte string #### `hexdigest()` * **Description:** Returns the **printable** digest of the tuple of byte strings. * **Return type:** string #### `update(*data)` * **Description:** Authenticates the next tuple of byte strings. TupleHash guarantees the logical separation between each byte string. * **Parameters:** `data` (bytes/bytearray/memoryview) – One or more items to hash. ``` -------------------------------- ### MD2 Hashing Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/md2.md Demonstrates how to create a new MD2 hash object, update it with data, and retrieve the hexadecimal digest. ```APIDOC ## MD2 Hashing Example ### Description This example shows how to use the MD2 hash algorithm to compute the digest of a message. ### Usage ```python from Crypto.Hash import MD2 h = MD2.new() h.update(b'Hello') print(h.hexdigest()) ``` ### Output ``` [hexadecimal digest of "Hello"] ``` ``` -------------------------------- ### Basic SHA-384 Hashing Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/sha384.md Demonstrates how to create a SHA-384 hash object, update it with data, and retrieve the hexadecimal digest. Ensure the `Crypto.Hash` module is imported. ```python from Crypto.Hash import SHA384 h = SHA384.new() h.update(b'Hello') print(h.hexdigest()) ``` -------------------------------- ### Compile PyCryptodome on Ubuntu (Python 2.x) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md Install build tools and PyCryptodome for Python 2.x on Ubuntu. Replace 'pycryptodomex' with 'pycryptodome' if installing under the 'Crypto' package. ```bash $ sudo apt-get install build-essential python-dev $ pip install pycryptodomex $ pip install pycryptodome-test-vectors $ python -m Cryptodome.SelfTest ``` -------------------------------- ### Compile PyCryptodome on Ubuntu (Python 3.x) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md Install build tools and PyCryptodome for Python 3.x on Ubuntu. Replace 'pycryptodomex' with 'pycryptodome' if installing under the 'Crypto' package. ```bash $ sudo apt-get install build-essential python3-dev $ pip install pycryptodomex $ pip install pycryptodome-test-vectors $ python3 -m Cryptodome.SelfTest ``` -------------------------------- ### Generating a MAC tag Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/poly1305.md Example demonstrating how to create a Poly1305 MAC object, update it with data, and retrieve the MAC tag. ```APIDOC ## Crypto.Hash.Poly1305.new() ### Description Creates a new Poly1305 MAC object. This is the primary function to instantiate the Poly1305 algorithm. ### Parameters * **key** (bytes/bytearray/memoryview) - Required - The 32-byte key for the Poly1305 object. * **cipher** (module from `Crypto.Cipher`) - Required - The cipher algorithm to use for deriving the Poly1305 key pair (r, s). It can only be `Crypto.Cipher.AES` or `Crypto.Cipher.ChaCha20`. * **nonce** (bytes/bytearray/memoryview) - Optional - The non-repeatable value to use for the MAC of this message. It must be 16 bytes long for `AES` and 8 or 12 bytes for `ChaCha20`. If not passed, a random nonce is created and available via the `nonce` attribute. * **data** (bytes/bytearray/memoryview) - Optional - The initial chunk of the message to authenticate. Equivalent to an early call to `update()`. ### Returns A [`Poly1305_MAC`](#Crypto.Hash.Poly1305.Poly1305_MAC) object. ### Example ```default >>> from Crypto.Hash import Poly1305 >>> from Crypto.Cipher import AES >>> >>> secret = b'Thirtytwo very very secret bytes' >>> mac = Poly1305.new(key=secret, cipher=AES) >>> mac.update(b'Hello') >>> print("Nonce: ", mac.nonce.hex()) >>> print("MAC: ", mac.hexdigest()) ``` ### One-liner digest() ```default >>> binary_tag = Poly1305.new(key=secret, cipher=AES, data=b'Hello').digest() ``` ### One-liner hexdigest() ```default >>> hex_tag = Poly1305.new(key=secret, cipher=AES, data=b'Hello').hexdigest() ``` ``` -------------------------------- ### Compile PyCryptodome on Fedora (Python 3.x) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md Install build tools and PyCryptodome for Python 3.x on Fedora. Replace 'pycryptodomex' with 'pycryptodome' if installing under the 'Crypto' package. ```bash $ sudo yum install gcc gmp python3-devel $ pip install pycryptodomex $ pip install pycryptodome-test-vectors $ python3 -m Cryptodome.SelfTest ``` -------------------------------- ### Compile PyCryptodome on Fedora (Python 2.x) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md Install build tools and PyCryptodome for Python 2.x on Fedora. Replace 'pycryptodomex' with 'pycryptodome' if installing under the 'Crypto' package. ```bash $ sudo yum install gcc gmp python-devel $ pip install pycryptodomex $ pip install pycryptodome-test-vectors $ python -m Cryptodome.SelfTest ``` -------------------------------- ### Signing a Message Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/signature/pkcs1_v1_5.md Example of how to use a private RSA key to compute the signature of a message. ```APIDOC ## Signing a Message ### Description This example demonstrates how to sign a message using a private RSA key with the PKCS#1 v1.5 scheme. ### Method `Crypto.Signature.pkcs1_15.new(rsa_key).sign(msg_hash)` ### Parameters #### RSA Key - **rsa_key** (RSA object) - Required - The private RSA key object used for signing. #### Message Hash - **msg_hash** (hash object) - Required - A hash object from `Crypto.Hash` that has digested the message. ### Request Example ```python from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 from Crypto.PublicKey import RSA message = b'To be signed' key = RSA.import_key(open('private_key.der').read()) h = SHA256.new(message) signature = pkcs1_15.new(key).sign(h) ``` ### Response #### Returns - **signature** (byte string) - The computed PKCS#1 v1.5 signature. ``` -------------------------------- ### Create and Hash a Message with MD5 Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/md5.md Instantiate an MD5 hash object and update it with message data. Use hexdigest() to get the printable hash. ```python from Crypto.Hash import MD5: h = MD5.new() h.update(b'Hello') print h.hexdigest() ``` -------------------------------- ### Signing a Message with PKCS#1 PSS Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/signature/pkcs1_pss.md Example demonstrating how a sender can use their private RSA key to create a PKCS#1 PSS signature for a message. ```APIDOC ## Signing a Message with PKCS#1 PSS ### Description This example shows the process of signing a message using a private RSA key with the PKCS#1 PSS scheme. ### Usage ```python from Crypto.Signature import pss from Crypto.Hash import SHA256 from Crypto.PublicKey import RSA message = b'To be signed' key = RSA.import_key(open('privkey.der', 'rb').read()) h = SHA256.new(message) signature = pss.new(key).sign(h) ``` ### Parameters - `key`: An RSA private key object loaded from a file. - `message`: The message to be signed (bytes). - `hash_algorithm`: The hash algorithm to use (e.g., SHA256). ### Returns - `signature`: The generated PKCS#1 PSS signature as bytes. ``` -------------------------------- ### Verifying a Signature Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/signature/pkcs1_v1_5.md Example of how to use a public RSA key to verify the signature of a message. ```APIDOC ## Verifying a Signature ### Description This example demonstrates how to verify a signature using a public RSA key with the PKCS#1 v1.5 scheme. ### Method `Crypto.Signature.pkcs1_15.new(rsa_key).verify(msg_hash, signature)` ### Parameters #### RSA Key - **rsa_key** (RSA object) - Required - The public RSA key object used for verification. #### Message Hash - **msg_hash** (hash object) - Required - A hash object from `Crypto.Hash` that has digested the original message. #### Signature - **signature** (byte string) - Required - The signature to be validated. ### Request Example ```python from Crypto.Signature import pkcs1_15 from Crypto.Hash import SHA256 from Crypto.PublicKey import RSA key = RSA.import_key(open('public_key.der').read()) h = SHA256.new(message) try: pkcs1_15.new(key).verify(h, signature) print("The signature is valid.") except (ValueError, TypeError): print("The signature is not valid.") ``` ### Response #### Raises - **ValueError**: If the signature is not valid. ``` -------------------------------- ### BLAKE2s MAC Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/blake2s.md Initialize a BLAKE2s hash object with a secret key to use it as a Message Authentication Code (MAC). The digest size and key can be specified. ```python from Crypto.Hash import BLAKE2s mac = BLAKE2s.new(digest_bits=128, key=b'secret') mac.update(b'Some data') print mac.hexdigest() ``` -------------------------------- ### Compile and Run Tests on Linux Source: https://github.com/legrandin/pycryptodome/blob/master/src/test/README.txt Use these commands on Linux to compile PyCryptodome and run its tests with SSE optimization enabled. Ensure CMake and make are installed. ```bash cmake -B build -DSSE=1 make -C build -j 8 all test ``` -------------------------------- ### TupleHash256 Usage Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/tuplehash256.md Demonstrates how to create a TupleHash256 object, update it with byte strings, and retrieve the hexadecimal digest. It also shows how to specify the digest size in bytes. ```APIDOC ## TupleHash256 Hashing TupleHash256 is a variable-length hash function for tuples of byte strings, derived from SHA-3, and standardized in [NIST SP 800-185](https://nvlpubs.nist.gov/nistpubs/specialpublications/nist.sp.800-185.pdf). TupleHash256 provides a robust way to hash a sequence of byte strings, while maintaining the semantics of each single string, and with a security strength of 256 bits. ### Crypto.Hash.TupleHash256.new(**kwargs) Create a new TupleHash256 object. * **Parameters:** * **digest_bytes** (*integer*) – Optional. The size of the digest, in bytes. Default is 64. Minimum is 8. * **digest_bits** (*integer*) – Optional and alternative to `digest_bytes`. The size of the digest, in bits (and in steps of 8). Default is 512. Minimum is 64. * **custom** (*bytes*) – Optional. A customization bytestring (`S` in SP 800-185). * **Return:** A `TupleHash` object ### Example Usage ```python >>> from Crypto.Hash import TupleHash256 >>> >>> # Example with default digest size (64 bytes) >>> hd = TupleHash256.new() >>> hd.update(b'deposit') >>> hd.update(b'100') >>> hd.update(b'joe') >>> print(hd.hexdigest()) # Output will be a 128-character hex string (64 bytes) >>> # Example with a 16-byte digest >>> hd = TupleHash256.new(digest_bytes=16) >>> hd.update(b'deposit') >>> hd.update(b'100') >>> hd.update(b'joe') >>> print(hd.hexdigest()) b101225b7e5f1f086fc6d0be01abfa1e >>> # Example submitting multiple byte strings at once >>> hd = TupleHash256.new(digest_bytes=16) # Using TupleHash128 here for demonstration, but TupleHash256 works similarly >>> hd.update(b'deposit', b'100', b'joe') >>> print(hd.hexdigest()) b101225b7e5f1f086fc6d0be01abfa1e >>> # Example with a 33-byte digest >>> hd = TupleHash256.new(digest_bytes=33) >>> hd.update(b'deposit') >>> hd.update(b'100') >>> hd.update(b'joe') >>> print(hd.hexdigest()) 29cbb43b90e19bfebf7ff0acfa651a889f106486dae9f9f42c34a48e1b8a7bfa6f ``` **Note:** The 16-byte digest is not a truncated version of the 33-byte digest; they are cryptographically uncorrelated. ``` -------------------------------- ### Compile and Run Tests on Windows Source: https://github.com/legrandin/pycryptodome/blob/master/src/test/README.txt Execute these commands on Windows to compile PyCryptodome and run its tests using NMake Makefiles. CMake must be installed and configured for NMake. ```bash cmake -B build -G "NMake Makefiles" cd build nmake all test ``` -------------------------------- ### Generate Truncated SHA-512/256 Hash Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/sha512.md This example demonstrates how to generate a SHA-512 hash truncated to 256 bits. The `truncate` parameter must be specified when creating the hash object. ```python >>> from Crypto.Hash import SHA512 >>> >>> h = SHA512.new(truncate="256") >>> h.update(b'Hello') >>> print(h.hexdigest()) 7e75b18b88d2cb8be95b05ec611e54e2460408a2dcf858f945686446c9d07aac ``` -------------------------------- ### Create and Hash Data with BLAKE2b Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/blake2b.md Instantiate a BLAKE2b hash object with a specified digest size and update it with data. Use hexdigest() to get the printable hash. ```python from Crypto.Hash import BLAKE2b h_obj = BLAKE2b.new(digest_bits=512) h_obj.update(b'Some data') print h_obj.hexdigest() ``` -------------------------------- ### Encrypting an ECC Private Key with PKCS#8 Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/io/pkcs8.md Example demonstrating how to encrypt an ECC private key using the PKCS#8.wrap function with specified protection parameters. ```APIDOC ## Crypto.IO.PKCS8.wrap ### Description Wraps a private key into a PKCS#8 container, optionally encrypting it. ### Parameters * **pkey** (bytes) - The private key to wrap, DER encoded. * **oid** (string) - The algorithm identifier of the private key (e.g., "1.2.840.10045.2.1" for unrestricted ECC). * **passphrase** (bytes or string, optional) - The passphrase to use for encryption. * **protection** (string, optional) - Defines the encryption algorithm and key derivation method. Must follow patterns like 'PBKDF2WithHMAC-HASHAndCIPHER' or 'scryptAndCIPHER'. * **prot_params** (dict, optional) - Parameters for the key derivation function, such as iteration_count, salt_size, block_size, and parallelization. ### Request Example ```python from Crypto.PublicKey import ECC from Crypto.IO import PKCS8 key = ECC.generate(curve='p256') pkey = key.export_key(format='DER') passphrase = b'secret santa' encrypted_key = PKCS8.wrap( pkey, "1.2.840.10045.2.1", # unrestricted ECC passphrase=passphrase, protection='PBKDF2WithHMAC-SHA512AndAES256-CBC', prot_params={'iteration_count': 210000} ) ``` ``` -------------------------------- ### Build Project Documentation Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/installation.md Use this command to build the project's HTML documentation from reStructuredText files using Sphinx. The output will be in the 'Doc/_build/html/' directory. ```bash > make -C Doc/ html ``` -------------------------------- ### Generate and Build Product Test Executable Source: https://github.com/legrandin/pycryptodome/blob/master/src/test/CMakeLists.txt Generates 'test_product.c' using a Python script and builds it into an executable, then registers it as a test. ```cmake add_custom_command( OUTPUT test_product.c COMMAND ${PYTHON} ${CMAKE_SOURCE_DIR}/make_tests_product.py > test_product.c DEPENDS make_tests_product.py ) add_executable(test_product test_product.c $) add_test(NAME test_product COMMAND test_product) ``` -------------------------------- ### Initialize and Read from cSHAKE128 Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/cshake128.md Demonstrates how to initialize a cSHAKE128 object with a custom string, update it with data, and read a specific number of bytes from the extendable output. The customization string is crucial for domain separation. ```default >>> from Crypto.Hash import cSHAKE128 >>> >>> shake = cSHAKE128.new(custom=b'Email Signature') >>> shake.update(b'Some data') >>> print(shake.read(26).hex()) ``` -------------------------------- ### ARC4 Cipher Usage Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/cipher/arc4.md Example demonstrating how to use the ARC4 cipher for encryption, including key derivation with a nonce. ```APIDOC ## ARC4 Cipher Usage Example ### Description This example shows how to encrypt a message using the ARC4 cipher. It involves deriving a temporary key from a long-term key and a nonce using HMAC-SHA256, then using this temporary key to initialize the ARC4 cipher. ### Code ```python from Crypto.Cipher import ARC4 from Crypto.Hash import SHA256, HMAC from Crypto.Random import get_random_bytes key = b'Very long and confidential key' nonce = get_random_bytes(16) tempkey = HMAC.new(key, nonce, digestmod=SHA256).digest() cipher = ARC4.new(tempkey) msg = nonce + cipher.encrypt(b'Open the pod bay doors, HAL') ``` ``` -------------------------------- ### Initialize and Hash Message with SHA-1 Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/sha1.md Demonstrates how to create a SHA-1 hash object, update it with message data, and retrieve the hexadecimal digest. This is a basic usage pattern for hashing. ```python >>> from Crypto.Hash import SHA1 >>> >>> h = SHA1.new() >>> h.update(b'Hello') >>> print h.hexdigest() ``` -------------------------------- ### BLAKE2b as a Cryptographic MAC Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/blake2b.md Illustrates how to initialize BLAKE2b with a secret key to use it as a Message Authentication Code (MAC). ```APIDOC ## BLAKE2b as a Cryptographic MAC ### Description This snippet demonstrates how to use BLAKE2b as a keyed MAC by providing a secret key during initialization. ### Method ```python from Crypto.Hash import BLAKE2b mac = BLAKE2b.new(digest_bits=256, key=b'secret') mac.update(b'Some data') print mac.hexdigest() ``` ``` -------------------------------- ### Build and Test Montgomery Executable Source: https://github.com/legrandin/pycryptodome/blob/master/src/test/CMakeLists.txt Builds the 'test_mont' executable and registers it as a test. ```cmake add_executable(test_mont test_mont.c $) add_test(NAME test_mont COMMAND test_mont) ``` -------------------------------- ### Import RSA Private Key Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/public_key/rsa.md Illustrates how to reimport an RSA private key from a file using its password. ```APIDOC >>> pwd = b'secret' >>> with open("myprivatekey.pem", "rb") as f: >>> data = f.read() >>> mykey = RSA.import_key(data, pwd) ``` -------------------------------- ### Salsa20 Decryption Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/cipher/salsa20.md Example demonstrating how to decrypt ciphertext using the Salsa20 cipher. It shows how to extract the nonce and ciphertext, create a cipher object, and then decrypt the data. ```APIDOC ## Salsa20 Decryption ### Description Decrypt a piece of data using the Salsa20 stream cipher. ### Method `Salsa20.new(key, nonce).decrypt(ciphertext)` ### Parameters * **key** (bytes) - The secret key (16 or 32 bytes). * **nonce** (bytes) - The 8-byte nonce used during encryption. * **ciphertext** (bytes/bytearray/memoryview) - The data to decrypt (including the nonce prefix). ### Request Example ```pycon from Crypto.Cipher import Salsa20 secret = b'*Thirty-two byte (256 bits) key*' msg_nonce = msg[:8] # Assuming msg contains nonce + ciphertext ciphertext = msg[8:] cipher = Salsa20.new(key=secret, nonce=msg_nonce) plaintext = cipher.decrypt(ciphertext) ``` ### Response * **plaintext** (bytes) - The decrypted data. ``` -------------------------------- ### RC2 Encryption Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/cipher/arc2.md Demonstrates how to encrypt a message using the ARC2 cipher in CFB mode. The initialization vector is prepended to the ciphertext. Ensure the key is 16 bytes for this example. ```python from Crypto.Cipher import ARC2 key = b'Sixteen byte key' cipher = ARC2.new(key, ARC2.MODE_CFB) msg = cipher.iv + cipher.encrypt(b'Attack at dawn') ``` -------------------------------- ### Blowfish Encryption Example (CBC Mode) Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/cipher/blowfish.md Demonstrates how to encrypt a plaintext message using Blowfish in CBC mode. It includes key generation, cipher initialization with an IV, padding the plaintext to a multiple of the block size, and encrypting the padded message. ```python >>> from Crypto.Cipher import Blowfish >>> from struct import pack >>> >>> bs = Blowfish.block_size >>> key = b'An arbitrarily long key' >>> cipher = Blowfish.new(key, Blowfish.MODE_CBC) >>> plaintext = b'docendo discimus ' >>> plen = bs - len(plaintext) % bs >>> padding = [plen]*plen >>> padding = pack('b'*plen, *padding) >>> msg = cipher.iv + cipher.encrypt(plaintext + padding) ``` -------------------------------- ### ChaCha20-Poly1305 Decryption Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/cipher/chacha20_poly1305.md Decrypts and verifies data encrypted with ChaCha20-Poly1305. This example shows how to initialize the cipher with the same key and nonce used for encryption, update with the associated data, and then decrypt and verify the ciphertext using the provided authentication tag. ```APIDOC ## ChaCha20-Poly1305 Decryption Example ### Description This example demonstrates how to decrypt and verify data that was previously encrypted using ChaCha20-Poly1305. It requires the same secret key and the nonce used during encryption. The associated data must also be provided to correctly authenticate and decrypt the message. ### Method ```python import json from base64 import b64decode from Crypto.Cipher import ChaCha20_Poly1305 # Assume 'key' is the same secret key used for encryption # Assume 'json_input' is the JSON string containing nonce, header, ciphertext, and tag # Example JSON input (replace with actual input) json_input = '{"nonce": "4EE/9uqhoZ3mQXmm", "header": "aGVhZGVy", "ciphertext": "Wmmo4Vzn+eS3tUPv2a8=", "tag": "/FgVbM8qhzssPRY80T0iVA=="}' try: b64 = json.loads(json_input) jk = [ 'nonce', 'header', 'ciphertext', 'tag' ] jv = {k:b64decode(b64[k]) for k in jk} # Recreate the cipher object with the same key and nonce cipher = ChaCha20_Poly1305.new(key=key, nonce=jv['nonce']) # Update with the associated data cipher.update(jv['header']) # Decrypt and verify the ciphertext using the tag plaintext = cipher.decrypt_and_verify(jv['ciphertext'], jv['tag']) print("The message was: " + plaintext.decode()) except (ValueError, KeyError): print("Incorrect decryption") ``` ``` -------------------------------- ### ChaCha20-Poly1305 Encryption Example Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/cipher/chacha20_poly1305.md Encrypts and authenticates data using ChaCha20-Poly1305 with a 12-byte nonce. The example demonstrates how to generate a key, create a cipher object, update with header data, and encrypt the plaintext, returning the ciphertext and authentication tag. ```APIDOC ## ChaCha20-Poly1305 Encryption Example ### Description This example demonstrates how to encrypt and authenticate data using the ChaCha20-Poly1305 cipher with a 12-byte nonce. It shows the process of key generation, cipher initialization, updating with associated data, and finally encrypting the plaintext to obtain ciphertext and an authentication tag. ### Method ```python from Crypto.Cipher import ChaCha20_Poly1305 from Crypto.Random import get_random_bytes import json from base64 import b64encode # Key for encryption (32 bytes) key = get_random_bytes(32) # Create a new ChaCha20-Poly1305 cipher object. # A 12-byte nonce will be automatically generated. cipher = ChaCha20_Poly1305.new(key=key) # Associated data (optional) header = b"header" plaintext = b'Attack at dawn' # Update the cipher with associated data cipher.update(header) # Encrypt the plaintext and get the authentication tag ciphertext, tag = cipher.encrypt_and_digest(plaintext) # Access the generated nonce nonce = cipher.nonce # Prepare output for demonstration (e.g., JSON) jk = [ 'nonce', 'header', 'ciphertext', 'tag' ] jv = [ b64encode(x).decode('utf-8') for x in (nonce, header, ciphertext, tag) ] result = json.dumps(dict(zip(jk, jv))) print(result) ``` ### Output Example ```json {"nonce": "4EE/9uqhoZ3mQXmm", "header": "aGVhZGVy", "ciphertext": "Wmmo4Vzn+eS3tUPv2a8=", "tag": "/FgVbM8qhzssPRY80T0iVA=="} ``` ``` -------------------------------- ### Create and Hash Data with BLAKE2b as MAC Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/blake2b.md Initialize a BLAKE2b hash object with a secret key and digest size to use it as a keyed MAC. Update with data and retrieve the MAC digest. ```python from Crypto.Hash import BLAKE2b mac = BLAKE2b.new(digest_bits=256, key=b'secret') mac.update(b'Some data') print mac.hexdigest() ``` -------------------------------- ### Validating a MAC tag Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/poly1305.md Example demonstrating how to validate a received MAC tag against a message and key. ```APIDOC ## Crypto.Hash.Poly1305.Poly1305_MAC.verify() and hexverify() ### Description Verifies that a given MAC tag (binary or hexadecimal) is valid for the message authenticated so far. ### verify(mac_tag) Verifies a **binary** MAC tag. * **Parameters**: * **mac_tag** (byte string/byte string/memoryview) - The expected MAC of the message. * **Raises**: **ValueError** - If the MAC does not match. ### hexverify(hex_mac_tag) Verifies a **printable** MAC tag. * **Parameters**: * **hex_mac_tag** (string) - The expected MAC of the message, as a hexadecimal string. * **Raises**: **ValueError** - If the MAC does not match. ### Example (hexverify) ```default >>> from Crypto.Hash import Poly1305 >>> from Crypto.Cipher import AES >>> from binascii import unhexlify >>> >>> # Assume msg, mac_tag_hex, and nonce_hex are received >>> secret = b'Thirtytwo very very secret bytes' >>> nonce = unhexlify(nonce_hex) >>> mac = Poly1305.new(key=secret, nonce=nonce, cipher=AES, data=msg) >>> try: >>> mac.hexverify(mac_tag_hex) >>> print("The message is authentic") >>> except ValueError: >>> print("The message or the key is wrong") ``` ### One-liner verify() ```default >>> Poly1305.new(key=secret, cipher=AES, data=b'Hello').verify(binary_tag) ``` ### One-liner hexverify() ```default >>> Poly1305.new(key=secret, cipher=AES, data=b'Hello').hexverify(hex_tag) ``` ``` -------------------------------- ### Import X448 Private Key Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/protocol/dh.md Creates a new X448 private key object from raw bytes as described in RFC7748. ```APIDOC ## Crypto.Protocol.DH.import_x448_private_key(encoded) ### Description Create a new X448 private key object, starting from the key encoded as raw `bytes`, in the format described in RFC7748. ### Parameters #### Path Parameters - **encoded** (bytes) - Required - The X448 private key to import. It must be 56 bytes. ### Returns - **EccKey** - a new ECC key object. ### Raises - **ValueError** - when the given key cannot be parsed. ``` -------------------------------- ### SHA3_512.new() Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/sha3_512.md Creates a new SHA3-512 hash object. This is the primary function to start hashing data. ```APIDOC ## Crypto.Hash.SHA3_512.new(data=None, update_after_digest=False) ### Description Create a fresh SHA3-521 hash object. ### Parameters * **data** (byte string/byte array/memoryview) - The very first chunk of the message to hash. It is equivalent to an early call to [`update()`](../cipher/modern.md#update). * **update_after_digest** (boolean) - Whether [`digest()`](../cipher/modern.md#digest) can be followed by another [`update()`](../cipher/modern.md#update) (default: `False`). ### Return A [`SHA3_512_Hash`](#Crypto.Hash.SHA3_512.SHA3_512_Hash) hash object ``` -------------------------------- ### Create KDF with functools.partial Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/protocol/dh.md Construct a KDF function suitable for key agreement by fixing parameters of an underlying KDF like HKDF using functools.partial. The resulting function must accept a single bytes argument. ```python from Crypto.Protocol.KDF import HKDF from Crypto.Hash import SHA256 import functools kdf = functools.partial(HKDF, key_len=32, salt=b'nonce', hashmod=SHA256, num_keys=2, context=b'Some context about the operation') # Pass kdf to key_agreement() ``` -------------------------------- ### SHA3_256.new() Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/sha3_256.md Creates a new SHA3-256 hash object. This is the primary function to start hashing data. ```APIDOC ## Crypto.Hash.SHA3_256.new() ### Description Create a new SHA3-256 hash object. This function initializes a new hash object that can be used to compute the SHA3-256 digest of a message. ### Parameters * **data** (byte string/byte array/memoryview) - The very first chunk of the message to hash. It is equivalent to an early call to [`update()`](../cipher/modern.md#update). * **update_after_digest** (boolean) - Whether [`digest()`](../cipher/modern.md#digest) can be followed by another [`update()`](../cipher/modern.md#update) (default: `False`). ### Return A [`SHA3_256_Hash`](#Crypto.Hash.SHA3_256.SHA3_256_Hash) hash object. ``` -------------------------------- ### SHA3_224.new() Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/sha3_224.md Creates a new SHA3-224 hash object. This is the primary function to start hashing data. ```APIDOC ## Crypto.Hash.SHA3_224.new(data=None, update_after_digest=False) ### Description Creates a fresh SHA3-224 hash object. This function can optionally take initial data to hash. ### Parameters * **data** (byte string/byte array/memoryview) - The very first chunk of the message to hash. It is equivalent to an early call to `update()`. * **update_after_digest** (boolean) - Whether `digest()` can be followed by another `update()` (default: `False`). ### Return A `SHA3_224_Hash` hash object. ``` -------------------------------- ### RIPEMD160.new() Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/ripemd160.md Creates a new RIPEMD-160 hash object. This is the primary function to start hashing a message. ```APIDOC ### Crypto.Hash.RIPEMD160.new(data=None) Create a new hash object. * **Parameters:** **data** (*byte string/byte array/memoryview*) – Optional. The very first chunk of the message to hash. It is equivalent to an early call to [`RIPEMD160Hash.update()`](#Crypto.Hash.RIPEMD160.RIPEMD160Hash.update). * **Return:** A [`RIPEMD160Hash`](#Crypto.Hash.RIPEMD160.RIPEMD160Hash) hash object ``` -------------------------------- ### Import X448 Public Key Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/protocol/dh.md Creates a new X448 public key object from raw bytes as described in RFC7748. ```APIDOC ## Crypto.Protocol.DH.import_x448_public_key(encoded) ### Description Create a new X448 public key object, starting from the key encoded as raw `bytes`, in the format described in RFC7748. ### Parameters #### Path Parameters - **encoded** (bytes) - Required - The x448 public key to import. It must be 56 bytes. ### Returns - **EccKey** - a new ECC key object. ### Raises - **ValueError** - when the given key cannot be parsed. ``` -------------------------------- ### SHA256.new() Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/sha256.md Creates a new SHA-256 hash object. This is the primary function to start hashing a message. ```APIDOC ## Crypto.Hash.SHA256.new(data=None) Create a new hash object. ### Parameters #### data (byte string/byte array/memoryview) - Optional The very first chunk of the message to hash. It is equivalent to an early call to [`SHA256Hash.update()`](#Crypto.Hash.SHA256.SHA256Hash.update). ### Return A [`SHA256Hash`](#Crypto.Hash.SHA256.SHA256Hash) hash object ``` -------------------------------- ### Crypto.Hash.MD2.new() Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/hash/md2.md Creates a new MD2 hash object. This is the recommended way to start hashing a message. ```APIDOC ## Crypto.Hash.MD2.new(data=None) ### Description Creates a new MD2 hash object. Optionally, it can be initialized with the first chunk of data. ### Parameters * **data** (*bytes/bytearray/memoryview*) - Optional. The initial data to hash. ### Returns A [`MD2Hash`](#Crypto.Hash.MD2.MD2Hash) hash object. ``` -------------------------------- ### Instantiate AES Cipher with CBC Mode Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/cipher/classic.md Demonstrates how to create an AES cipher object configured for CBC mode using a random key. This cipher object can then be used for encryption or decryption. ```python from Crypto.Cipher import AES from Crypto.Random import get_random_bytes key = get_random_bytes(16) cipher = AES.new(key, AES.MODE_CBC) # You can now use use cipher to encrypt or decrypt... ``` -------------------------------- ### Get Public Key Source: https://github.com/legrandin/pycryptodome/blob/master/Doc/src/public_key/ecc.md Retrieves the corresponding ECC public key object from an ECC key object. ```APIDOC ## public_key() A matching ECC public key. ### Returns a new [`EccKey`](#Crypto.PublicKey.ECC.EccKey) object ```