From: CuleX Date: Sat, 26 Aug 2017 10:09:19 +0000 (+0200) Subject: Add man pages X-Git-Url: https://git.codecow.com/?a=commitdiff_plain;h=04c6b9d31a97ef2995f5c7df0f1dfe54a2f39ca5;p=Monocypher.git Add man pages They've been given a custom section 3monocypher to avoid potential clashes with the system. This also allows having a custom intro page, which would otherwise clash or need a different name. --- diff --git a/man/3monocypher/crypto_aead_lock.3monocypher b/man/3monocypher/crypto_aead_lock.3monocypher new file mode 100644 index 0000000..f66a921 --- /dev/null +++ b/man/3monocypher/crypto_aead_lock.3monocypher @@ -0,0 +1,147 @@ +.Dd August 25, 2017 +.Dt CRYPTO_AEAD_LOCK 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_aead_lock , +.Nm crypto_aead_unlock +.Nd authenticated encryption with additional data +.Sh SYNOPSIS +.In monocypher.h +.Ft void +.Fo crypto_aead_lock +.Fa "uint8_t mac[16]" +.Fa "uint8_t *cipher_text" +.Fa "const uint8_t key[32]" +.Fa "const uint8_t nonce[24]" +.Fa "const uint8_t *ad" +.Fa "size_t ad_size" +.Fa "const uint8_t *plain_text" +.Fa "size_t text_size" +.Fc +.Ft int +.Fo crypto_aead_unlock +.Fa "uint8_t *plain_text" +.Fa "const uint8_t key[32]" +.Fa "const uint8_t nonce[24]" +.Fa "const uint8_t mac[16]" +.Fa "const uint8_t *ad" +.Fa "size_t ad_size" +.Fa "const uint8_t *cipher_text" +.Fa "size_t text_size" +.Fc +.Sh DESCRIPTION +These functions are variants of +.Xr crypto_lock 3monocypher +and +.Xr crypto_unlock 3monocypher , +permitting additional data. +Addiional data is authenticated, but +.Em not +encrypted. +.Pp +.Bf Em +Note: using these functions is discouraged: +if the data you are transmitting is worth authenticating, it is probably +worth encrypting as well. +Do so if you can, using +.Xr crypto_lock 3monocypher and +.Xr crypto_unlock 3monocypher . +.Ef +.Pp +If you must send unencrypted data, remember that you cannot trust +unauthenticated data. +.Em Including the length of the additional data . +If you transmit that length over the wire, you must authenticate it. +(The easiest way to do so is to append that length to the additional +data before you call +.Fn crypto_aead_lock +or +.Fn crypto_aead_unlock ) . +Otherwise, an attacker could provide a false length, effectively moving +the boundary between the additional data and the ciphertext or possibly +causing buffer overflows. +If however the length of the additional data is implicit (fixed size) +or self-contained (such as length appending or null termination), you do +not need to authenticate it explicitly. +.Pp +The +.Fn crypto_aead_lock +function encrypts and authenticates a plaintext and authenticates +additional data. +It can be decrypted by the +.Fn crypto_aead_unlock +function. +Arguments that are already documented in +.Xr crypto_lock 3monocypher +will not be repeated here. +The arguments are: +.Bl -tag -width Ds +.It Fa ad +additional data. +This can be any arbitrary byte sequence. +It will not be encrypted. +.It Fa ad_size +length of the additional data. +.El +.Pp +If +.Fa ad +is +.Dv NULL +and +.Fa ad_size +is zero, these functions behave like +.Xr crypto_lock 3monocypher +and +.Xr crypto_unlock 3monocypher . +This can be useful if your protocol somehow requires you to +send unencrypted data. +.Pp +Unlocking proceeds in two steps: first, we authenticate the ciphertext +and additional data with the provided MAC. +If it has been corrupted, the +.Fn crypto_aead_unlock +function returns immediately, +without decrypting the message. +If the message is genuine, the +.Fn crypto_aead_unlock +function decrypts the ciphertext. +.Em Always check the return value . +.Sh RETURN VALUES +The +.Fn crypto_aead_lock +function returns nothing. +It cannot fail. +The +.Fn crypto_aead_unlock +function returns 0 on success or -1 if the message was corrupted (i.e. +.Fa mac +mismatched the combination of +.Fa key , +.Fa nonce , +.Fa ad +and +.Fa cipher_text ) . +Corruption can happen because of transmission errors, programmer error +(e.g. failed to parse the protocol properly and thus supplied only part +of the expected +.Fa ad +or +.Fa cipher_text ) +or an attacker's interference. +.Sh SEE ALSO +.Xr crypto_key_exchange 3monocypher , +.Xr crypto_lock 3monocypher , +.Xr crypto_unlock 3monocypher , +.Xr intro 3monocypher +.Sh IMPLEMENTATION DETAILS +These functions do not authenticate the length themselves for +simplicity, compatibility, and efficiency reasons: +most of the time, the length of the additional data is either fixed or +self-contained, and thus outside of attacker control. +It also makes them compatible with +.Xr crypto_lock 3monocypher +and +.Xr crypto_unlock 3monocypher +when the size of the additional data is zero, and simplifies the +implementation. diff --git a/man/3monocypher/crypto_argon2i.3monocypher b/man/3monocypher/crypto_argon2i.3monocypher new file mode 100644 index 0000000..998c148 --- /dev/null +++ b/man/3monocypher/crypto_argon2i.3monocypher @@ -0,0 +1,182 @@ +.Dd August 26, 2017 +.Dt CRYPTO_ARGON2I 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_argon2i +.Nd password key derivation +.Sh SYNOPSIS +.In monocypher.h +.Ft void +.Fo crypto_argon2i +.Fa "uint8_t *hash" +.Fa "uint32_t hash_size" +.Fa "void *work_area" +.Fa "uint32_t nb_blocks" +.Fa "uint32_t nb_iterations" +.Fa "const uint8_t *password" +.Fa "const uint32_t password_size" +.Fa "const uint8_t *salt" +.Fa "const uint32_t salt_size" +.Fa "const uint8_t *key" +.Fa "const uint32_t key_size" +.Fa "const uint8_t *ad" +.Fa "const uint32_t ad_size" +.Fc +.Sh DESCRIPTION +Storing passwords in plaintext is a serious security liability. +Storing hashed and salted passwords is better, but still very dangerous: +passwords simply do not have enough entropy to prevent a dedicated +attacker from guessing them by sheer brute force. +.Pp +One way to prevent such attacks is to make sure hashing a password +takes too much resources for a brute force search to be effective. +Moreover, we would like the attacker to spend as much resources for each +attempt as we do, even if they have access to dedicated hardware. +.Pp +Argon2i is a resource intensive password key derivation scheme +optimised for the typical x86-like processor. +It runs in constant time with respect to the contents of the password. +.Pp +Typical applications are password checking (for online services), and +key derivation (for encryption). +You can use this, for instance, to protect your private keys: +Encrypt the private keys using a key derived from a strong passphrase. +.Pp +The version currently provided by Monocypher has no threading support, +so the degree of parallelism is currently limited to 1. +This is considered good enough for most purposes anyway. +.Pp +The arguments are: +.Bl -tag -width Ds +.It Fa hash +the output hash. +The length of the output hash must be at least 4. +A length of 32 is recommended. +.It Fa hash_size +the length of the output +.Fa hash . +.It Fa work_area +The address of a work area for the algorithm. +It must be big enough to hold +.Fa nb_blocks +blocks and suitably aligned for 64-bit integers. +A block is 1024 bytes in length. +.Xr malloc 3 +should yield a suitable chunk of memory. +.It Fa nb_blocks +the number of blocks for the work area. +It must be at least 8. +A value of 100000 (one hundred megabytes) is recommended. +If the computation takes too long, reduce this number. +If the computation does not take long enough, increase this number. +If the computation still does not take long enough, increase +.Fa nb_iterations . +.It Fa nb_iterations +the number of iterations. +It must be at least 1. +A value of 3 is recommended. +.It Fa password +the password to hash. +.It Fa password_size +the length of +.Fa password . +.It Fa salt +a password salt. +This is a random value generated separately for each password to be +hashed. +It must be at least 8 bytes long. +A length of 16 is recommended. +.It Fa salt_size +the length of +.Fa salt . +.It Fa key +a key to use in the hash. +This parameter can be +.Dv NULL +if +.Fa key_size +is zero. +You generally do not need this parameter, but it does have some use: +The key is supposed to be unknown to the attacker. +In the context of password derivation, it would stay unknown +.Em even if an attacker steals your password database. +This may be possible if that key is stored separately from your password +database (like on a separate server, and never written on the main +server's disks). +Note: to change the key, you have to re-hash the user's password, +which is only possible upon user login. +.It Fa key_size +the length of the key. +This is normally zero, unless you use the +.Fa key +parameter. +.It Fa ad +additional data. +This is additional data that goes into the hash, similar to the +authenticated encryption with authenticated data (AEAD) construction in +.Xr crypto_aead_lock 3monocypher . +This most likely has no practical application but is exposed for the +sake of completeness. +This parameter may be +.Dv NULL +if +.Fa ad_size +is zero. +.It Fa ad_size +the length of +.Fa ad . +.El +.Pp +Use +.Xr crypto_memcmp 3monocypher +to compare password hashes to prevent timing attacks, which are feasible +against the weakest passwords. +.Pp +The hardness of the computation can be chosen thus: +.Bl -bullet +.It +Decide how long the computation should take. +For user authentication, this is typically somewhere between half a +second (convenient) and several seconds (paranoid). +You may likely have to do some benchmarking which parameters take how +long. +.It +Try to hash a password with 3 iterations and 100000 blocks (one hundred +megabytes) to establish a baseline. +See above for adjusting +.Fa nb_blocks +and +.Fa nb_iterations . +.El +.Sh RETURN VALUES +This function returns nothing. +.Sh EXAMPLES +This example shows how to hash a password with the recommended baseline +parameters: +.Bd -literal -offset indent +uint8_t hash[32], salt[16]; +const uint32_t nb_blocks = 100000; +const uint32_t nb_iterations = 3; +void *work_area = malloc(nb_blocks * 1024); +const char *password = "TooManySecrets"; + +if (work_area == NULL) { + /* handle malloc() failure */ +} + +/* ...randomly generate salt here... */ + +crypto_argon2i(hash, sizeof(hash), work_area, nb_blocks, nb_iterations, + salt, sizeof(salt), NULL, 0, NULL, 0); +.Ed +.Sh SEE ALSO +.Xr crypto_lock 3monocypher , +.Xr crypto_memcmp 3monocypher , +.Xr intro 3monocypher +.Sh CAVEATS +Any deviation from the specified input and output length ranges results +in +.Sy undefined behavior . +Make sure your inputs are correct. +.Sh IMPLEMENTATION DETAILS +This function implements Argon2i. diff --git a/man/3monocypher/crypto_blake2b.3monocypher b/man/3monocypher/crypto_blake2b.3monocypher new file mode 100644 index 0000000..3adf095 --- /dev/null +++ b/man/3monocypher/crypto_blake2b.3monocypher @@ -0,0 +1,146 @@ +.Dd August 26, 2017 +.Dt CRYPTO_BLAKE2B 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_blake2b , +.Nm crypto_blake2b_general , +.Nm crypto_blake2b_general_init , +.Nm crypto_blake2b_init , +.Nm crypto_blake2b_update , +.Nm crypto_blake2b_final +.Nd cryptographic hashing +.Sh SYNOPSIS +.In monocypher.h +.Ft void +.Fo crypto_blake2b +.Fa "uint8_t hash[64]" +.Fa "uint8_t *message" +.Fa "size_t message_size" +.Fc +.Ft void +.Fo crypto_blake2b_general +.Fa "uint8_t *hash" +.Fa "size_t hash_size" +.Fa "uint8_t *key" +.Fa "size_t key_size" +.Fa "uint8_t *message" +.Fa "size_t message_size" +.Fc +.Ft void +.Fo crypto_blake2b_init +.Fa "crypto_blake2b_ctx *ctx" +.Fc +.Ft void +.Fo crypto_blake2b_general_init +.Fa "crypto_blake2b_ctx *ctx" +.Fa "size_t hash_size" +.Fa "uint8_t *key" +.Fa "size_t key_size" +.Fc +.Ft void +.Fo crypto_blake2b_update +.Fa "crypto_blake2b_ctx *ctx" +.Fa "const uint8_t *message" +.Fa "size_t message_size" +.Fc +.Ft void +.Fo crypto_blake2b_final +.Fa "crypto_blake2b_ctx *ctx" +.Fa "uint8_t *hash" +.Fc +.Sh DESCRIPTION +Blake2b is a fast cryptographically secure hash, based on the ideas of +Chacha20. +It is faster than md5, yet just as secure as SHA-3. +.Pp +Blake2b is immune to length extension attacks, and as such does not +require any specific precautions, such as using the HMAC algorithm. +It can authenticate messages with a naive approach. +.Pp +The arguments are: +.Bl -tag -width Ds +.It Fa hash +the output hash. +Must have at least +.Fa hash_size +free bytes. +.It Fa hash_size +the length of the output hash. +Must be between 1 and 64. +.It Fa key +some secret key. +May be +.Dv NULL +if +.Fa key_size +is 0. +.It Fa key_size +length of the +.Fa key . +Must be between 0 and 64. +.It Fa message +the message to hash. +.It Fa message_size +the length of the message. +.El +.Ss Direct interface +The direct interface sports 2 functions: +.Fn crypto_blake2b +and +.Fn crypto_blake2b_general . +The +.Fn crypto_blake2b +is provided for convenience. +It uses a 64 bytes hash and no key (this is a good default). +.Pp +If you use the +.Fn crypto_blake2b_general +function, you can specify the size of the hash (sizes below 32 bytes +are discouraged), and use a secret key to make the hash unpredictable +\(en useful for message authentication codes. +.Ss Incremental interface +Incremental interfaces are useful to handle streams of data or large +files without using too much memory. +This interface uses 3 steps: +.Bl -bullet +.It +initialisation, where we set up a context with the various hashing +parameters; +.It +update, where we hash the message chunk by chunk, and keep the +intermediary result in the context; +.It +and finalisation, where we produce the final hash. +.El +The invariants of the parameters are the same as for +.Fn crypto_blake2b_general . +.Fn crypto_blake2b_init +is a convenience initialisation function that +specifies a 64-byte hash and no key. +This is a good default. +.Sh RETURN VALUES +These functions return nothing. +.Sh EXAMPLES +This example shows how to hash the concatenation of 3 chunks using the +incremental interface: +.Bd -literal -offset indent +uint8_t hash[64]; +crypto_blake2b_ctx ctx; + +crypto_blake2b_init (&ctx); +crypto_blake2b_update(&ctx, chunk1, chunk1_size); +crypto_blake2b_update(&ctx, chunk2, chunk2_size); +crypto_blake2b_update(&ctx, chunk3, chunk3_size); +crypto_blake2b_final (&ctx, hash); +.Ed +.Sh SEE ALSO +.Xr crypto_key_exchange 3monocypher , +.Xr crypto_lock 3monocypher , +.Xr intro 3monocypher +.Sh CAVEATS +Any deviation from the specified input and output length ranges results +in +.Sy undefined behavior . +Make sure your inputs are correct. +.Sh IMPLEMENTATION DETAILS +These functions implement Blake2b. diff --git a/man/3monocypher/crypto_chacha20_H.3monocypher b/man/3monocypher/crypto_chacha20_H.3monocypher new file mode 100644 index 0000000..e20a861 --- /dev/null +++ b/man/3monocypher/crypto_chacha20_H.3monocypher @@ -0,0 +1,48 @@ +.Dd August 26, 2017 +.Dt CRYPTO_CHACHA20_H 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_chacha20_H +.Nd HChacha20 special-purpose hashing +.Sh SYNOPSIS +.In monocypher.h +.Ft void +.Fo crypto_chacha20_H +.Fa "uint8_t out[32]" +.Fa "const uint8_t key[32]" +.Fa "const uint8_t in[16]" +.Fc +.Sh DESCRIPTION +The +.Fn crypto_chacha20_H +function provides a not-so-cryptographic hash. +It may be used for some specific purposes, such as X25519 key +derivation, or XChacha20 initialisation. +If in doubt, do not use directly. +Use +.Xr crypto_blake2b 3monocypher +instead. +.Pp +The output +.Fa out +is a cryptographically secure random number +.Em if +there is enough entropy in in the input +.Fa key . +X25519 shared secrets have enough entropy. +The input +.Fa in +fills the space reserved for the +nonce and counter. +It does not have to be random. +.Sh RETURN VALUES +This function returns nothing. +It cannot fail. +.Sh SEE ALSO +.Xr crypto_chacha20_encrypt 3monocypher , +.Xr crypto_key_exchange 3monocypher , +.Xr intro 3monocypher +.Sh CAVEATS +.Sy This is not a general-purpose cryptographic hash function . +.Sh IMPLEMENTATION DETAILS +This function implements HChacha20. diff --git a/man/3monocypher/crypto_chacha20_encrypt.3monocypher b/man/3monocypher/crypto_chacha20_encrypt.3monocypher new file mode 100644 index 0000000..f22cb53 --- /dev/null +++ b/man/3monocypher/crypto_chacha20_encrypt.3monocypher @@ -0,0 +1,159 @@ +.Dd August 26, 2017 +.Dt CRYPTO_CHACHA20_ENCRYPT 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_chacha20_encrypt , +.Nm crypto_chacha20_init , +.Nm crypto_chacha20_x_init , +.Nm crypto_chacha20_stream , +.Nm crypto_chacha20_set_ctr +.Nd Chacha20 encryption +.Sh SYNOPSIS +.In monocypher.h +.Ft void +.Fo crypto_chacha20_encrypt +.Fa "crypto_chacha_ctx *ctx" +.Fa "uint8_t *cipher_text" +.Fa "const uint8_t *plain_text" +.Fa "size_t text_size" +.Fc +.Ft void +.Fo crypto_chacha20_init +.Fa "crypto_chacha_ctx *ctx" +.Fa "const uint8_t key[32]" +.Fa "const uint8_t nonce[8]" +.Fc +.Ft void +.Fo crypto_chacha20_x_init +.Fa "crypto_chacha_ctx *ctx" +.Fa "const uint8_t key[32]" +.Fa "const uint8_t nonce[24]" +.Fc +.Ft void +.Fo crypto_chacha20_encrypt +.Fa "crypto_chacha_ctx *ctx" +.Fa "uint8_t *cipher_text" +.Fa "const uint8_t *plain_text" +.Fa "size_t text_size" +.Fc +.Ft void +.Fo crypto_chacha20_stream +.Fa "crypto_chacha_ctx *ctx" +.Fa "uint8_t *stream" +.Fa "size_t size" +.Fc +.Ft void +.Fo crypto_chacha20_set_ctr +.Fa "crypto_chacha_ctx *ctx" +.Fa "uint64_t ctr" +.Fc +.Sh DESCRIPTION +These functions provides an incremental interface for Chacha20, with an +initialisation, and as many encryption steps as you want. +.Pp +To use these functions, you must first initialize a +.Vt crypto_chacha_ctx +using +.Fn crypto_chacha20_init +or +.Fn crypto_chacha20_x_init . +When using the former, +.Em do not select the nonce at random, use a counter instead . +When using the latter, select the nonce at random. +See +.Xr intro 3monocypher +about generating random numbers (use the operating system's random +number generator). +The initialization routine +.Fn crypto_chacha20_x_init +is a tiny bit slower \(en though that is irrelevant in practice. +.Pp +The +.Fn crypto_chacha20_encrypt +function encrypts the +.Fa plain_text +by XORing it with a pseudo-random stream of +numbers, seeded by the provided +.Vt crypto_chacha_ctx . +Decryption is the same operation as encryption. +Once the context is initialised, encryption can safely be chained thus: +.Bd -literal -offset indent + crypto_encrypt_chacha20(ctx, plain_0, cipher_0, length_0); + crypto_encrypt_chacha20(ctx, plain_1, cipher_1, length_1); + crypto_encrypt_chacha20(ctx, plain_2, cipher_2, length_2); +.Ed +The input +.Fa plain_text +and the output +.Fa cipher_text +may point to the same location, for in-place encryption. +The input +.Fa plain_text +is allowed to be +.Dv NULL +(0), in which case it will be interpreted as an all zero input. +The cipher_text will then contain the raw Chacha20 stream. +.Pp +The +.Fn crypto_chacha20_stream +function is provided for convenience. +It is the same as +.Fn crypto_chacha20_encrypt +with +.Fa plain_text +being +.Dv NULL . +This is useful as a user space random number generator. +Do not use this as a cryptographic random number generator. +Still, this function can be used outside of a security context: +deterministic procedural generation comes to mind. +.Pp +The +.Fn crypto_chacha20_set_ctr +function resets the internal counter of the Chacha context to the value +specified in +.Fa ctr . +Resuming the encryption will use the stream at the +block +.Fa ctr +(which is the byte +.Ql ctr \(mu 64 ) . +This can be used to encrypt (or decrypt) part of a long message, or to +implement some AEAD constructions such as the one described in RFC 7539 +(not implemented in Monocypher because of its complexity and +limitations). +.Sh RETURN VALUES +These functions return nothing. +They cannot fail. +.Sh SEE ALSO +.Xr crypto_lock 3monocypher , +.Xr intro 3monocypher +.Sh CAVEATS +.Sy Encryption alone is not sufficient for security . +Using Chacha20 directly is therefore discouraged. +Use authenticated encryption instead; see +.Xr crypto_lock 3monocypher . +.Pp +When using +.Fn crypto_chacha20_init , +.Sy do not select the nonce at random . +Unlike the authenticated encryption we've seen at the top, this nonce is +only 64 bits in length. +This is too small for random nonces: you might reuse one by sheer +misfortune. +Use a counter instead. +If there are multiple parties sending out messages, you can give them +all an initial nonce of 0, 1 .. n-1 respectively, and have them +increment their nonce by n and make sure the counters never wrap +around. +.Pp +Do not reuse a nonce for the same key. +You would expose the XOR of subsequent encrypted messages, and +destroy confidentiality. +.Pp +Do not use these functions as cryptographic random number generator. +Always use the operating system's random number generator for +cryptographic purposes, see +.Xr intro 3monocypher . +.Sh IMPLEMENTATION DETAILS +These functions implement Chacha20 and XChacha20. diff --git a/man/3monocypher/crypto_key_exchange.3monocypher b/man/3monocypher/crypto_key_exchange.3monocypher new file mode 100644 index 0000000..b10de9e --- /dev/null +++ b/man/3monocypher/crypto_key_exchange.3monocypher @@ -0,0 +1,143 @@ +.Dd August 26, 2017 +.Dt CRYPTO_KEY_EXCHANGE 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_key_exchange , +.Nm crypto_x25519_public_key , +.Nm crypto_x25519 +.Nd Elliptic Curve Diffie-Hellman key exchange +.Sh SYNOPSIS +.In monocypher.h +.Ft int +.Fo crypto_key_exchange +.Fa "uint8_t shared_key[32]" +.Fa "const uint8_t your_secret_key[32]" +.Fa "const uint8_t their_public_key[32]" +.Fc +.Ft void +.Fo crypto_x25519_public_key +.Fa "uint8_t public_key[32]" +.Fa "const uint8_t secret_key[32]" +.Fc +.Ft int +.Fo crypto_x25519 +.Fa "uint8_t shared_secret[32]" +.Fa "const uint8_t your_secret_key[32]" +.Fa "const uint8_t their_public_key[32]" +.Fc +.Sh DESCRIPTION +Key exchange works thus: Alice and Bob each have a key pair (a secret +key and a public key). +They know each other's public key, but they keep their own secret key +secret. +If Eve (an attacker) learns Alice's secret key, she could compute the +shared secret between Alice and anyone else (including Bob), allowing +her to read and forge correspondence. +Protect your secret key. +.Pp +Furthermore, Alice and Bob must know each other's public keys +.Em beforehand . +If they do not, and try to communicate those keys over an insecure +channel, Eve might intercept their communications (Man-in-the-middle +attack) and provide false public keys. +There are various ways to learn of each other's public keys (crypto +parties, certificate authorities, web of trust…), each with their own +advantages and drawbacks. +.Pp +The +.Fn crypto_key_exchange +function computes a shared key with your secret key and their public +key, suitable for the +.Xr crypto_lock 3monocypher , +.Xr crypto_unlock 3monocypher , +.Xr crypto_aead_lock 3monocypher , +and +.Xr crypto_aead_unlock 3monocypher +functions. +It performs an X25519 key exchange, then hashes the shared secret (with +HChacha20) to get a suitably random-looking shared key. +.Pp +Keep in mind that if either of your long term secret keys leaks, it +may compromise +.Em all past messages ! +If you want forward secrecy, you will need to exchange temporary public +keys, then compute your shared secret with +.Em them . +.Pp +The +.Fn crypto_x25519_public_key +function eterministically computes the public key from +.Fa secret_key . +Make sure the secret key is random. +See +.Xr intro 3monocypher +for advice about generating random bytes (basically, use your operating +system's random number generator). +.Pp +The +.Fn crypto_x25519 +function allows doing a raw X25519 key exchange. +This is a low-level function. +Unless you +.Em really +know what you are doing, you should use +.Fn crypto_key_exchange +instead. +This function computes a shared secret with your secret key +.Fa your_secret_key +and the other party's public key +.Fa their_public_key. +.Sy Warning: the shared secret is not cryptographically random. +Do not use it directly as a session key. +You need to hash it first. +Any cryptographically secure hash will do. +The +.Fn crypto_key_exchange +function uses HChacha20 via +.Xr crypto_chacha20_H 3monocypher , +which is not a general purpose hash, but here it works just fine. +.Sh RETURN VALUES +The +.Fn crypto_key_exchange +and +.Fn crypto_x25519 +functions return zero on success. +The return value serves as a security check: there are a couple evil +public keys out there, that force the shared key to a known constant +(the HCHacha20 of zero in the case of +.Fn crypto_key_exchange +or all-zero in the case of +.Fn crypto_x25519 ) . +This never happens with legitimate public keys, but if the ones you +process aren't known to be trustworthy, check the return value. +.Pp +The +.Fn crypto_x25519_public_key +function returns nothing. +It cannot fail. +.Sh SEE ALSO +.Xr crypto_lock 3monocypher , +.Xr intro 3monocypher +.Sh CAVEATS +No implementation advice can be given for implementing forward secrecy +using temporary public/private key pairs due to unfamiliarity of the +author with that matter. +.Pp +X25519 generally encodes all numbers in little endian. +This may require special attention when interoperating with other +cryptographic libraries that expose an ECDH interface consuming only +big integers in big endian representation, notably mbedTLS. +.Sh IMPLEMENTATION DETAILS +These functions implement X25519. +The +.Fn crypto_key_exchange +function utilizes HChacha20 as well. +.Pp +Note that the most significant bit of the public key is systematically +ignored. +It is not needed, because every public key should be smaller than +2^255-19, which fits in 255 bits. +If another implementation of X25519 gives you a key that's not fully +reduced and has its high bit set, the computation will fail. +On the other hand, it also means you may use this bit for other purposes +(such as parity flipping for Ed25519 compatibility). diff --git a/man/3monocypher/crypto_lock.3monocypher b/man/3monocypher/crypto_lock.3monocypher new file mode 100644 index 0000000..f048a3f --- /dev/null +++ b/man/3monocypher/crypto_lock.3monocypher @@ -0,0 +1,183 @@ +.Dd August 25, 2017 +.Dt CRYPTO_LOCK 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_lock , +.Nm crypto_unlock +.Nd authenticated encryption +.Sh SYNOPSIS +.In monocypher.h +.Ft void +.Fo crypto_lock +.Fa "uint8_t mac[16]" +.Fa "uint8_t *cipher_text" +.Fa "const uint8_t key[32]" +.Fa "const uint8_t nonce[24]" +.Fa "const uint8_t *plain_text" +.Fa "size_t text_size" +.Fc +.Ft int +.Fo crypto_unlock +.Fa "uint8_t *plain_text" +.Fa "const uint8_t key[32]" +.Fa "const uint8_t nonce[24]" +.Fa "const uint8_t mac[16]" +.Fa "const uint8_t *cipher_text" +.Fa "size_t text_size" +.Fc +.Sh DESCRIPTION +Encryption makes your messages unreadable to eavesdroppers. +Authentication ascertain the origin and integrity of the messages you +read. +Both are important. +Without encryption, you give away all your secrets, and without +authentication, you can fall prey to forgeries (messages that look +legitimate, but actually come from an attacker). +A clever attacker may even leverage forgeries to steal your secrets. +Always authenticate your messages. +.Pp +The +.Fn crypto_lock +function encrypts and authenticates a plaintext. +It can be decrypted by the +.Fn crypto_unlock +function. +The arguments are: +.Bl -tag -width Ds +.It Fa key +a 32-byte session key, shared between you and the recipient. +It must be secret (unknown to the attacker) and random (unpredictable to +an attacker). +Of course, one does not simply transmit this key over the network. +Meeting physically or performing a Diffie Hellman key exchange (see +.Xr crypto_key_exchange 3monocypher ) +are preferable methods. +.It Fa nonce +a 24-byte number, used only once with any given session key. +It does not have to be secret or random. +But you must +.Em never +reuse that number with the same key. +If you do, the attacker will have access to the XOR of 2 different +messages, allowing decryption, +.Em and +the ability to forge messages in your stead. +The easiest (and recommended) way to generate this nonce is to +select it at random. +See +.Xr intro 3monocypher +about random number generation (in short: use your operating +system's random number generator). +.It Fa mac +a 16-byte +.Em message authentication code (MAC) , +that only you could have produced. +This guarantee cannot be upheld once an attacker learns your session +key, or sees 2 messages with the same nonce. +Seriously, do not reuse the nonce. +The MAC is intended to be sent along with the ciphertext. +.It Fa plain_text +the secret you want to send. +Of course, it must be unknown to an attacker. +Keep in mind however that the +.Em length +of the plaintext, unlike its content, is not made secret by these +functions. +Make sure your protocol does not leak secret information with the length +of messages. +This has happened before with variable-length voice +encoding software. +Solutions to mitigate this include constant-length encodings and +padding. +.It Fa cipher_text +the encrypted message (same length as the plaintext +message). +Transmit it over the network so the recipient can decrypt +and read it. +Note: +.Fa cipher_text is allowed to have the same value as +.Fa plain_text . +If so, encryption or decryption will happen in place. +.El +.Pp +Unlocking proceeds in two steps: first, we authenticate the ciphertext +with the provided MAC. +If it has been corrupted, the +.Fn crypto_aead_unlock +function returns immediately, +without decrypting the message. +If the message is genuine, the +.Fn crypto_aead_unlock +function decrypts the ciphertext. +.Em Always check the return value . +.Sh RETURN VALUES +The +.Fn crypto_lock +function returns nothing. +It cannot fail. +The +.Fn crypto_unlock +function returns 0 on success or -1 if the message was corrupted +(i.e. +.Fa mac +mismatched the combination of +.Fa key , +.Fa nonce +and +.Fa cipher_text ) . +Corruption can happen because of transmission errors, programmer error +(e.g. failed to parse the protocol properly and thus supplied only part +of the expected +.Fa cipher_text ) +or an attacker's interference. +.Sh EXAMPLES +Encryption: +.Bd -literal -offset indent +uint8_t key[32], nonce[24]; +uint8_t mac[16]; +char plain_text[] = "This does not have to be literally text."; +uint8_t cipher_text[51]; /* strlen(plain_text) + terminating NUL */ + +/* ...Generate a key, as well as a random nonce... */ + +crypto_lock(mac, cipher_text, key, nonce, plain_text, + sizeof(plain_text)); + +/* You can now transmit over the network: + * - cipher_text + * - nonce + * - mac + */ +.Ed +.Pp +To decrypt the above: +.Bd -literal -offset indent +uint8_t key[32], nonce[24]; +uint8_t mac[16]; +char plain_text[51]; /* strlen(plain_text) + terminating NUL */ +uint8_t cipher_text[51]; +int ret; + +/* Ensure that the key and nonce match the ones used in the + * encryption process. + * + * Now read mac and cipher_text from the network; nonce as well if it + * was sent along. + */ + +ret = crypto_unlock(plain_text, key, nonce, mac, cipher_text, + sizeof(cipher_text)); +if (ret != 0) { + /* Message corrupted; possibly an attacker is interfering + * with the connection. + */ +} +.Ed +.Sh SEE ALSO +.Xr crypto_aead_lock 3monocypher , +.Xr crypto_aead_unlock 3monocypher , +.Xr crypto_key_exchange 3monocypher , +.Xr intro 3monocypher +.Sh IMPLEMENTATION DETAILS +These functions implement the XChacha20 (encryption) and Poly1305 (MAC) +primitives. diff --git a/man/3monocypher/crypto_memcmp.3monocypher b/man/3monocypher/crypto_memcmp.3monocypher new file mode 100644 index 0000000..6aa18c0 --- /dev/null +++ b/man/3monocypher/crypto_memcmp.3monocypher @@ -0,0 +1,67 @@ +.Dd August 25, 2017 +.Dt CRYPTO_MEMCMP 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_memcmp , +.Nm crypto_zerocmp +.Nd timing-safe data comparisons +.Sh SYNOPSIS +.In monocypher.h +.Ft int +.Fn crypto_memcmp "const uint8_t *p1" "const uint8_t *p2" "size_t n" +.Ft int +.Fn crypto_zerocmp "const uint8_t *p" "size_t n" +.Sh DESCRIPTION +In crypto, we often need to compare secrets together. +A message authentication code for instance: +while the MAC sent over the network along with a message is public, the +true MAC is secret. +If the attacker attempts a forgery, you do not want to state +.Dq your MAC is wrong, Em and it took 384 microseconds to know . +If the next attempt takes 462 microseconds instead, it gives away the +fact that the attacker just got a few bytes right. +That way, an attacker can derive the correct MAC. +.Pp +To avoid such catastrophe, +.Fn crypto_memcmp +and +.Fn crypto_zerocmp +provide comparison functions whose timing is independent from the +context of their input. +.Pp +The +.Fn crypto_memcmp +function compares the first +.Fa n +bytes of the two byte arrays +.Fa p1 +and +.Fa p2 . +The +.Fn crypto_zerocmp +function compares the first +.Fa n +bytes of the byte array +.Fa p1 +against zero. +.Pp +You should not need these functions if you use the high-level interface +of Monocypher \(en just look at the return codes. +But if you do have to compare secrets, make sure you use +.Fn crypto_memcmp +or +.Fn crypto_zerocmp . +If you are in doubt whether you need to use these functions, prefer +these over +.Xr memcmp 3 . +.Sh RETURN VALUES +The +.Fn crypto_memcmp +function returns 0 if the two memory chunks are the same, -1 otherwise. +The +.Fn crypto_zerocmp +function returns 0 if all bytes of the memory chunk are zero, -1 +otherwise. +.Sh SEE ALSO +.Xr memcmp 3 , +.Xr intro 3monocypher diff --git a/man/3monocypher/crypto_poly1305_auth.3monocypher b/man/3monocypher/crypto_poly1305_auth.3monocypher new file mode 100644 index 0000000..961b1f7 --- /dev/null +++ b/man/3monocypher/crypto_poly1305_auth.3monocypher @@ -0,0 +1,133 @@ +.Dd August 26, 2017 +.Dt CRYPTO_POLY1305_AUTH 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_poly1305_auth , +.Nm crypto_poly1305_init , +.Nm crypto_poly1305_update , +.Nm crypto_poly1305_final +.Nd Poly1305 one-time message authentication codes +.Sh SYNOPSIS +.In monocypher.h +.Ft void +.Fo crypto_poly1305_auth +.Fa "uint8_t mac[16]" +.Fa "const uint8_t *message" +.Fa "size_t message_size" +.Fa "const uint8_t key[32]" +.Fc +.Ft void +.Fo crypto_poly1305_init +.Fa "crypto_poly1305_ctx *ctx" +.Fa "const uint8_t key[32]" +.Fc +.Ft void +.Fo crypto_poly1305_update +.Fa "crypto_poly1305_ctx *ctx" +.Fa "const uint8_t *message" +.Fa "size_t message_size" +.Fc +.Ft void +.Fo crypto_poly1305_final +.Fa "crypto_poly1305_ctx *ctx" +.Fa "const uint8_t mac[16]" +.Fc +.Sh DESCRIPTION +Monocypher provides both a direct interface and an incremental +interface for Poly1305, which is used to generate a one-time message +authentication code (MAC). +.Sy Poly1305 is easy to mess up . +Using it directly is likely to lead to mistakes. +.Pp +Be careful when using this function. +The requirements for a Poly1305 key are +.Em stringent : +.Bl -bullet +.It +It must be secret: the attacker cannot be allowed to guess that key. +.It +It must be shared: the recipient must know this key. +Without it, the integrity of the message cannot be verified. +.It +It must +.Sy never +be reused. +That would allow the attacker to recover the key then forge messages, +destroying any security. +.El +.Pp +You cannot use the session key for this: it is secret and shared, but +it is +.Em reused . +If you use it, the attacker will recover it as soon as the second +message is sent, and will break all security. +.Pp +You cannot use a random number: if you do not send it over the network, +it will not be shared, and the recipient will be unable to check the +MAC. +If you do, it will not be secret, and the attacker will be able to forge +messages. +.Pp +The only practical source for the authentication key is a chunk of the +encryption stream used to encrypt the message. +However, you must ensure you do not reuse that part of the stream to +encrypt the message itself: +the attacker could guess the stream by guessing the message, and forge +messages afterwards. +.Pp +To get this right, you need a session key, a +.Em unique +nonce, and a +stream cipher. +Generate a stream with the session key and nonce. +Take the first 32 bits of that stream as your authentication key, then +use the +.Em rest +of the stream to encrypt your message. +Check out the source code of +.Xr crypto_aead_lock 3monocypher +to see how it is done. +.Pp +The direct interface consists of the +.Fn crypto_poly1305_auth +function produces a message authentication code for the given +message and authentication key. +.Pp +The indirect interface consists of the +.Fn crypto_poly1305_init , +.Fn crypto_poly1305_update , +and +.Fn crypto_poly1305_final +functions. +The +.Fn crypto_poly1305_init +function initialises a context, and the +.Fn crypto_poly1305_update +function authenticates the message chunk by chunk. +Once the message is entirely processed, the +.Fn crypto_poly1305_final +function yields the message authentication code. +.Pp +Use +.Xr crypto_memcmp 3monocypher +to compare the MAC received to the output +.Fa mac . +.Sh RETURN VALUES +These functions return nothing. +They cannot fail. +.Sh SEE ALSO +.Xr crypto_blake2b 3monocypher , +.Xr crypto_lock 3monocypher , +.Xr crypto_memcmp 3monocypher , +.Xr intro 3monocypher +.Sh CAVEATS +Using Poly1305 correctly is very difficult. +Please do not use it unless you are absolutely sure what you are doing. +Use authenticated encryption instead; see +.Xr crypto_lock 3monocypher . +If you are absolutely certain you do not want encryption, refer to +.Xr crypto_blake2b 3monocypher , +which contains information on how to use Blake2b to generate message +authentication codes. +.Sh IMPLEMENTATION DETAILS +These functions implement Poly1305. diff --git a/man/3monocypher/crypto_sign.3monocypher b/man/3monocypher/crypto_sign.3monocypher new file mode 100644 index 0000000..ee76e63 --- /dev/null +++ b/man/3monocypher/crypto_sign.3monocypher @@ -0,0 +1,120 @@ +.Dd August 26, 2017 +.Dt CRYPTO_SIGN 3MONOCYPHER +.Os +.Sh NAME +.Nm crypto_sign , +.Nm crypto_check , +.Nm crypto_sign_public_key +.Nd public key signatures +.Sh SYNOPSIS +.In monocypher.h +.Ft int +.Fo crypto_sign +.Fa "uint8_t signature[64]" +.Fa "const uint8_t secret_key[32]" +.Fa "const uint8_t public_key[32]" +.Fa "const uint8_t *message" +.Fa "size_t message_size" +.Fc +.Ft int +.Fo crypto_check +.Fa "const uint8_t signature[64]" +.Fa "const uint8_t public_key[32]" +.Fa "const uint8_t *message" +.Fa "size_t message_size" +.Fc +.Ft void +.Fo crypto_sign_public_key +.Fa "uint8_t public_key[32]" +.Fa "const uint8_t secret_key[32]" +.Fc +.Sh DESCRIPTION +Authenticated encryption with key exchange is not always enough. +Sometimes, you want to +.Em broadcast +a signature, in such a way that +.Em everybody +can verify. +.Pp +When you sign a message with your private key, anybody who knows your +public key can verify that you signed the message. +Obviously, any attacker that gets a hold of your private key can sign +messages in your stead. +Protect your private key. +.Pp +These functions provide public key signatures with a variant of ed25519, +which uses Blake2b as the hash instead of SHA-512. +SHA-512 is provided as an option for compatibility with other systems. +.Pp +Blake2b is the default because it is faster, more flexible, harder to +misuse than SHA-512, and already required by +.Xr crypto_argon2i 3monocypher . +Monocypher needs only one hash, and that shall be Blake2b. +.Pp +Note that using Blake2b instead of SHA-512 does +.Em not +block your upgrade path to faster implementations: Floodyberry's Donna +(ed25519-donna) library provides blazing fast implementations that can +work with custom hashes. +.Pp +The keys used for these functions are +.Em not +the same as used for +.Xr crypto_key_exchange 3monocypher . +There are ways to convert keys from signing keys to X25519 keys, +but those are not covered by Monocypher. +.Pp +The +.Fn crypto_sign_public_key +function deterministically computes a public key from the specified +secret key. +Make sure the secret key is randomly selected. +Refer to +.Xr intro 3monocypher +for details about random number generation (use your operating system's +random number generator). +.Pp +The +.Fn crypto_sign +function signs a message with your secret key +.Fa secret_key . +The public key is optional, and will be recomputed if not provided. +However, this doubles execution time. +.Pp +The +.Fn crypto_check +function checks that a given signature is genuine. +Of course, if an attacker gets a hold of the matching private key, +no security guarantees can be made anymore. +This function does +.Em not +run in constant time. +It does not have to in most threat models, because nothing is secret: +everyone knows the public key, and the signature and message are +rarely secret. +If you want to ascertain the origin of a secret message, you may want +to use the +.Xr crypto_key_exchange 3monocypher +function instead. +.Sh RETURN VALUES +The +.Fn crypto_sign_public_key +and +.Fn crypto_sign +functions return nothing. +They cannot fail. +.Pp +The +.Fn crypto_check +function returns zero for legitimate messages and -1 for forgeries. +.Sh SEE ALSO +.Xr crypto_blake2b 3monocypher , +.Xr crypto_key_exchange 3monocypher , +.Xr crypto_lock 3monocypher , +.Xr intro 3monocypher +.Sh IMPLEMENTATION DETAILS +These functions implement edDSA with Curve25519 and Blake2b (or +optionally SHA-512). +.Pp +The reason why there is a SHA-512 option at all is due to official test +vectors. diff --git a/man/3monocypher/intro.3monocypher b/man/3monocypher/intro.3monocypher new file mode 100644 index 0000000..34915bc --- /dev/null +++ b/man/3monocypher/intro.3monocypher @@ -0,0 +1,165 @@ +.Dd August 26, 2017 +.Dt INTRO 3MONOCYPHER +.Os +.Sh NAME +.Nm intro +.Nd introduction to Monocypher +.Sh DESCRIPTION +Monocypher is a cryptographic library. +It provides functions for authenticated encryption, cryptographic +hashing, public key signatures and password key derivation. +The rest of this section covers various topics that require special +consideration, followed by an index. +.Ss Random number generation +Monocypher does not provide a random number generator. +You are supposed to use the facilities of your operating system. +Avoid user space random number generators. +They are easy to misuse, which has lead to countless vulnerabilities +in the past, typically by repeating parts of the random stream. +They typically require an external random seed anyway. +.Pp +On Linux, you can use the +.Xr getrandom 2 +system call from +.In linux/random.h . +Do not set any flag. +.Pp +On BSD, you can use +.Xr arc4random_buf 3 +from +.In stdlib.h +or +.In bsd/stdlib.h . +This is arguably even easier to use than +.Fn getrandom . +.Pp +Windows provides the +.Fn CryptGenRandom +function. +.Pp +If no easy to use system call is available on your system, you may +have to use +.Pa /dev/urandom . +It is more difficult to use, however, because it involves reading a file +and the read may get aborted. +Make sure you indeed get all the random bytes you requested. +Generating random numbers for cryptographic purposes portably is +currently impossible without using other libraries. +.Ss Avoid swapping secrets to disk +Ideally, you want your computer to reliably forget your secrets once +it is done with them. +Unfortunately, computers often need to swap memory to disk. +This would make your secrets persistent, and may allow an attacker to +recover them later if they can read the swap partition. +.Pp +There are several ways to avoid swapping secrets to disk. +The most secure is to disable swapping entirely. +Doing so is recommended on sensitive machines. +Or you could use an encrypted partition for the swap (less safe). +In addition, you can disable swap locally \(en this is often the only +way. +.Pp +To disable swap on specific memory regions, UNIX systems provide the +.Xr mlock 2 +system call. +Windows has +.Fn VirtualLock . +UNIX systems also provide the +.Xr mlockall 2 +system call, which locks +.Em all +memory used by a single process. +Though possibly overkill, this is easier to use safely. +.Pp +.Bf Em +Note: core dumps cause similar problems. +Disable them. +Also beware of suspend to disk (deep sleep mode), which writes all RAM +to disk regardless of swap policy, as well as virtual machine snapshots. +.Ef +.Ss Index +Monocypher provides functions the following: +.Bl -ohang -offset indent +.It Authenticated encryption +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_lock 3monocypher +.It Xr crypto_unlock 3monocypher +.El +.It Authenticated encryption with additional data (AEAD) +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_aead_lock 3monocypher +.It Xr crypto_aead_unlock 3monocypher +.El +.It (Elliptic Curve) Diffie-Hellman key exchange +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_key_exchange 3monocypher +.It Xr crypto_x25519_public_key 3monocypher +.It Xr crypto_x25519 3monocypher +.El +.It Public key signatures +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_sign_public_key 3monocypher +.It Xr crypto_sign 3monocypher +.It Xr crypto_check 3monocypher +.El +.It Cryptographic hashing +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_blake2b_general 3monocypher +.It Xr crypto_blake2b 3monocypher +.It Xr crypto_blake2b_general_init 3monocypher +.It Xr crypto_blake2b_init 3monocypher +.It Xr crypto_blake2b_update 3monocypher +.It Xr crypto_blake2b_final 3monocypher +.El +.It Special-purpose hashing +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_chacha20_H 3monocypher +.El +.It Password key derivation +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_argon2i 3monocypher +.El +.It Unauthenticated encryption +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_chacha20_init 3monocypher +.It Xr crypto_chacha20_x_init 3monocypher +.It Xr crypto_chacha20_encrypt 3monocypher +.It Xr crypto_chacha20_stream 3monocypher +.It Xr crypto_chacha20_set_ctr 3monocypher +.El +.It One-time authentication +.Bl -tag -offset indent-two -width Ds +.It Xr crypto_poly1305_auth 3monocypher +.It Xr crypto_poly1305_init 3monocypher +.It Xr crypto_poly1305_update 3monocypher +.It Xr crypto_poly1305_final 3monocypher +.El +.El +.Sh SEE ALSO +.Xr crypto_lock 3monocypher , +.Xr crypto_unlock 3monocypher , +.Xr crypto_aead_lock 3monocypher , +.Xr crypto_aead_unlock 3monocypher , +.Xr crypto_key_exchange 3monocypher , +.Xr crypto_x25519_public_key 3monocypher , +.Xr crypto_x25519 3monocypher , +.Xr crypto_sign_public_key 3monocypher , +.Xr crypto_sign 3monocypher , +.Xr crypto_check 3monocypher , +.Xr crypto_blake2b_general 3monocypher , +.Xr crypto_blake2b 3monocypher , +.Xr crypto_blake2b_general_init 3monocypher , +.Xr crypto_blake2b_init 3monocypher , +.Xr crypto_blake2b_update 3monocypher , +.Xr crypto_blake2b_final 3monocypher , +.Xr crypto_chacha20_H 3monocypher , +.Xr crypto_argon2i 3monocypher , +.Xr crypto_chacha20_init 3monocypher , +.Xr crypto_chacha20_x_init 3monocypher , +.Xr crypto_chacha20_encrypt 3monocypher , +.Xr crypto_chacha20_stream 3monocypher , +.Xr crypto_chacha20_set_ctr 3monocypher , +.Xr crypto_poly1305_auth 3monocypher , +.Xr crypto_poly1305_init 3monocypher , +.Xr crypto_poly1305_update 3monocypher , +.Xr crypto_poly1305_final 3monocypher