]> git.codecow.com Git - Monocypher.git/commitdiff
Add man pages
authorCuleX <cculex@gmail.com>
Sat, 26 Aug 2017 10:09:19 +0000 (12:09 +0200)
committerCuleX <cculex@gmail.com>
Sat, 26 Aug 2017 12:06:42 +0000 (14:06 +0200)
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.

man/3monocypher/crypto_aead_lock.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_argon2i.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_blake2b.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_chacha20_H.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_chacha20_encrypt.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_key_exchange.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_lock.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_memcmp.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_poly1305_auth.3monocypher [new file with mode: 0644]
man/3monocypher/crypto_sign.3monocypher [new file with mode: 0644]
man/3monocypher/intro.3monocypher [new file with mode: 0644]

diff --git a/man/3monocypher/crypto_aead_lock.3monocypher b/man/3monocypher/crypto_aead_lock.3monocypher
new file mode 100644 (file)
index 0000000..f66a921
--- /dev/null
@@ -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 (file)
index 0000000..998c148
--- /dev/null
@@ -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 (file)
index 0000000..3adf095
--- /dev/null
@@ -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 (file)
index 0000000..e20a861
--- /dev/null
@@ -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 (file)
index 0000000..f22cb53
--- /dev/null
@@ -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 (file)
index 0000000..b10de9e
--- /dev/null
@@ -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 (file)
index 0000000..f048a3f
--- /dev/null
@@ -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 (file)
index 0000000..6aa18c0
--- /dev/null
@@ -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 (file)
index 0000000..961b1f7
--- /dev/null
@@ -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 (file)
index 0000000..ee76e63
--- /dev/null
@@ -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 (file)
index 0000000..34915bc
--- /dev/null
@@ -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