From cad4a813cf4cfd0ebac48f0f0f21157a5a434a81 Mon Sep 17 00:00:00 2001 From: Dmitry Simonenko Date: Tue, 20 Jun 2017 18:33:32 +0300 Subject: [PATCH] odissey: convert id to hex instead of code table --- src/od_id.c | 55 ++++++++++++++++++++++++++--------------------------- src/od_id.h | 14 +++++++++++--- 2 files changed, 38 insertions(+), 31 deletions(-) diff --git a/src/od_id.c b/src/od_id.c index 3ddf8f92..262d178a 100644 --- a/src/od_id.c +++ b/src/od_id.c @@ -30,9 +30,9 @@ #include "od_macro.h" #include "od_pid.h" +#include "od_id.h" #include "od_syslog.h" #include "od_log.h" -#include "od_id.h" void od_idmgr_init(od_idmgr_t *mgr) { @@ -42,25 +42,23 @@ void od_idmgr_init(od_idmgr_t *mgr) mgr->pid = getpid(); } -int od_idmgr_seed(od_idmgr_t *mgr, od_log_t *log) +int od_idmgr_seed(od_idmgr_t *mgr) { struct timeval tv; gettimeofday(&tv, 0); srand((mgr->pid << 16) ^ mgr->uid ^ tv.tv_sec ^ tv.tv_usec); int i = 0; - for (; i < 8; i++) + for (; i < OD_ID_SEEDMAX; i++) mgr->seed[i] = (rand() >> 7) & 0xFF; int fd; fd = open("/dev/urandom", O_RDONLY); if (fd == -1) fd = open("/dev/random", O_RDONLY); - if (fd == -1) { - od_error(log, "id_manager", "failed to open /dev/{u}random"); + if (fd == -1) return -1; - } - char seed[8]; + char seed[OD_ID_SEEDMAX]; int seed_read = 0; - while (seed_read <= 8) { + while (seed_read <= OD_ID_SEEDMAX) { int rc; rc = read(fd, seed, sizeof(seed)); if (rc == -1) { @@ -71,19 +69,12 @@ int od_idmgr_seed(od_idmgr_t *mgr, od_log_t *log) } seed_read += rc; } - for (i = 0; i < 8; i++) + for (i = 0; i < OD_ID_SEEDMAX; i++) mgr->seed[i] ^= seed[i]; close(fd); return 0; } -static const uint8_t codetable[] = - "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwx"; -static const size_t codetable_size = sizeof(codetable); -static const size_t codetable_single_divisor = sizeof(codetable) * 1; -static const size_t codetable_double_divisor = sizeof(codetable) * 2; -static const size_t codetable_triple_divisor = sizeof(codetable) * 3; - void od_idmgr_generate(od_idmgr_t *mgr, od_id_t *id) { struct timespec t; @@ -111,19 +102,27 @@ void od_idmgr_generate(od_idmgr_t *mgr, od_id_t *id) month = current_time % 12; current_time /= 60; - uint64_t seq; + uint32_t seq; seq = ++mgr->seq; seq ^= t.tv_nsec; + seq ^= machine_self(); + seq ^= rand(); - uint8_t *seed = &id->id[0]; - seed[0] = mgr->seed[0] ^ codetable[second]; - seed[1] = mgr->seed[1] ^ codetable[minute]; - seed[2] = mgr->seed[2] ^ codetable[(hour + day + month) % codetable_size]; - seed[3] = mgr->seed[3] ^ codetable[(seq) % codetable_size]; - seed[4] = mgr->seed[4] ^ codetable[(seq / codetable_single_divisor) % codetable_size]; - seed[5] = mgr->seed[5] ^ codetable[(seq / codetable_double_divisor) % codetable_size]; - seed[6] = mgr->seed[6] ^ codetable[(seq / codetable_triple_divisor) % codetable_size]; - seed[7] = mgr->seed[7] ^ codetable[(uintptr_t)id % codetable_size]; - seed[8] = mgr->seed[8] ^ codetable[(mgr->pid + mgr->uid) % codetable_size]; - memcpy(mgr->seed, seed, 8); + mgr->seed[0] ^= seq ^ second; + mgr->seed[1] ^= seq ^ minute; + mgr->seed[2] ^= seq ^ (hour + day + month); + mgr->seed[3] ^= ((uint8_t*)&seq)[0] ^ ((uint8_t*)&seq)[1]; + mgr->seed[4] ^= ((uint8_t*)&seq)[2] ^ ((uint8_t*)&seq)[3]; + mgr->seed[5] ^= seq ^ (uintptr_t)id; + mgr->seed[6] ^= seq ^ (mgr->pid + mgr->uid); + mgr->seed[7] ^= seq; + + uint8_t *dest = &id->id[0]; + static const char *hex = "0123456789abcdef"; + int q, w; + for (q = 0, w = 0; q < OD_ID_SEEDMAX; q++) { + dest[w++] = hex[(mgr->seed[q] >> 4) & 0x0F]; + dest[w++] = hex[(mgr->seed[q] ) & 0x0F]; + } + assert(w == (OD_ID_SEEDMAX * 2)); } diff --git a/src/od_id.h b/src/od_id.h index 4a26b70c..a35cd9b6 100644 --- a/src/od_id.h +++ b/src/od_id.h @@ -10,21 +10,29 @@ typedef struct od_id od_id_t; typedef struct od_idmgr od_idmgr_t; +#define OD_ID_SEEDMAX 6 + struct od_id { - uint8_t id[8]; + uint8_t id[OD_ID_SEEDMAX * 2]; }; struct od_idmgr { uint64_t seq; - uint8_t seed[8]; + uint8_t seed[OD_ID_SEEDMAX]; pid_t pid; uid_t uid; }; void od_idmgr_init(od_idmgr_t*); -int od_idmgr_seed(od_idmgr_t*, od_log_t*); +int od_idmgr_seed(od_idmgr_t*); void od_idmgr_generate(od_idmgr_t*, od_id_t*); +static inline int +od_idmgr_cmp(od_id_t *a, od_id_t *b) +{ + return *(uint64_t*)a->id == *(uint64_t*)b->id; +} + #endif /* OD_ID_H */