If a system wants to generate UUIDs but has no IEE 802 compliant network card or other source of IEEE 802 addresses, then this section describes how to generate one.
The ideal solution is to obtain a 47 bit cryptographic quality random number, and use it as the low 47 bits of the node ID, with the most significant bit of the first octet of the node ID set to 1. This bit is the unicast/multicast bit, which will never be set in IEEE 802 addresses obtained from network cards; hence, there can never be a conflict between UUIDs generated by machines with and without network cards.
If a system does not have a primitive to generate cryptographic quality random numbers, then in most systems there are usually a fairly large number of sources of randomness available from which one can be generated. Such sources are system specific, but often include:
(Note that it precisely the above kinds of sources of randomness that are used to seed cryptographic quality random number generators on systems without special hardware for their construction.)
In addition, items such as the computer&rsquo’s name and the name of the operating system, while not strictly speaking random, will help differentiate the results from those obtained by other systems.
The exact algorithm to generate a node ID using these data is system specific, because both the data available and the functions to obtain them are often very system specific. However, assuming that one can concatenate all the values from the randomness sources into a buffer, and that a cryptographic hash function such as MD5 [3] is available, the following code will compute a node ID:
#include <md5.h>
#define HASHLEN 16
void GenNodeID(
unsigned char * pDataBuf,// concatenated "randomness values"
long cData,// size of randomness values
unsigned char NodeID[6]// node ID
)
{
int i, j, k;
unsigned char Hash[HASHLEN];
MD_CTX context;
MDInit (&context);
MDUpdate (&context, pDataBuf, cData);
MDFinal (Hash, &context);
for (j = 0; j<6; j++) NodeId[j]=0;
for (i = 0,j = 0; i < HASHLEN; i++) {
NodeID[j++] ^= Hash[i];
if (j == 6) j = 0;
};
NodeID[0] |= 0x80;// set the multicast bit
};
Other hash functions, such as SHA-1 [4], can also be used (in which case HASHLEN will be 20). The only requirement is that the result be suitably random – in the sense that the outputs from a set uniformly distributed inputs are themselves uniformly distributed, and that a single bit change in the input can be expected to cause half of the output bits to change.