ParticipantQos中的wire_protocol(WireProtocolConfigQos类型)成员中存在participant_id成员:
DomainParticipantImpl::DomainParticipantImpl(...) {
...
participant_id_ = qos_.wire_protocol().participant_id;
}
如果用户不指定,则其wire_protocol的participant_id默认为-1,这种情况下,RTPSDomain会自动分配一个可用的participant_id替换这个-1:
DomainParticipantImpl::DomainParticipantImpl(...) {
...
// Pre calculate participant id and generated guid
participant_id_ = qos_.wire_protocol().participant_id;
eprosima::fastrtps::rtps::RTPSDomainImpl::create_participant_guid(participant_id_, guid_);
...
}
void RTPSDomainImpl::create_participant_guid(
int32_t& participant_id,
GUID_t& guid)
{
if (participant_id < 0)
{
... // 调用getNewId获取一个未被使用的participant_id
}
guid_prefix_create(participant_id, guid.guidPrefix); // 根据participantid生成guid_prefix
guid.entityId = c_EntityId_RTPSParticipant; // guid_prefix + participant固定的entityID组成其guid
}
participant_id会影响到RTPSParticipant的GUID中GuidPrefix的值
GuidPrefix总共12字节,其中前8个字节是整个进程的guid_prefix,后4个字节就是participant_id
void guid_prefix_create(
uint32_t participant_id,
GuidPrefix_t& guid_prefix) const
{
// Use precalculated vendor-host-process part of the prefix 前8个字节从进程的GuidPrefix获取
std::copy(prefix_.value, prefix_.value + 8, guid_prefix.value);
// Add little endian serialization of participant_id 后4个字节为participant_id
guid_prefix.value[8] = static_cast<octet>(participant_id & 0xFF);
guid_prefix.value[9] = static_cast<octet>((participant_id >> 8) & 0xFF);
guid_prefix.value[10] = static_cast<octet>((participant_id >> 16) & 0xFF);
guid_prefix.value[11] = static_cast<octet>((participant_id >> 24) & 0xFF);
}
进程的guid_prefix在GuidUtil的构造函数中设置:
GuidUtils() {
... // 0,1 两个字节是dds厂商ID,这里是eprosima的vendorID(0x01, 0x0F)
... // 2,3 两个字节是根据当前主机IP地址集合计算出的MD5值
... // 4,5 两个字节是当前DDS进程的ID
... // 6,7 两个字节是随机值
... // 剩下的4个字节是0
}