diff options
author | Christian Grothoff <christian@grothoff.org> | 2021-01-28 22:28:01 +0100 |
---|---|---|
committer | Christian Grothoff <christian@grothoff.org> | 2021-01-28 22:28:01 +0100 |
commit | a2169368bbd92b77636e39b5cfe864a1236b083b (patch) | |
tree | 65da98ffc353e87a75e7e65877f3a04c897b18b4 /src/util | |
parent | 2741db1300fddb17e39373fb9d649b7022ed81d3 (diff) | |
download | gnunet-a2169368bbd92b77636e39b5cfe864a1236b083b.tar.gz gnunet-a2169368bbd92b77636e39b5cfe864a1236b083b.zip |
implement #6716
Diffstat (limited to 'src/util')
-rw-r--r-- | src/util/crypto_random.c | 44 | ||||
-rw-r--r-- | src/util/test_crypto_random.c | 3 |
2 files changed, 43 insertions, 4 deletions
diff --git a/src/util/crypto_random.c b/src/util/crypto_random.c index ffcabd0df..0c5d6fe7e 100644 --- a/src/util/crypto_random.c +++ b/src/util/crypto_random.c | |||
@@ -26,6 +26,7 @@ | |||
26 | */ | 26 | */ |
27 | #include "platform.h" | 27 | #include "platform.h" |
28 | #include "gnunet_crypto_lib.h" | 28 | #include "gnunet_crypto_lib.h" |
29 | #include "gnunet_time_lib.h" | ||
29 | #include <gcrypt.h> | 30 | #include <gcrypt.h> |
30 | 31 | ||
31 | #define LOG(kind, ...) GNUNET_log_from (kind, "util-crypto-random", __VA_ARGS__) | 32 | #define LOG(kind, ...) GNUNET_log_from (kind, "util-crypto-random", __VA_ARGS__) |
@@ -80,7 +81,7 @@ glibc_weak_rand32 () | |||
80 | * @return number between 0 and 1. | 81 | * @return number between 0 and 1. |
81 | */ | 82 | */ |
82 | static double | 83 | static double |
83 | get_weak_random () | 84 | get_weak_random (void) |
84 | { | 85 | { |
85 | return((double) random () / RAND_MAX); | 86 | return((double) random () / RAND_MAX); |
86 | } | 87 | } |
@@ -176,7 +177,8 @@ GNUNET_CRYPTO_random_block (enum GNUNET_CRYPTO_Quality mode, | |||
176 | * @return a random value in the interval [0,i[. | 177 | * @return a random value in the interval [0,i[. |
177 | */ | 178 | */ |
178 | uint32_t | 179 | uint32_t |
179 | GNUNET_CRYPTO_random_u32 (enum GNUNET_CRYPTO_Quality mode, uint32_t i) | 180 | GNUNET_CRYPTO_random_u32 (enum GNUNET_CRYPTO_Quality mode, |
181 | uint32_t i) | ||
180 | { | 182 | { |
181 | #ifdef gcry_fast_random_poll | 183 | #ifdef gcry_fast_random_poll |
182 | static unsigned int invokeCount; | 184 | static unsigned int invokeCount; |
@@ -235,7 +237,8 @@ GNUNET_CRYPTO_random_u32 (enum GNUNET_CRYPTO_Quality mode, uint32_t i) | |||
235 | * @return the permutation array (allocated from heap) | 237 | * @return the permutation array (allocated from heap) |
236 | */ | 238 | */ |
237 | unsigned int * | 239 | unsigned int * |
238 | GNUNET_CRYPTO_random_permute (enum GNUNET_CRYPTO_Quality mode, unsigned int n) | 240 | GNUNET_CRYPTO_random_permute (enum GNUNET_CRYPTO_Quality mode, |
241 | unsigned int n) | ||
239 | { | 242 | { |
240 | unsigned int *ret; | 243 | unsigned int *ret; |
241 | unsigned int i; | 244 | unsigned int i; |
@@ -265,7 +268,8 @@ GNUNET_CRYPTO_random_permute (enum GNUNET_CRYPTO_Quality mode, unsigned int n) | |||
265 | * @return random 64-bit number | 268 | * @return random 64-bit number |
266 | */ | 269 | */ |
267 | uint64_t | 270 | uint64_t |
268 | GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode, uint64_t max) | 271 | GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode, |
272 | uint64_t max) | ||
269 | { | 273 | { |
270 | uint64_t ret; | 274 | uint64_t ret; |
271 | uint64_t ul; | 275 | uint64_t ul; |
@@ -308,6 +312,38 @@ GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode, uint64_t max) | |||
308 | 312 | ||
309 | 313 | ||
310 | /** | 314 | /** |
315 | * @ingroup crypto | ||
316 | * Fill UUID with a timeflake pseudo-random value. Note that | ||
317 | * timeflakes use only 80 bits of randomness and 48 bits | ||
318 | * to encode a timestamp in milliseconds. So what we return | ||
319 | * here is not a completely random number. | ||
320 | * | ||
321 | * @param mode desired quality of the random number | ||
322 | * @param uuid the value to fill | ||
323 | */ | ||
324 | void | ||
325 | GNUNET_CRYPTO_random_timeflake (enum GNUNET_CRYPTO_Quality mode, | ||
326 | struct GNUNET_Uuid *uuid) | ||
327 | { | ||
328 | struct GNUNET_TIME_Absolute now; | ||
329 | uint64_t ms; | ||
330 | uint64_t be; | ||
331 | char *base; | ||
332 | |||
333 | GNUNET_CRYPTO_random_block (mode, | ||
334 | uuid, | ||
335 | sizeof (struct GNUNET_Uuid)); | ||
336 | now = GNUNET_TIME_absolute_get (); | ||
337 | ms = now.abs_value_us / GNUNET_TIME_UNIT_MILLISECONDS.rel_value_us; | ||
338 | be = GNUNET_htonll (ms); | ||
339 | base = (char *) &be; | ||
340 | memcpy (uuid, | ||
341 | base + 2, | ||
342 | sizeof (be) - 2); | ||
343 | } | ||
344 | |||
345 | |||
346 | /** | ||
311 | * Allocation wrapper for libgcrypt, used to avoid bad locking | 347 | * Allocation wrapper for libgcrypt, used to avoid bad locking |
312 | * strategy of libgcrypt implementation. | 348 | * strategy of libgcrypt implementation. |
313 | */ | 349 | */ |
diff --git a/src/util/test_crypto_random.c b/src/util/test_crypto_random.c index 5e159d949..b9cbbdf76 100644 --- a/src/util/test_crypto_random.c +++ b/src/util/test_crypto_random.c | |||
@@ -33,6 +33,7 @@ test (enum GNUNET_CRYPTO_Quality mode) | |||
33 | unsigned int *b2; | 33 | unsigned int *b2; |
34 | int i; | 34 | int i; |
35 | unsigned long long n; | 35 | unsigned long long n; |
36 | struct GNUNET_Uuid tf; | ||
36 | 37 | ||
37 | for (i = 0; i < 1024; i++) | 38 | for (i = 0; i < 1024; i++) |
38 | GNUNET_break (1024 > (buf[i] = GNUNET_CRYPTO_random_u32 (mode, 1024))); | 39 | GNUNET_break (1024 > (buf[i] = GNUNET_CRYPTO_random_u32 (mode, 1024))); |
@@ -53,6 +54,8 @@ test (enum GNUNET_CRYPTO_Quality mode) | |||
53 | 54 | ||
54 | for (n = 10; n < 1024LL * 1024LL * 1024LL; n *= 10) | 55 | for (n = 10; n < 1024LL * 1024LL * 1024LL; n *= 10) |
55 | GNUNET_break (n > GNUNET_CRYPTO_random_u64 (mode, n)); | 56 | GNUNET_break (n > GNUNET_CRYPTO_random_u64 (mode, n)); |
57 | GNUNET_CRYPTO_random_timeflake (mode, | ||
58 | &tf); | ||
56 | return 0; | 59 | return 0; |
57 | } | 60 | } |
58 | 61 | ||