diff options
-rw-r--r-- | Doxyfile.in | 4 | ||||
-rw-r--r-- | src/method.h | 40 | ||||
-rw-r--r-- | src/sha256.c | 23 | ||||
-rw-r--r-- | src/sha256.h | 18 |
4 files changed, 72 insertions, 13 deletions
diff --git a/Doxyfile.in b/Doxyfile.in index 8334b9e..7b9f2ba 100644 --- a/Doxyfile.in +++ b/Doxyfile.in @@ -726,7 +726,7 @@ WARN_IF_DOC_ERROR = YES # documentation, but not about the absence of documentation. # The default value is: NO. -WARN_NO_PARAMDOC = YES +WARN_NO_PARAMDOC = NO # The WARN_FORMAT tag determines the format of the warning messages that doxygen # can produce. The string should contain the $file, $line, and $text tags, which @@ -774,7 +774,7 @@ INPUT_ENCODING = UTF-8 # *.md, *.mm, *.dox, *.py, *.f90, *.f, *.for, *.tcl, *.vhd, *.vhdl, *.ucf, # *.qsf, *.as and *.js. -FILE_PATTERNS = "*.c" "*.h" "*.h.in" +FILE_PATTERNS = "*.c" "*.h" "*.c.in" "*.h.in" # The RECURSIVE tag can be used to specify whether or not subdirectories should # be searched for input files as well. diff --git a/src/method.h b/src/method.h index d7f3304..32b5b5c 100644 --- a/src/method.h +++ b/src/method.h @@ -23,39 +23,60 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +/** + \file method.h + + Management of encryption methods +*/ + #pragma once #include "fastd.h" +/** Information about a single encryption method */ struct fastd_method_info { - const char *name; - const fastd_method_provider_t *provider; - fastd_method_t *method; + const char *name; /**< The method name */ + const fastd_method_provider_t *provider; /**< The provider of the method */ + fastd_method_t *method; /**< Provider-specific method data */ }; +/** Describes a method provider (an implementation of a class of encryption methods) */ struct fastd_method_provider { - size_t max_overhead; - size_t min_encrypt_head_space; - size_t min_decrypt_head_space; - size_t min_encrypt_tail_space; - size_t min_decrypt_tail_space; + size_t max_overhead; /**< The maximum number of bytes of overhead the methods may add */ + size_t min_encrypt_head_space; /**< The minimum head space needed for encrytion */ + size_t min_decrypt_head_space; /**< The minimum head space needed for decryption */ + size_t min_encrypt_tail_space; /**< The minimum tail space needed for encryption */ + size_t min_decrypt_tail_space; /**< The minimum tail space needed for decryption */ + /** Tries to create a method with the given name */ bool (*create_by_name)(const char *name, fastd_method_t **method); + /** Frees the resources allocated for a method */ void (*destroy)(fastd_method_t *method); + /** Returns the key length used by a method */ size_t (*key_length)(const fastd_method_t *method); + /** Initiates a session */ fastd_method_session_state_t* (*session_init)(const fastd_method_t *method, const uint8_t *secret, bool initiator); + /** Initiates a session in pre-v11 compatiblity mode */ fastd_method_session_state_t* (*session_init_compat)(const fastd_method_t *method, const uint8_t *secret, size_t length, bool initiator); + /** Closes a session */ + void (*session_free)(fastd_method_session_state_t *session); + + /** Determines if a session is currently valid */ bool (*session_is_valid)(fastd_method_session_state_t *session); + /** Determines if this fastd instance is the intiator of a given session */ bool (*session_is_initiator)(fastd_method_session_state_t *session); + /** Checks if this side wants to refresh the session, negotiating a new session key */ bool (*session_want_refresh)(fastd_method_session_state_t *session); + /** Marks a session as superseded after a refresh */ void (*session_superseded)(fastd_method_session_state_t *session); - void (*session_free)(fastd_method_session_state_t *session); + /** Encrypts a packet for a given session, adding method-specific headers */ bool (*encrypt)(fastd_peer_t *peer, fastd_method_session_state_t *session, fastd_buffer_t *out, fastd_buffer_t in); + /** Decrypts a packet for a given session, stripping method-specific headers */ bool (*decrypt)(fastd_peer_t *peer, fastd_method_session_state_t *session, fastd_buffer_t *out, fastd_buffer_t in); }; @@ -63,6 +84,7 @@ struct fastd_method_provider { bool fastd_method_create_by_name(const char *name, const fastd_method_provider_t **provider, fastd_method_t **method); +/** Finds the fastd_method_info_t for a configured method */ static inline const fastd_method_info_t* fastd_method_get_by_name(const char *name) { size_t i; for (i = 0; conf.methods[i].name; i++) { diff --git a/src/sha256.c b/src/sha256.c index 38bc43d..c05adbc 100644 --- a/src/sha256.c +++ b/src/sha256.c @@ -23,6 +23,12 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +/** + \file sha256.c + + Small SHA256 and HMAC-SHA256 implementation +*/ + #include "sha256.h" @@ -32,10 +38,16 @@ #include <arpa/inet.h> +/** right-rotation of a 32bit value */ static inline uint32_t rotr(uint32_t x, int r) { return (x >> r) | (x << (32-r)); } +/** + Copies a (potentially incomplete) input block, while switching from big endian to CPU byte order + + After the last byte, a one-bit is added, as SHA256 defines. +*/ static inline void copy_words(uint32_t w[8], const uint32_t *in, ssize_t *left) { size_t i; for (i = 0; i < 8; i++) { @@ -58,6 +70,7 @@ static inline void copy_words(uint32_t w[8], const uint32_t *in, ssize_t *left) } } +/** Hashes a list of input blocks */ static void sha256_list(uint32_t out[FASTD_SHA256_HASH_WORDS], const uint32_t *const *in, size_t len) { static const uint32_t k[64] = { 0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5, 0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5, @@ -126,6 +139,7 @@ static void sha256_list(uint32_t out[FASTD_SHA256_HASH_WORDS], const uint32_t *c out[i] = htonl(h[i]); } +/** Hashes a NULL-terminated va_list of complete input blocks */ static void sha256_blocks_va(uint32_t out[FASTD_SHA256_HASH_WORDS], va_list ap) { size_t count = 0; va_list ap2; @@ -145,6 +159,7 @@ static void sha256_blocks_va(uint32_t out[FASTD_SHA256_HASH_WORDS], va_list ap) sha256_list(out, blocks, count*FASTD_SHA256_BLOCK_BYTES); } +/** Hashes complete input blocks (argument list must by NULL-terminated) */ void fastd_sha256_blocks(fastd_sha256_t *out, ...) { va_list ap; @@ -153,6 +168,7 @@ void fastd_sha256_blocks(fastd_sha256_t *out, ...) { va_end(ap); } +/** Hashes a buffer of arbitraty length (must by 32bit-aligned) */ void fastd_sha256(fastd_sha256_t *out, const uint32_t *in, size_t len) { size_t i, count = (len+FASTD_SHA256_BLOCK_BYTES-1) / FASTD_SHA256_BLOCK_BYTES; const uint32_t *blocks[count]; @@ -163,6 +179,7 @@ void fastd_sha256(fastd_sha256_t *out, const uint32_t *in, size_t len) { sha256_list(out->w, blocks, len); } +/** Computes the HMAC-SHA256 of a list of (potentially incomplete) input blocks */ static void hmacsha256_list(fastd_sha256_t *out, const uint32_t key[FASTD_HMACSHA256_KEY_WORDS], const uint32_t *const *in, size_t len) { static const uint32_t ipad2[8] = { 0x36363636, @@ -205,6 +222,7 @@ static void hmacsha256_list(fastd_sha256_t *out, const uint32_t key[FASTD_HMACSH fastd_sha256_blocks(out, opad, opad2, temp, NULL); } +/** Computes the HMAC-SHA256 of a list of NULL-terminated va_list of input blocks */ static void hmacsha256_blocks_va(fastd_sha256_t *out, const uint32_t key[FASTD_HMACSHA256_KEY_WORDS], va_list ap) { size_t count = 0; va_list ap2; @@ -224,6 +242,8 @@ static void hmacsha256_blocks_va(fastd_sha256_t *out, const uint32_t key[FASTD_H hmacsha256_list(out, key, blocks, count*FASTD_SHA256_BLOCK_BYTES); } + +/** Computes the HMAC-SHA256 of the complete blocks given as arguments (the argument list must be NULL-terminated) */ void fastd_hmacsha256_blocks(fastd_sha256_t *out, const uint32_t key[FASTD_HMACSHA256_KEY_WORDS], ...) { va_list ap; @@ -232,6 +252,7 @@ void fastd_hmacsha256_blocks(fastd_sha256_t *out, const uint32_t key[FASTD_HMACS va_end(ap); } +/** Verifies the HMAC-SHA256 of the complete blocks given as arguments (the argument list must be NULL-terminated) */ bool fastd_hmacsha256_blocks_verify(const uint8_t mac[FASTD_SHA256_HASH_BYTES], const uint32_t key[FASTD_HMACSHA256_KEY_WORDS], ...) { va_list ap; fastd_sha256_t out; @@ -243,6 +264,7 @@ bool fastd_hmacsha256_blocks_verify(const uint8_t mac[FASTD_SHA256_HASH_BYTES], return !memcmp(out.b, mac, FASTD_SHA256_HASH_BYTES); } +/** Computes the HMAC-SHA256 of an arbitraty input buffer */ void fastd_hmacsha256(fastd_sha256_t *out, const uint32_t key[FASTD_HMACSHA256_KEY_WORDS], const uint32_t *in, size_t len) { size_t i, count = (len+FASTD_SHA256_BLOCK_BYTES-1) / FASTD_SHA256_BLOCK_BYTES; const uint32_t *blocks[count]; @@ -253,6 +275,7 @@ void fastd_hmacsha256(fastd_sha256_t *out, const uint32_t key[FASTD_HMACSHA256_K hmacsha256_list(out, key, blocks, len); } +/** Verifies the HMAC-SHA256 of an arbitraty input buffer */ bool fastd_hmacsha256_verify(const uint8_t mac[FASTD_SHA256_HASH_BYTES], const uint32_t key[FASTD_HMACSHA256_KEY_WORDS], const uint32_t *in, size_t len) { fastd_sha256_t out; diff --git a/src/sha256.h b/src/sha256.h index 30a8d35..a0b8805 100644 --- a/src/sha256.h +++ b/src/sha256.h @@ -23,6 +23,13 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +/** + \file sha256.h + + Small SHA256 and HMAC-SHA256 implementation +*/ + + #pragma once @@ -31,20 +38,27 @@ #include <stdint.h> +/** 32bit words per SHA256 hash */ #define FASTD_SHA256_HASH_WORDS 8 +/** 32bit words per input block */ #define FASTD_SHA256_BLOCK_WORDS 8 +/** 32bit words per HMAC-SHA256 key */ #define FASTD_HMACSHA256_KEY_WORDS 8 +/** bytes per SHA256 hash */ #define FASTD_SHA256_HASH_BYTES (4*FASTD_SHA256_HASH_WORDS) +/** bytes per input block */ #define FASTD_SHA256_BLOCK_BYTES (4*FASTD_SHA256_BLOCK_WORDS) +/** bytes per HMAC-SHA256 key */ #define FASTD_HMACSHA256_KEY_BYTES (4*FASTD_HMACSHA256_KEY_WORDS) +/** A SHA256 hash output */ typedef union fastd_sha256 { - uint32_t w[FASTD_SHA256_HASH_WORDS]; - uint8_t b[FASTD_SHA256_HASH_BYTES]; + uint32_t w[FASTD_SHA256_HASH_WORDS]; /**< 32bit-word-wise access */ + uint8_t b[FASTD_SHA256_HASH_BYTES]; /**< bytewise access */ } fastd_sha256_t; |