diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/lib/libcrypto/sha/sha3.c | 282 | ||||
| -rw-r--r-- | src/lib/libcrypto/sha/sha3_internal.h | 16 |
2 files changed, 152 insertions, 146 deletions
diff --git a/src/lib/libcrypto/sha/sha3.c b/src/lib/libcrypto/sha/sha3.c index 1489fb74f4..13faed3e9e 100644 --- a/src/lib/libcrypto/sha/sha3.c +++ b/src/lib/libcrypto/sha/sha3.c | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: sha3.c,v 1.3 2023/04/15 18:00:57 jsing Exp $ */ | 1 | /* $OpenBSD: sha3.c,v 1.4 2023/04/15 18:07:44 jsing Exp $ */ |
| 2 | /* | 2 | /* |
| 3 | * The MIT License (MIT) | 3 | * The MIT License (MIT) |
| 4 | * | 4 | * |
| @@ -33,184 +33,190 @@ | |||
| 33 | 33 | ||
| 34 | // update the state with given number of rounds | 34 | // update the state with given number of rounds |
| 35 | 35 | ||
| 36 | void sha3_keccakf(uint64_t st[25]) | 36 | void |
| 37 | sha3_keccakf(uint64_t st[25]) | ||
| 37 | { | 38 | { |
| 38 | // constants | 39 | // constants |
| 39 | const uint64_t keccakf_rndc[24] = { | 40 | const uint64_t keccakf_rndc[24] = { |
| 40 | 0x0000000000000001, 0x0000000000008082, 0x800000000000808a, | 41 | 0x0000000000000001, 0x0000000000008082, 0x800000000000808a, |
| 41 | 0x8000000080008000, 0x000000000000808b, 0x0000000080000001, | 42 | 0x8000000080008000, 0x000000000000808b, 0x0000000080000001, |
| 42 | 0x8000000080008081, 0x8000000000008009, 0x000000000000008a, | 43 | 0x8000000080008081, 0x8000000000008009, 0x000000000000008a, |
| 43 | 0x0000000000000088, 0x0000000080008009, 0x000000008000000a, | 44 | 0x0000000000000088, 0x0000000080008009, 0x000000008000000a, |
| 44 | 0x000000008000808b, 0x800000000000008b, 0x8000000000008089, | 45 | 0x000000008000808b, 0x800000000000008b, 0x8000000000008089, |
| 45 | 0x8000000000008003, 0x8000000000008002, 0x8000000000000080, | 46 | 0x8000000000008003, 0x8000000000008002, 0x8000000000000080, |
| 46 | 0x000000000000800a, 0x800000008000000a, 0x8000000080008081, | 47 | 0x000000000000800a, 0x800000008000000a, 0x8000000080008081, |
| 47 | 0x8000000000008080, 0x0000000080000001, 0x8000000080008008 | 48 | 0x8000000000008080, 0x0000000080000001, 0x8000000080008008 |
| 48 | }; | 49 | }; |
| 49 | const int keccakf_rotc[24] = { | 50 | const int keccakf_rotc[24] = { |
| 50 | 1, 3, 6, 10, 15, 21, 28, 36, 45, 55, 2, 14, | 51 | 1, 3, 6, 10, 15, 21, 28, 36, 45, 55, 2, 14, |
| 51 | 27, 41, 56, 8, 25, 43, 62, 18, 39, 61, 20, 44 | 52 | 27, 41, 56, 8, 25, 43, 62, 18, 39, 61, 20, 44 |
| 52 | }; | 53 | }; |
| 53 | const int keccakf_piln[24] = { | 54 | const int keccakf_piln[24] = { |
| 54 | 10, 7, 11, 17, 18, 3, 5, 16, 8, 21, 24, 4, | 55 | 10, 7, 11, 17, 18, 3, 5, 16, 8, 21, 24, 4, |
| 55 | 15, 23, 19, 13, 12, 2, 20, 14, 22, 9, 6, 1 | 56 | 15, 23, 19, 13, 12, 2, 20, 14, 22, 9, 6, 1 |
| 56 | }; | 57 | }; |
| 57 | 58 | ||
| 58 | // variables | 59 | // variables |
| 59 | int i, j, r; | 60 | int i, j, r; |
| 60 | uint64_t t, bc[5]; | 61 | uint64_t t, bc[5]; |
| 61 | 62 | ||
| 62 | #if __BYTE_ORDER__ != __ORDER_LITTLE_ENDIAN__ | 63 | #if __BYTE_ORDER__ != __ORDER_LITTLE_ENDIAN__ |
| 63 | uint8_t *v; | 64 | uint8_t *v; |
| 64 | 65 | ||
| 65 | // endianess conversion. this is redundant on little-endian targets | 66 | // endianess conversion. this is redundant on little-endian targets |
| 66 | for (i = 0; i < 25; i++) { | 67 | for (i = 0; i < 25; i++) { |
| 67 | v = (uint8_t *) &st[i]; | 68 | v = (uint8_t *) &st[i]; |
| 68 | st[i] = ((uint64_t) v[0]) | (((uint64_t) v[1]) << 8) | | 69 | st[i] = ((uint64_t) v[0]) | (((uint64_t) v[1]) << 8) | |
| 69 | (((uint64_t) v[2]) << 16) | (((uint64_t) v[3]) << 24) | | 70 | (((uint64_t) v[2]) << 16) | (((uint64_t) v[3]) << 24) | |
| 70 | (((uint64_t) v[4]) << 32) | (((uint64_t) v[5]) << 40) | | 71 | (((uint64_t) v[4]) << 32) | (((uint64_t) v[5]) << 40) | |
| 71 | (((uint64_t) v[6]) << 48) | (((uint64_t) v[7]) << 56); | 72 | (((uint64_t) v[6]) << 48) | (((uint64_t) v[7]) << 56); |
| 72 | } | 73 | } |
| 73 | #endif | 74 | #endif |
| 74 | 75 | ||
| 75 | // actual iteration | 76 | // actual iteration |
| 76 | for (r = 0; r < KECCAKF_ROUNDS; r++) { | 77 | for (r = 0; r < KECCAKF_ROUNDS; r++) { |
| 77 | 78 | ||
| 78 | // Theta | 79 | // Theta |
| 79 | for (i = 0; i < 5; i++) | 80 | for (i = 0; i < 5; i++) |
| 80 | bc[i] = st[i] ^ st[i + 5] ^ st[i + 10] ^ st[i + 15] ^ st[i + 20]; | 81 | bc[i] = st[i] ^ st[i + 5] ^ st[i + 10] ^ st[i + 15] ^ st[i + 20]; |
| 81 | 82 | ||
| 82 | for (i = 0; i < 5; i++) { | 83 | for (i = 0; i < 5; i++) { |
| 83 | t = bc[(i + 4) % 5] ^ ROTL64(bc[(i + 1) % 5], 1); | 84 | t = bc[(i + 4) % 5] ^ ROTL64(bc[(i + 1) % 5], 1); |
| 84 | for (j = 0; j < 25; j += 5) | 85 | for (j = 0; j < 25; j += 5) |
| 85 | st[j + i] ^= t; | 86 | st[j + i] ^= t; |
| 86 | } | 87 | } |
| 87 | 88 | ||
| 88 | // Rho Pi | 89 | // Rho Pi |
| 89 | t = st[1]; | 90 | t = st[1]; |
| 90 | for (i = 0; i < 24; i++) { | 91 | for (i = 0; i < 24; i++) { |
| 91 | j = keccakf_piln[i]; | 92 | j = keccakf_piln[i]; |
| 92 | bc[0] = st[j]; | 93 | bc[0] = st[j]; |
| 93 | st[j] = ROTL64(t, keccakf_rotc[i]); | 94 | st[j] = ROTL64(t, keccakf_rotc[i]); |
| 94 | t = bc[0]; | 95 | t = bc[0]; |
| 95 | } | 96 | } |
| 96 | 97 | ||
| 97 | // Chi | 98 | // Chi |
| 98 | for (j = 0; j < 25; j += 5) { | 99 | for (j = 0; j < 25; j += 5) { |
| 99 | for (i = 0; i < 5; i++) | 100 | for (i = 0; i < 5; i++) |
| 100 | bc[i] = st[j + i]; | 101 | bc[i] = st[j + i]; |
| 101 | for (i = 0; i < 5; i++) | 102 | for (i = 0; i < 5; i++) |
| 102 | st[j + i] ^= (~bc[(i + 1) % 5]) & bc[(i + 2) % 5]; | 103 | st[j + i] ^= (~bc[(i + 1) % 5]) & bc[(i + 2) % 5]; |
| 103 | } | 104 | } |
| 104 | 105 | ||
| 105 | // Iota | 106 | // Iota |
| 106 | st[0] ^= keccakf_rndc[r]; | 107 | st[0] ^= keccakf_rndc[r]; |
| 107 | } | 108 | } |
| 108 | 109 | ||
| 109 | #if __BYTE_ORDER__ != __ORDER_LITTLE_ENDIAN__ | 110 | #if __BYTE_ORDER__ != __ORDER_LITTLE_ENDIAN__ |
| 110 | // endianess conversion. this is redundant on little-endian targets | 111 | // endianess conversion. this is redundant on little-endian targets |
| 111 | for (i = 0; i < 25; i++) { | 112 | for (i = 0; i < 25; i++) { |
| 112 | v = (uint8_t *) &st[i]; | 113 | v = (uint8_t *) &st[i]; |
| 113 | t = st[i]; | 114 | t = st[i]; |
| 114 | v[0] = t & 0xFF; | 115 | v[0] = t & 0xFF; |
| 115 | v[1] = (t >> 8) & 0xFF; | 116 | v[1] = (t >> 8) & 0xFF; |
| 116 | v[2] = (t >> 16) & 0xFF; | 117 | v[2] = (t >> 16) & 0xFF; |
| 117 | v[3] = (t >> 24) & 0xFF; | 118 | v[3] = (t >> 24) & 0xFF; |
| 118 | v[4] = (t >> 32) & 0xFF; | 119 | v[4] = (t >> 32) & 0xFF; |
| 119 | v[5] = (t >> 40) & 0xFF; | 120 | v[5] = (t >> 40) & 0xFF; |
| 120 | v[6] = (t >> 48) & 0xFF; | 121 | v[6] = (t >> 48) & 0xFF; |
| 121 | v[7] = (t >> 56) & 0xFF; | 122 | v[7] = (t >> 56) & 0xFF; |
| 122 | } | 123 | } |
| 123 | #endif | 124 | #endif |
| 124 | } | 125 | } |
| 125 | 126 | ||
| 126 | // Initialize the context for SHA3 | 127 | // Initialize the context for SHA3 |
| 127 | 128 | ||
| 128 | int sha3_init(sha3_ctx_t *c, int mdlen) | 129 | int |
| 130 | sha3_init(sha3_ctx_t *c, int mdlen) | ||
| 129 | { | 131 | { |
| 130 | int i; | 132 | int i; |
| 131 | 133 | ||
| 132 | for (i = 0; i < 25; i++) | 134 | for (i = 0; i < 25; i++) |
| 133 | c->st.q[i] = 0; | 135 | c->st.q[i] = 0; |
| 134 | c->mdlen = mdlen; | 136 | c->mdlen = mdlen; |
| 135 | c->rsiz = 200 - 2 * mdlen; | 137 | c->rsiz = 200 - 2 * mdlen; |
| 136 | c->pt = 0; | 138 | c->pt = 0; |
| 137 | 139 | ||
| 138 | return 1; | 140 | return 1; |
| 139 | } | 141 | } |
| 140 | 142 | ||
| 141 | // update state with more data | 143 | // update state with more data |
| 142 | 144 | ||
| 143 | int sha3_update(sha3_ctx_t *c, const void *data, size_t len) | 145 | int |
| 146 | sha3_update(sha3_ctx_t *c, const void *data, size_t len) | ||
| 144 | { | 147 | { |
| 145 | size_t i; | 148 | size_t i; |
| 146 | int j; | 149 | int j; |
| 147 | 150 | ||
| 148 | j = c->pt; | 151 | j = c->pt; |
| 149 | for (i = 0; i < len; i++) { | 152 | for (i = 0; i < len; i++) { |
| 150 | c->st.b[j++] ^= ((const uint8_t *) data)[i]; | 153 | c->st.b[j++] ^= ((const uint8_t *) data)[i]; |
| 151 | if (j >= c->rsiz) { | 154 | if (j >= c->rsiz) { |
| 152 | sha3_keccakf(c->st.q); | 155 | sha3_keccakf(c->st.q); |
| 153 | j = 0; | 156 | j = 0; |
| 154 | } | 157 | } |
| 155 | } | 158 | } |
| 156 | c->pt = j; | 159 | c->pt = j; |
| 157 | 160 | ||
| 158 | return 1; | 161 | return 1; |
| 159 | } | 162 | } |
| 160 | 163 | ||
| 161 | // finalize and output a hash | 164 | // finalize and output a hash |
| 162 | 165 | ||
| 163 | int sha3_final(void *md, sha3_ctx_t *c) | 166 | int |
| 167 | sha3_final(void *md, sha3_ctx_t *c) | ||
| 164 | { | 168 | { |
| 165 | int i; | 169 | int i; |
| 166 | 170 | ||
| 167 | c->st.b[c->pt] ^= 0x06; | 171 | c->st.b[c->pt] ^= 0x06; |
| 168 | c->st.b[c->rsiz - 1] ^= 0x80; | 172 | c->st.b[c->rsiz - 1] ^= 0x80; |
| 169 | sha3_keccakf(c->st.q); | 173 | sha3_keccakf(c->st.q); |
| 170 | 174 | ||
| 171 | for (i = 0; i < c->mdlen; i++) { | 175 | for (i = 0; i < c->mdlen; i++) { |
| 172 | ((uint8_t *) md)[i] = c->st.b[i]; | 176 | ((uint8_t *) md)[i] = c->st.b[i]; |
| 173 | } | 177 | } |
| 174 | 178 | ||
| 175 | return 1; | 179 | return 1; |
| 176 | } | 180 | } |
| 177 | 181 | ||
| 178 | // compute a SHA-3 hash (md) of given byte length from "in" | 182 | // compute a SHA-3 hash (md) of given byte length from "in" |
| 179 | 183 | ||
| 180 | void *sha3(const void *in, size_t inlen, void *md, int mdlen) | 184 | void * |
| 185 | sha3(const void *in, size_t inlen, void *md, int mdlen) | ||
| 181 | { | 186 | { |
| 182 | sha3_ctx_t sha3; | 187 | sha3_ctx_t sha3; |
| 183 | 188 | ||
| 184 | sha3_init(&sha3, mdlen); | 189 | sha3_init(&sha3, mdlen); |
| 185 | sha3_update(&sha3, in, inlen); | 190 | sha3_update(&sha3, in, inlen); |
| 186 | sha3_final(md, &sha3); | 191 | sha3_final(md, &sha3); |
| 187 | 192 | ||
| 188 | return md; | 193 | return md; |
| 189 | } | 194 | } |
| 190 | 195 | ||
| 191 | // SHAKE128 and SHAKE256 extensible-output functionality | 196 | // SHAKE128 and SHAKE256 extensible-output functionality |
| 192 | 197 | ||
| 193 | void shake_xof(sha3_ctx_t *c) | 198 | void |
| 199 | shake_xof(sha3_ctx_t *c) | ||
| 194 | { | 200 | { |
| 195 | c->st.b[c->pt] ^= 0x1F; | 201 | c->st.b[c->pt] ^= 0x1F; |
| 196 | c->st.b[c->rsiz - 1] ^= 0x80; | 202 | c->st.b[c->rsiz - 1] ^= 0x80; |
| 197 | sha3_keccakf(c->st.q); | 203 | sha3_keccakf(c->st.q); |
| 198 | c->pt = 0; | 204 | c->pt = 0; |
| 199 | } | 205 | } |
| 200 | 206 | ||
| 201 | void shake_out(sha3_ctx_t *c, void *out, size_t len) | 207 | void |
| 208 | shake_out(sha3_ctx_t *c, void *out, size_t len) | ||
| 202 | { | 209 | { |
| 203 | size_t i; | 210 | size_t i; |
| 204 | int j; | 211 | int j; |
| 205 | 212 | ||
| 206 | j = c->pt; | 213 | j = c->pt; |
| 207 | for (i = 0; i < len; i++) { | 214 | for (i = 0; i < len; i++) { |
| 208 | if (j >= c->rsiz) { | 215 | if (j >= c->rsiz) { |
| 209 | sha3_keccakf(c->st.q); | 216 | sha3_keccakf(c->st.q); |
| 210 | j = 0; | 217 | j = 0; |
| 211 | } | 218 | } |
| 212 | ((uint8_t *) out)[i] = c->st.b[j++]; | 219 | ((uint8_t *) out)[i] = c->st.b[j++]; |
| 213 | } | 220 | } |
| 214 | c->pt = j; | 221 | c->pt = j; |
| 215 | } | 222 | } |
| 216 | |||
diff --git a/src/lib/libcrypto/sha/sha3_internal.h b/src/lib/libcrypto/sha/sha3_internal.h index 1c63b979ef..1b4c6675ad 100644 --- a/src/lib/libcrypto/sha/sha3_internal.h +++ b/src/lib/libcrypto/sha/sha3_internal.h | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: sha3_internal.h,v 1.2 2023/04/15 17:59:50 jsing Exp $ */ | 1 | /* $OpenBSD: sha3_internal.h,v 1.3 2023/04/15 18:07:44 jsing Exp $ */ |
| 2 | /* | 2 | /* |
| 3 | * The MIT License (MIT) | 3 | * The MIT License (MIT) |
| 4 | * | 4 | * |
| @@ -42,20 +42,20 @@ | |||
| 42 | 42 | ||
| 43 | // state context | 43 | // state context |
| 44 | typedef struct { | 44 | typedef struct { |
| 45 | union { // state: | 45 | union { // state: |
| 46 | uint8_t b[200]; // 8-bit bytes | 46 | uint8_t b[200]; // 8-bit bytes |
| 47 | uint64_t q[25]; // 64-bit words | 47 | uint64_t q[25]; // 64-bit words |
| 48 | } st; | 48 | } st; |
| 49 | int pt, rsiz, mdlen; // these don't overflow | 49 | int pt, rsiz, mdlen; // these don't overflow |
| 50 | } sha3_ctx_t; | 50 | } sha3_ctx_t; |
| 51 | 51 | ||
| 52 | // Compression function. | 52 | // Compression function. |
| 53 | void sha3_keccakf(uint64_t st[25]); | 53 | void sha3_keccakf(uint64_t st[25]); |
| 54 | 54 | ||
| 55 | // OpenSSL - like interfece | 55 | // OpenSSL - like interfece |
| 56 | int sha3_init(sha3_ctx_t *c, int mdlen); // mdlen = hash output in bytes | 56 | int sha3_init(sha3_ctx_t *c, int mdlen); // mdlen = hash output in bytes |
| 57 | int sha3_update(sha3_ctx_t *c, const void *data, size_t len); | 57 | int sha3_update(sha3_ctx_t *c, const void *data, size_t len); |
| 58 | int sha3_final(void *md, sha3_ctx_t *c); // digest goes to md | 58 | int sha3_final(void *md, sha3_ctx_t *c); // digest goes to md |
| 59 | 59 | ||
| 60 | // compute a sha3 hash (md) of given byte length from "in" | 60 | // compute a sha3 hash (md) of given byte length from "in" |
| 61 | void *sha3(const void *in, size_t inlen, void *md, int mdlen); | 61 | void *sha3(const void *in, size_t inlen, void *md, int mdlen); |
