Generate (hopefully) decent DDSI2.2-compliant GUID
Signed-off-by: Erik Boasson <eb@ilities.com>
This commit is contained in:
parent
a632f80000
commit
87398bdc98
3 changed files with 42 additions and 18 deletions
|
@ -158,7 +158,7 @@ struct q_globals {
|
|||
|
||||
/* GUID to be used in next call to new_participant; also protected
|
||||
by privileged_pp_lock */
|
||||
struct nn_guid next_ppguid;
|
||||
struct nn_guid ppguid_base;
|
||||
|
||||
/* number of up, non-loopback, IPv4/IPv6 interfaces, the index of
|
||||
the selected/preferred one, and the discovered interfaces. */
|
||||
|
|
|
@ -701,18 +701,14 @@ dds_return_t new_participant_guid (const nn_guid_t *ppguid, struct q_globals *gv
|
|||
|
||||
dds_return_t new_participant (nn_guid_t *p_ppguid, struct q_globals *gv, unsigned flags, const nn_plist_t *plist)
|
||||
{
|
||||
nn_guid_t ppguid;
|
||||
|
||||
ddsrt_mutex_lock (&gv->privileged_pp_lock);
|
||||
ppguid = gv->next_ppguid;
|
||||
if (gv->next_ppguid.prefix.u[2]++ == ~0u)
|
||||
{
|
||||
ddsrt_mutex_unlock (&gv->privileged_pp_lock);
|
||||
return DDS_RETCODE_OUT_OF_RESOURCES;
|
||||
}
|
||||
ddsrt_mutex_unlock (&gv->privileged_pp_lock);
|
||||
*p_ppguid = ppguid;
|
||||
|
||||
union { uint64_t u64; uint32_t u32[2]; } u;
|
||||
u.u32[0] = gv->ppguid_base.prefix.u[1];
|
||||
u.u32[1] = gv->ppguid_base.prefix.u[2];
|
||||
u.u64 += ddsi_iid_gen ();
|
||||
p_ppguid->prefix.u[0] = gv->ppguid_base.prefix.u[0];
|
||||
p_ppguid->prefix.u[1] = u.u32[0];
|
||||
p_ppguid->prefix.u[2] = u.u32[1];
|
||||
p_ppguid->entityid.u = NN_ENTITYID_PARTICIPANT;
|
||||
return new_participant_guid (p_ppguid, gv, flags, plist);
|
||||
}
|
||||
|
||||
|
|
|
@ -1033,11 +1033,39 @@ int rtps_init (struct q_globals *gv)
|
|||
ddsrt_mutex_init (&gv->privileged_pp_lock);
|
||||
gv->privileged_pp = NULL;
|
||||
|
||||
/* Template PP guid -- protected by privileged_pp_lock for simplicity */
|
||||
gv->next_ppguid.prefix.u[0] = locator_to_hopefully_unique_uint32 (&gv->ownloc);
|
||||
gv->next_ppguid.prefix.u[1] = (unsigned) ddsrt_getpid ();
|
||||
gv->next_ppguid.prefix.u[2] = 1;
|
||||
gv->next_ppguid.entityid.u = NN_ENTITYID_PARTICIPANT;
|
||||
/* Base participant GUID. IID initialisation should be from a really good random
|
||||
generator and yield almost-unique numbers, and with a fallback of using process
|
||||
id, timestamp and a counter, so incorporating that should do a lot to construct
|
||||
a pseudo-random ID. (The assumption here is that feeding pseudo-random data in
|
||||
MD5 will not change the randomness ...) Mix in the network configuration to
|
||||
make machines with very reproducible boot sequences and low-resolution clocks
|
||||
distinguishable.
|
||||
|
||||
This base is kept constant, prefix.u[1] and prefix.u[2] are then treated as a
|
||||
64-bit unsigned integer to which we add IIDs to generate a hopping sequence
|
||||
that won't repeat in the lifetime of the process. Seems like it ought to work
|
||||
to keep the risks of collisions low. */
|
||||
{
|
||||
uint64_t iid = toBE8u (ddsi_iid_gen ());
|
||||
ddsrt_md5_state_t st;
|
||||
ddsrt_md5_byte_t digest[16];
|
||||
ddsrt_md5_init (&st);
|
||||
ddsrt_md5_append (&st, (const ddsrt_md5_byte_t *) &iid, sizeof (iid));
|
||||
for (int i = 0; i < gv->n_interfaces; i++)
|
||||
{
|
||||
const struct nn_interface *intf = &gv->interfaces[i];
|
||||
ddsrt_md5_append (&st, (const ddsrt_md5_byte_t *) &intf->loc.kind, sizeof (intf->loc.kind));
|
||||
ddsrt_md5_append (&st, (const ddsrt_md5_byte_t *) intf->loc.address, sizeof (intf->loc.address));
|
||||
}
|
||||
ddsrt_md5_finish (&st, digest);
|
||||
/* DDSI 2.2 requires the first two bytes of the GUID to be set to the vendor
|
||||
code -- a terrible waste of entropy ... */
|
||||
gv->ppguid_base.prefix.s[0] = NN_VENDORID_ECLIPSE.id[0];
|
||||
gv->ppguid_base.prefix.s[1] = NN_VENDORID_ECLIPSE.id[1];
|
||||
DDSRT_STATIC_ASSERT (sizeof (gv->ppguid_base.prefix.s) > 2 && sizeof (gv->ppguid_base.prefix.s) - 2 <= sizeof (digest));
|
||||
memcpy (&gv->ppguid_base.prefix.s[2], digest, sizeof (gv->ppguid_base.prefix.s) - 2);
|
||||
gv->ppguid_base.entityid.u = NN_ENTITYID_PARTICIPANT;
|
||||
}
|
||||
|
||||
ddsrt_mutex_init (&gv->lock);
|
||||
ddsrt_mutex_init (&gv->spdp_lock);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue