StreamCrypt performs authenticated encryption of streams using Xoofff. It is highly parallel and supports AVX-512. It allows any length of key to be specified down to the granularity of a bit. It can represent the key in a wide range of bases, including a word-based scheme complete with visual cues, to aid in key entry, storage and memorization. It supports padding of input plaintext to nearest power-of-two length for length obfuscation. It supports armoring of enciphered output for systems that are not 8-bit clean. It is written in pure unmanaged C++ using Win32 for window creation and event handling and Direct2D/DirectWrite for custom UI rendering. A cross-platform console version also exists.


In a nutshell, the program splits an input stream into blocks of specifiable size (the default being 8 KiB). Each block is encrypted and authenticated as part of a stateful session, resulting in a sequence of (ciphertext, tag)-tuples being written to the output stream.


More specifically, the program first generates a random nonce N using OS-specific secure random number generator facilities. Then, it compresses the nonce into the state for diversification and authentication. A startup tag T0 is then expanded which is used to authenticate the nonce at decipher time. In other words, if any tampering of nonce N or tag T0 occur, then it is detected before any ciphertext is handled and the session is terminated. Following the tag, enough keystream K1 is expanded to encrypt plaintext P1, both of which are XORed together to produce ciphertext C1. Ciphertext C1 is then compressed into the state and tag T1 is expanded, which authenticates not only C1 but everything compressed thus far (the nonce N). This process is repeated as many times as necessary, until the entire stream has been enciphered. Because each tag authenticates all compressed blocks thus far in the session, the adversary is prevented from being able to undetectably tamper with any blocks in any way imaginable. Because the last ciphertext block is known to be partial, truncation is also detected. There is no practical limit on the size of streams that can be handled thanks to Xoofff's data complexity bound. Semantic security is achieved due to the random nonce: enciphering the same stream repeatedly will result in entirely uncorrelated ciphertexts.

The first plaintext block (P1) is used to store encipherment parameters, such as the block length. By encrypting the parameters, the adversary cannot glean useful information from the enciphered stream. By compressing the parameters into the state, if the adversary tampers with the parameters block in any way, the state becomes corrupt and no subsequent tags will verify. The parameters block also configures the decipherment process so that the user need not remember what parameters were used at encipherment time. In addition, padding is intelligently handled at both encipherment and decipherment time, without any abnormal memory requirements.

The random nonce is 256 bits in length. Using a nonce of this length ensures that it would take on average about 2128 encipherments under a single key for some pair of nonces to collide, which is simply astronomical. Tags are 128 bits in length, which means it would take on average about 2127 attempts by the adversary to successfully forge a ciphertext block. Because forgery attempts are inherently online (i.e., such an attack requires access to a keyed decipher oracle), this attack is expensive. Instead, the adversary would likely try to brute force search for the key, which would take about 2127 attempts on average, assuming a 128-bit key is used. Even if all of the computing power in the world was capable of testing 297 keys per year, it would take more than 1 billion years to find a 128-bit key on average.


StreamCrypt StreamCrypt StreamCrypt StreamCrypt StreamCrypt StreamCrypt StreamCrypt StreamCrypt

A cross-platform console version also exists and has been tested under FreeBSD and Windows. It supports the same features as the GUI version, including AVX-512.


In this example, a ZFS dataset is being piped through the program, producing an enciphered output file.