1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
|
/* See LICENSE file for copyright and license details. */
#include "common.h"
#ifndef TEST
size_t
librecrypt_settings_prefix(const char *hash, size_t *hashsize_out)
{
size_t i, len, ret = 0u;
size_t last_offset = 0u;
const struct algorithm *algo;
uintmax_t hashsize;
/* Find last algorithm, and beginning of result */
for (i = 0u; hash[i]; i++) {
if (hash[i] == LIBRECRYPT_HASH_COMPOSITION_DELIMITER)
ret = i + 1u;
else if (hash[i] == LIBRECRYPT_ALGORITHM_LINK_DELIMITER)
last_offset = ret = i + 1u;
}
/* and get `strlen(hash)` */
len = i;
/* Special case for bsdicrypt */
if (ret == last_offset && ret < len && hash[ret] == '_')
ret += 1u;
/* Return if hash size is not required */
if (!hashsize_out)
goto out;
/* Return 0 as hash size if default is specified */
if (ret == i)
goto zero;
/* Return 0 as hash size if algorithm cannot be identified or has fixed hash size */
algo = librecrypt_find_first_algorithm_(&hash[last_offset], len - last_offset);
if (!algo || !algo->flexible_hash_size)
goto zero;
/* Get the hash size */
if (!librecrypt_check_settings_(&hash[ret], len - ret, "%^b",
&hashsize, (uintmax_t)1u, (uintmax_t)SIZE_MAX,
algo->decoding_lut, algo->pad, algo->strict_pad))
goto zero;
*hashsize_out = (size_t)hashsize;
goto out;
zero:
*hashsize_out = 0u;
out:
return ret;
}
#else
#define CHECK_NULL(PREFIX, SUFFIX)\
do {\
EXPECT(librecrypt_settings_prefix(PREFIX SUFFIX, NULL) == sizeof(PREFIX) - 1u);\
EXPECT(librecrypt_settings_prefix(PREFIX, NULL) == sizeof(PREFIX) - 1u); \
} while (0)
#if 0
#define CHECK_ASTERISK(PREFIX, SUFFIX, HASH)\
do {\
size_t hashsize = 99999u;\
EXPECT(librecrypt_settings_prefix(PREFIX SUFFIX #HASH, &hashsize) == sizeof(PREFIX) - 1u);\
EXPECT(hashsize == HASH##u);\
} while (0)
#define CHECK_ZERO(PREFIX, SUFFIX)\
do {\
size_t hashsize = 99999u;\
EXPECT(librecrypt_settings_prefix(PREFIX SUFFIX, &hashsize) == sizeof(PREFIX) - 1u);\
EXPECT(hashsize == 0u);\
} while (0)
#define CHECK_HASHED(PREFIX, SUFFIX, HASH)\
do {\
size_t hashsize = 99999u;\
EXPECT(librecrypt_settings_prefix(PREFIX SUFFIX, &hashsize) == sizeof(PREFIX) - 1u);\
EXPECT(hashsize == HASH##u);\
} while (0)
#endif
int
main(void)
{
SET_UP_ALARM();
INIT_RESOURCE_TEST();
/* Simple cases */
CHECK_NULL("", "result");
CHECK_NULL(">", "double-des result");
CHECK_NULL("$", "x");
CHECK_NULL("y$", "x");
CHECK_NULL("y>", "x");
CHECK_NULL("a$b$c>d$e$", "x");
CHECK_NULL("a$b$c>", "x");
/* Discard asterisk-notation */
CHECK_NULL("", "*10");
CHECK_NULL(">", "*11");
CHECK_NULL("$", "*12");
CHECK_NULL("y$", "*13");
CHECK_NULL("y>", "*012");
CHECK_NULL("a$b$c>d$e$", "*1");
CHECK_NULL("a$b$c>", "*2");
CHECK_NULL("a$b$c>*10$", "*2");
/* Special case: bsdicrypt */
CHECK_NULL("_", "res");
CHECK_NULL("_", "");
CHECK_NULL("$x$*10>_", "_");
/* TODO test hash size output (requires algorithms) */
STOP_RESOURCE_TEST();
return 0;
}
#endif
|