LCOV - code coverage report
Current view: top level - common/utils - muuid.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 4 4 100.0 %
Date: 2021-10-27 03:06:47 Functions: 1 1 100.0 %

          Line data    Source code
       1             : /*
       2             :  * This Source Code Form is subject to the terms of the Mozilla Public
       3             :  * License, v. 2.0.  If a copy of the MPL was not distributed with this
       4             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       5             :  *
       6             :  * Copyright 1997 - July 2008 CWI, August 2008 - 2021 MonetDB B.V.
       7             :  */
       8             : 
       9             : /* NOTE: for this file to work correctly, the random number generator
      10             :  * must have been seeded (srand) with something like the current time */
      11             : 
      12             : #include "monetdb_config.h"
      13             : #include "muuid.h"
      14             : #include <string.h> /* strdup */
      15             : #ifdef HAVE_UUID_UUID_H
      16             : # include <uuid/uuid.h>
      17             : #endif
      18             : #if defined(HAVE_GETENTROPY) && defined(HAVE_SYS_RANDOM_H)
      19             : #include <sys/random.h>
      20             : #endif
      21             : 
      22             : #if !defined(HAVE_UUID) && !defined(HAVE_GETENTROPY) && defined(HAVE_RAND_S)
      23             : static inline bool
      24             : generate_uuid(char *out)
      25             : {
      26             :         union {
      27             :                 unsigned int randbuf[4];
      28             :                 unsigned char uuid[16];
      29             :         } u;
      30             :         for (int i = 0; i < 4; i++)
      31             :                 if (rand_s(&u.randbuf[i]) != 0)
      32             :                         return false;
      33             :         /* make sure this is a variant 1 UUID (RFC 4122/DCE 1.1) */
      34             :         u.uuid[8] = (u.uuid[8] & 0x3F) | 0x80;
      35             :         /* make sure this is version 4 (random UUID) */
      36             :         u.uuid[6] = (u.uuid[6] & 0x0F) | 0x40;
      37             :         snprintf(out, 37,
      38             :                          "%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-"
      39             :                          "%02x%02x%02x%02x%02x%02x",
      40             :                          u.uuid[0], u.uuid[1], u.uuid[2], u.uuid[3],
      41             :                          u.uuid[4], u.uuid[5], u.uuid[6], u.uuid[7],
      42             :                          u.uuid[8], u.uuid[9], u.uuid[10], u.uuid[11],
      43             :                          u.uuid[12], u.uuid[13], u.uuid[14], u.uuid[15]);
      44             :         return true;
      45             : }
      46             : #endif
      47             : 
      48             : /**
      49             :  * Shallow wrapper around uuid, that comes up with some random pseudo
      50             :  * uuid if uuid is not available
      51             :  */
      52             : char *
      53         331 : generateUUID(void)
      54             : {
      55             : #ifdef HAVE_UUID
      56             : # ifdef UUID_PRINTABLE_STRING_LENGTH
      57             :         /* Solaris */
      58             :         char out[UUID_PRINTABLE_STRING_LENGTH];
      59             : # else
      60             :         char out[37];
      61             : # endif
      62             :         uuid_t uuid;
      63         331 :         uuid_generate(uuid);
      64         331 :         uuid_unparse(uuid, out);
      65             : #else
      66             :         /* try to do some pseudo interesting stuff, and stash it in the
      67             :          * format of a UUID to at least return some uniform answer */
      68             :         char out[37];
      69             : #if defined(HAVE_GETENTROPY)
      70             :         unsigned char randbuf[16];
      71             :         if (getentropy(randbuf, 16) == 0) {
      72             :                 /* make sure this is a variant 1 UUID (RFC 4122/DCE 1.1) */
      73             :                 randbuf[8] = (randbuf[8] & 0x3F) | 0x80;
      74             :                 /* make sure this is version 4 (random UUID) */
      75             :                 randbuf[6] = (randbuf[6] & 0x0F) | 0x40;
      76             :                 snprintf(out, sizeof(out),
      77             :                          "%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-"
      78             :                          "%02x%02x%02x%02x%02x%02x",
      79             :                          randbuf[0], randbuf[1], randbuf[2], randbuf[3],
      80             :                          randbuf[4], randbuf[5], randbuf[6], randbuf[7],
      81             :                          randbuf[8], randbuf[9], randbuf[10], randbuf[11],
      82             :                          randbuf[12], randbuf[13], randbuf[14], randbuf[15]);
      83             :         } else
      84             : #elif defined(HAVE_RAND_S)
      85             :         if (!generate_uuid(out))
      86             : #endif
      87             :         {
      88             :                 /* generate something like this:
      89             :                  * cefa7a9c-1dd2-41b2-8350-880020adbeef
      90             :                  * ("%08x-%04x-%04x-%04x-%012x") */
      91             :                 snprintf(out, sizeof(out),
      92             :                          "%04x%04x-%04x-4%03x-8%03x-%04x%04x%04x",
      93             :                          (unsigned) rand() & 0xFFFF, (unsigned) rand() & 0xFFFF,
      94             :                          (unsigned) rand() & 0xFFFF, (unsigned) rand() & 0x0FFF,
      95             :                          (unsigned) rand() & 0x0FFF, (unsigned) rand() & 0xFFFF,
      96             :                          (unsigned) rand() & 0xFFFF, (unsigned) rand() & 0xFFFF);
      97             :         }
      98             : #endif
      99         331 :         return strdup(out);
     100             : }

Generated by: LCOV version 1.14