diff options
Diffstat (limited to '')
-rw-r--r-- | libbb/hash_md5_sha.c | 146 |
1 files changed, 133 insertions, 13 deletions
diff --git a/libbb/hash_md5_sha.c b/libbb/hash_md5_sha.c index 75a61c32c..fd56d831b 100644 --- a/libbb/hash_md5_sha.c +++ b/libbb/hash_md5_sha.c | |||
@@ -11,7 +11,93 @@ | |||
11 | #define STR1(s) #s | 11 | #define STR1(s) #s |
12 | #define STR(s) STR1(s) | 12 | #define STR(s) STR1(s) |
13 | 13 | ||
14 | #define NEED_SHA512 (ENABLE_SHA512SUM || ENABLE_USE_BB_CRYPT_SHA) | 14 | #define NEED_SHA512 (ENABLE_SHA512SUM || ENABLE_SHA384SUM || ENABLE_USE_BB_CRYPT_SHA) |
15 | |||
16 | #if ENABLE_FEATURE_USE_CNG_API | ||
17 | # include <windows.h> | ||
18 | # include <bcrypt.h> | ||
19 | |||
20 | // these work on Windows >= 10 | ||
21 | # define BCRYPT_MD5_ALG_HANDLE ((BCRYPT_ALG_HANDLE) 0x00000021) | ||
22 | # define BCRYPT_SHA1_ALG_HANDLE ((BCRYPT_ALG_HANDLE) 0x00000031) | ||
23 | # define BCRYPT_SHA256_ALG_HANDLE ((BCRYPT_ALG_HANDLE) 0x00000041) | ||
24 | # define BCRYPT_SHA384_ALG_HANDLE ((BCRYPT_ALG_HANDLE) 0x00000051) | ||
25 | # define BCRYPT_SHA512_ALG_HANDLE ((BCRYPT_ALG_HANDLE) 0x00000061) | ||
26 | |||
27 | /* Initialize structure containing state of computation. | ||
28 | * (RFC 1321, 3.3: Step 3) | ||
29 | */ | ||
30 | |||
31 | static void generic_init(struct bcrypt_hash_ctx_t *ctx, BCRYPT_ALG_HANDLE alg_handle) { | ||
32 | DWORD hash_object_length = 0; | ||
33 | ULONG _unused; | ||
34 | NTSTATUS status; | ||
35 | |||
36 | status = BCryptGetProperty(alg_handle, BCRYPT_OBJECT_LENGTH, (PUCHAR)&hash_object_length, sizeof(DWORD), &_unused, 0); | ||
37 | mingw_die_if_error(status, "BCryptGetProperty"); | ||
38 | status = BCryptGetProperty(alg_handle, BCRYPT_HASH_LENGTH, (PUCHAR)&ctx->output_size, sizeof(DWORD), &_unused, 0); | ||
39 | mingw_die_if_error(status, "BCryptGetProperty"); | ||
40 | |||
41 | |||
42 | ctx->hash_obj = xmalloc(hash_object_length); | ||
43 | |||
44 | status = BCryptCreateHash(alg_handle, &ctx->handle, ctx->hash_obj, hash_object_length, NULL, 0, 0); | ||
45 | mingw_die_if_error(status, "BCryptCreateHash"); | ||
46 | } | ||
47 | |||
48 | void FAST_FUNC md5_begin(md5_ctx_t *ctx) | ||
49 | { | ||
50 | generic_init(ctx, BCRYPT_MD5_ALG_HANDLE); | ||
51 | } | ||
52 | |||
53 | void FAST_FUNC sha1_begin(sha1_ctx_t *ctx) | ||
54 | { | ||
55 | generic_init(ctx, BCRYPT_SHA1_ALG_HANDLE); | ||
56 | } | ||
57 | |||
58 | /* Initialize structure containing state of computation. | ||
59 | (FIPS 180-2:5.3.2) */ | ||
60 | void FAST_FUNC sha256_begin(sha256_ctx_t *ctx) | ||
61 | { | ||
62 | generic_init(ctx, BCRYPT_SHA256_ALG_HANDLE); | ||
63 | } | ||
64 | |||
65 | #if ENABLE_SHA384SUM | ||
66 | /* Initialize structure containing state of computation. | ||
67 | (FIPS 180-2:5.3.3) */ | ||
68 | void FAST_FUNC sha384_begin(sha384_ctx_t *ctx) | ||
69 | { | ||
70 | generic_init(ctx, BCRYPT_SHA384_ALG_HANDLE); | ||
71 | } | ||
72 | #endif /* ENABLE_SHA384SUM */ | ||
73 | |||
74 | #if NEED_SHA512 | ||
75 | /* Initialize structure containing state of computation. | ||
76 | (FIPS 180-2:5.3.4) */ | ||
77 | void FAST_FUNC sha512_begin(sha512_ctx_t *ctx) | ||
78 | { | ||
79 | generic_init(ctx, BCRYPT_SHA512_ALG_HANDLE); | ||
80 | } | ||
81 | #endif /* NEED_SHA512 */ | ||
82 | |||
83 | void FAST_FUNC generic_hash(struct bcrypt_hash_ctx_t *ctx, const void *buffer, size_t len) | ||
84 | { | ||
85 | /* | ||
86 | for perf, no error checking here | ||
87 | */ | ||
88 | /*NTSTATUS status = */ BCryptHashData(ctx->handle, (const PUCHAR)buffer, len, 0); | ||
89 | // mingw_die_if_error(status, "BCryptHashData"); | ||
90 | } | ||
91 | |||
92 | unsigned FAST_FUNC generic_end(struct bcrypt_hash_ctx_t *ctx, void *resbuf) | ||
93 | { | ||
94 | NTSTATUS status = BCryptFinishHash(ctx->handle, resbuf, ctx->output_size, 0); | ||
95 | mingw_die_if_error(status, "BCryptFinishHash"); | ||
96 | BCryptDestroyHash(ctx->handle); | ||
97 | free(ctx->hash_obj); | ||
98 | return ctx->output_size; | ||
99 | } | ||
100 | #endif /* !ENABLE_FEATURE_USE_CNG_API */ | ||
15 | 101 | ||
16 | #if ENABLE_SHA1_HWACCEL || ENABLE_SHA256_HWACCEL | 102 | #if ENABLE_SHA1_HWACCEL || ENABLE_SHA256_HWACCEL |
17 | # if defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__)) | 103 | # if defined(__GNUC__) && (defined(__i386__) || defined(__x86_64__)) |
@@ -80,6 +166,7 @@ static ALWAYS_INLINE uint64_t rotl64(uint64_t x, unsigned n) | |||
80 | return (x << n) | (x >> (64 - n)); | 166 | return (x << n) | (x >> (64 - n)); |
81 | } | 167 | } |
82 | 168 | ||
169 | #if !ENABLE_FEATURE_USE_CNG_API | ||
83 | /* Process the remaining bytes in the buffer */ | 170 | /* Process the remaining bytes in the buffer */ |
84 | static void FAST_FUNC common64_end(md5_ctx_t *ctx, int swap_needed) | 171 | static void FAST_FUNC common64_end(md5_ctx_t *ctx, int swap_needed) |
85 | { | 172 | { |
@@ -1032,7 +1119,7 @@ static const sha_K_int sha_K[] ALIGN8 = { | |||
1032 | K(0x84c87814a1f0ab72ULL), K(0x8cc702081a6439ecULL), | 1119 | K(0x84c87814a1f0ab72ULL), K(0x8cc702081a6439ecULL), |
1033 | K(0x90befffa23631e28ULL), K(0xa4506cebde82bde9ULL), | 1120 | K(0x90befffa23631e28ULL), K(0xa4506cebde82bde9ULL), |
1034 | K(0xbef9a3f7b2c67915ULL), K(0xc67178f2e372532bULL), | 1121 | K(0xbef9a3f7b2c67915ULL), K(0xc67178f2e372532bULL), |
1035 | #if NEED_SHA512 /* [64]+ are used for sha512 only */ | 1122 | #if NEED_SHA512 /* [64]+ are used for sha384 and sha512 only */ |
1036 | K(0xca273eceea26619cULL), K(0xd186b8c721c0c207ULL), | 1123 | K(0xca273eceea26619cULL), K(0xd186b8c721c0c207ULL), |
1037 | K(0xeada7dd6cde0eb1eULL), K(0xf57d4f7fee6ed178ULL), | 1124 | K(0xeada7dd6cde0eb1eULL), K(0xf57d4f7fee6ed178ULL), |
1038 | K(0x06f067aa72176fbaULL), K(0x0a637dc5a2c898a6ULL), | 1125 | K(0x06f067aa72176fbaULL), K(0x0a637dc5a2c898a6ULL), |
@@ -1229,11 +1316,20 @@ static const uint32_t init512_lo[] ALIGN4 = { | |||
1229 | 0x137e2179, | 1316 | 0x137e2179, |
1230 | }; | 1317 | }; |
1231 | #endif /* NEED_SHA512 */ | 1318 | #endif /* NEED_SHA512 */ |
1232 | 1319 | #if ENABLE_SHA384SUM | |
1233 | // Note: SHA-384 is identical to SHA-512, except that initial hash values are | 1320 | static const uint64_t init384[] ALIGN8 = { |
1234 | // 0xcbbb9d5dc1059ed8, 0x629a292a367cd507, 0x9159015a3070dd17, 0x152fecd8f70e5939, | 1321 | 0, |
1235 | // 0x67332667ffc00b31, 0x8eb44a8768581511, 0xdb0c2e0d64f98fa7, 0x47b5481dbefa4fa4, | 1322 | 0, |
1236 | // and the output is constructed by omitting last two 64-bit words of it. | 1323 | 0xcbbb9d5dc1059ed8, |
1324 | 0x629a292a367cd507, | ||
1325 | 0x9159015a3070dd17, | ||
1326 | 0x152fecd8f70e5939, | ||
1327 | 0x67332667ffc00b31, | ||
1328 | 0x8eb44a8768581511, | ||
1329 | 0xdb0c2e0d64f98fa7, | ||
1330 | 0x47b5481dbefa4fa4, | ||
1331 | }; | ||
1332 | #endif | ||
1237 | 1333 | ||
1238 | /* Initialize structure containing state of computation. | 1334 | /* Initialize structure containing state of computation. |
1239 | (FIPS 180-2:5.3.2) */ | 1335 | (FIPS 180-2:5.3.2) */ |
@@ -1255,9 +1351,19 @@ void FAST_FUNC sha256_begin(sha256_ctx_t *ctx) | |||
1255 | #endif | 1351 | #endif |
1256 | } | 1352 | } |
1257 | 1353 | ||
1258 | #if NEED_SHA512 | 1354 | #if ENABLE_SHA384SUM |
1259 | /* Initialize structure containing state of computation. | 1355 | /* Initialize structure containing state of computation. |
1260 | (FIPS 180-2:5.3.3) */ | 1356 | (FIPS 180-2:5.3.3) */ |
1357 | void FAST_FUNC sha384_begin(sha512_ctx_t *ctx) | ||
1358 | { | ||
1359 | memcpy(&ctx->total64, init384, sizeof(init384)); | ||
1360 | /*ctx->total64[0] = ctx->total64[1] = 0; - already done */ | ||
1361 | } | ||
1362 | #endif | ||
1363 | |||
1364 | #if NEED_SHA512 | ||
1365 | /* Initialize structure containing state of computation. | ||
1366 | (FIPS 180-2:5.3.4) */ | ||
1261 | void FAST_FUNC sha512_begin(sha512_ctx_t *ctx) | 1367 | void FAST_FUNC sha512_begin(sha512_ctx_t *ctx) |
1262 | { | 1368 | { |
1263 | int i; | 1369 | int i; |
@@ -1332,7 +1438,7 @@ unsigned FAST_FUNC sha1_end(sha1_ctx_t *ctx, void *resbuf) | |||
1332 | } | 1438 | } |
1333 | 1439 | ||
1334 | #if NEED_SHA512 | 1440 | #if NEED_SHA512 |
1335 | unsigned FAST_FUNC sha512_end(sha512_ctx_t *ctx, void *resbuf) | 1441 | static unsigned FAST_FUNC sha512384_end(sha512_ctx_t *ctx, void *resbuf, unsigned outsize) |
1336 | { | 1442 | { |
1337 | unsigned bufpos = ctx->total64[0] & 127; | 1443 | unsigned bufpos = ctx->total64[0] & 127; |
1338 | 1444 | ||
@@ -1363,11 +1469,22 @@ unsigned FAST_FUNC sha512_end(sha512_ctx_t *ctx, void *resbuf) | |||
1363 | for (i = 0; i < ARRAY_SIZE(ctx->hash); ++i) | 1469 | for (i = 0; i < ARRAY_SIZE(ctx->hash); ++i) |
1364 | ctx->hash[i] = SWAP_BE64(ctx->hash[i]); | 1470 | ctx->hash[i] = SWAP_BE64(ctx->hash[i]); |
1365 | } | 1471 | } |
1366 | memcpy(resbuf, ctx->hash, sizeof(ctx->hash)); | 1472 | memcpy(resbuf, ctx->hash, outsize); |
1367 | return sizeof(ctx->hash); | 1473 | return outsize; |
1474 | } | ||
1475 | unsigned FAST_FUNC sha512_end(sha384_ctx_t *ctx, void *resbuf) | ||
1476 | { | ||
1477 | return sha512384_end(ctx, resbuf, SHA512_OUTSIZE); | ||
1368 | } | 1478 | } |
1369 | #endif /* NEED_SHA512 */ | 1479 | #endif /* NEED_SHA512 */ |
1370 | 1480 | ||
1481 | #if ENABLE_SHA384SUM | ||
1482 | unsigned FAST_FUNC sha384_end(sha384_ctx_t *ctx, void *resbuf) | ||
1483 | { | ||
1484 | return sha512384_end(ctx, resbuf, SHA384_OUTSIZE); | ||
1485 | } | ||
1486 | #endif | ||
1487 | #endif /* !ENABLE_FEATURE_USE_CNG_API */ | ||
1371 | 1488 | ||
1372 | /* | 1489 | /* |
1373 | * The Keccak sponge function, designed by Guido Bertoni, Joan Daemen, | 1490 | * The Keccak sponge function, designed by Guido Bertoni, Joan Daemen, |
@@ -1904,6 +2021,8 @@ void FAST_FUNC sha3_hash(sha3_ctx_t *ctx, const void *buffer, size_t len) | |||
1904 | 2021 | ||
1905 | unsigned FAST_FUNC sha3_end(sha3_ctx_t *ctx, void *resbuf) | 2022 | unsigned FAST_FUNC sha3_end(sha3_ctx_t *ctx, void *resbuf) |
1906 | { | 2023 | { |
2024 | unsigned hash_len; | ||
2025 | |||
1907 | /* Padding */ | 2026 | /* Padding */ |
1908 | uint8_t *buf = (uint8_t*)ctx->state; | 2027 | uint8_t *buf = (uint8_t*)ctx->state; |
1909 | /* | 2028 | /* |
@@ -1926,6 +2045,7 @@ unsigned FAST_FUNC sha3_end(sha3_ctx_t *ctx, void *resbuf) | |||
1926 | sha3_process_block72(ctx->state); | 2045 | sha3_process_block72(ctx->state); |
1927 | 2046 | ||
1928 | /* Output */ | 2047 | /* Output */ |
1929 | memcpy(resbuf, ctx->state, 64); | 2048 | hash_len = (1600/8 - ctx->input_block_bytes) / 2; |
1930 | return 64; | 2049 | memcpy(resbuf, ctx->state, hash_len); |
2050 | return hash_len; | ||
1931 | } | 2051 | } |