Aller au contenu principal

Discovery

La découverte (discovery) est le processus automatique par lequel les Participants et endpoints DDS se trouvent mutuellement sur le réseau.

Vue d'ensemble

DDS utilise deux protocoles de découverte :

ProtocoleFonctionTrafic
SPDPTrouver les ParticipantsMulticast
SEDPÉchanger les endpointsUnicast
+---------------------------------------------------------+
| Flux de découverte |
+---------------------------------------------------------+
| |
| Participant A Participant B |
| | | |
| | ---- SPDP (multicast) -------> | Phase 1 : |
| | <--- SPDP (multicast) -------- | Trouver les |
| | | Participants |
| | | |
| | ---- SEDP (unicast) ---------> | Phase 2 : |
| | <--- SEDP (unicast) ---------- | Échanger les |
| | | endpoints |
| | | |
| | ---- Données utilisateur ----->| Phase 3 : |
| | | Les données |
| | | circulent |
+---------------------------------------------------------+

SPDP (Simple Participant Discovery Protocol)

SPDP découvre les autres DomainParticipants dans le même Domain.

Fonctionnement

  1. Chaque Participant envoie des annonces périodiques via multicast
  2. Les annonces contiennent le GUID du Participant, les locators, la durée du bail
  3. Les Participants maintiennent une liste des Participants découverts

Messages SPDP

Annonce SPDP :
+----------------------------------------+
| GUID Prefix: [01, 0f, aa, ...] |
| Vendor ID: HDDS (0x01aa) |
| Unicast Locator: 192.168.1.100:7411 |
| Multicast Locator: 239.255.0.1:7400 |
| Lease Duration: 30s |
| User Data: "app=sensor" |
+----------------------------------------+

Configuration réseau

Paramètres multicast par défaut :

ParamètreDéfautDomain N
Adresse multicast239.255.0.1239.255.0.1
Port Discovery74007400 + N*10
Offset Participant+0, +1+0 à +9
// Customize discovery
let config = DomainParticipantConfig::default()
.discovery_multicast("239.255.0.1:7400")
.lease_duration(Duration::from_secs(30));

Timing SPDP

Annonces initiales :     Rafale rapide (0.5s, 1s, 2s)
État stable : Toutes les lease_duration/3
Expiration du bail : Suppression apres lease_duration

SEDP (Simple Endpoint Discovery Protocol)

SEDP échange les informations sur les DataWriters et DataReaders.

Fonctionnement

  1. Apres que SPDP à découvert un Participant, SEDP commence
  2. Les Participants échangent les informations d'endpoints via unicast
  3. Chaque côté apprend les Writers et Readers distants

Messages SEDP

SEDP Publication (Info Writer) :
+----------------------------------------+
| Endpoint GUID: [01, 0f, aa, ..., c2] |
| Topic Name: "SensorTopic" |
| Type Name: "sensors::SensorData" |
| Reliability: Reliable |
| Durability: TransientLocal |
| Ownership: Shared |
| Type Object: (XTypes info) |
+----------------------------------------+

SEDP Subscription (Info Reader) :
+----------------------------------------+
| Endpoint GUID: [02, 1a, bb, ..., c7] |
| Topic Name: "SensorTopic" |
| Type Name: "sensors::SensorData" |
| Reliability: Reliable |
| Durability: Volatile |
+----------------------------------------+

Endpoints intégrés

Chaque Participant possède des endpoints intégrés pour la découverte :

Entity IDFonction
0x000100c2SPDP Writer
0x000100c7SPDP Reader
0x000003c2Publications Writer
0x000003c7Publications Reader
0x000004c2Subscriptions Writer
0x000004c7Subscriptions Reader

Processus d'appariement

Apres l'échange SEDP, les endpoints sont appariés :

Criteres d'appariement :
1. Même nom de Topic (correspondance exacte)
2. Type compatible (nom de type + XTypes)
3. QoS compatibles (voir les règles QoS)
4. Même Domain (implicite par la découverte)
5. Chevauchement de Partition (si configure)

Verification de compatibilité QoS

PolitiqueExigence
ReliabilityWriter >= Reader
DurabilityWriter >= Reader
DeadlineWriter <= Reader
LivelinessWriter kind >= Reader kind
OwnershipWriter = Reader

Événements de découverte

Événements Participant

impl DomainParticipantListener for MyListener {
fn on_participant_discovered(&mut self, participant: &DomainParticipant, info: DiscoveredParticipantInfo) {
println!("Found participant: {:?}", info.guid);
println!(" Vendor: {:?}", info.vendor_id);
println!(" User data: {:?}", info.user_data);
}

fn on_participant_lost(&mut self, participant: &DomainParticipant, guid: GUID) {
println!("Participant left: {:?}", guid);
}
}

Événements Endpoint

impl DataWriterListener for MyListener {
fn on_publication_matched(&mut self, writer: &DataWriter<T>, status: PublicationMatchedStatus) {
println!("Writer matched {} readers (total: {})",
status.current_count_change,
status.current_count);
}
}

impl DataReaderListener for MyListener {
fn on_subscription_matched(&mut self, reader: &DataReader<T>, status: SubscriptionMatchedStatus) {
println!("Reader matched {} writers (total: {})",
status.current_count_change,
status.current_count);
}
}

Requêtes de découverte

Lister les Participants découverts

for info in participant.discovered_participants() {
println!("Participant: {:?}", info.guid);
println!(" Unicast: {:?}", info.unicast_locators);
}

Lister les Topics découverts

for info in participant.discovered_topics() {
println!("Topic: {} (type: {})", info.name, info.type_name);
}

Vérifier les endpoints appariés

// Writer side
let matched_readers = writer.matched_subscriptions();
for reader_guid in matched_readers {
println!("Matched reader: {:?}", reader_guid);
}

// Reader side
let matched_writers = reader.matched_publications();
for writer_guid in matched_writers {
println!("Matched writer: {:?}", writer_guid);
}

Discovery statique

Pour les réseaux sans multicast :

let config = DomainParticipantConfig::default()
// Disable multicast discovery
.enable_multicast_discovery(false)

// Manually specify peer addresses
.initial_peers(vec![
"192.168.1.100:7400".parse()?,
"192.168.1.101:7400".parse()?,
]);

Timing de la découverte

Temps de découverte typiques

ScenarioTemps
Même hôte50-100 ms
Même LAN100-500 ms
Cross-subnet (statique)100-200 ms

Accélérer la découverte

let config = DomainParticipantConfig::default()
// Faster initial announcements
.initial_announcement_period(Duration::from_millis(100))

// Shorter lease (faster détection of failures)
.lease_duration(Duration::from_secs(10));

Dépannage de la découverte

Aucun Participant trouve

# Check multicast connectivity
ping -c 3 239.255.0.1

# Verify SPDP traffic
tcpdump -i any -n udp port 7400

# Enable discovery debug
export RUST_LOG=hdds::discovery=debug

Endpoints non appariés

Causes fréquentes :

ProblèmeSolution
Domain ID différentUtiliser le même Domain
Nom de Topic différentVérifier l'orthographe, la casse
Nom de type différentUtiliser le même IDL
QoS incompatiblesVérifier Reliability, Durability
Partition differenteVérifier les chaînes de Partition

Configuration du pare-feu

Ports requis :

UDP 7400-7500    (discovery + données, par Domain)
UDP 239.255.0.0/16 (multicast, si active)

Interopérabilité entre vendeurs

La découverte fonctionne entre les vendeurs DDS :

VendeurSPDPSEDPNotes
FastDDSOuiOuiLes paramètres par défaut fonctionnent
RTI ConnextOuiOuiPeut nécessiter le mode interop
CycloneDDSOuiOuiExcellente conformité
OpenDDSOuiOuiFonctionne avec RTPS

Détection du vendeur

for info in participant.discovered_participants() {
match info.vendor_id {
VendorId::HDDS => println!("HDDS participant"),
VendorId::RTI => println!("RTI Connext participant"),
VendorId::EPROSIMA => println!("FastDDS participant"),
VendorId::CYCLONE => println!("CycloneDDS participant"),
_ => println!("Unknown vendor: {:?}", info.vendor_id),
}
}

Architecture de la découverte

+---------------------------------------------------------+
| Sous-système de découverte |
+---------------------------------------------------------+
| |
| +-------------+ +-------------+ +-------------+ |
| | SPDP Writer | | SEDP Pubs | | SEDP Subs | |
| | (builtin) | | Writer | | Writer | |
| +-------------+ +-------------+ +-------------+ |
| | | | |
| v v v |
| +------------------------------------------------------+|
| | Base de données de découverte ||
| | - Participants découverts ||
| | - Endpoints découverts ||
| | - État d'appariement ||
| +------------------------------------------------------+|
| ^ ^ ^ |
| +-------------+ +-------------+ +-------------+ |
| | SPDP Reader | | SEDP Pubs | | SEDP Subs | |
| | (builtin) | | Reader | | Reader | |
| +-------------+ +-------------+ +-------------+ |
| |
+---------------------------------------------------------+

Prochaines étapes