TL;DR — OPC UA Part 12: Discovery and Global Services (GDS)

Full spec: reference.opcfoundation.org/GDS/v105/docs

What Is It?

OPC UA Part 12 defines the centralized infrastructure for discovering OPC UA applications and managing their certificates and trust lists across an entire network. It introduces two main services:

  1. Global Discovery Server (GDS) — an enterprise-wide registry of OPC UA applications
  2. Certificate Manager — automates issuance, renewal, and revocation of X.509 certificates for all applications

Think of the GDS as the "DNS + Certificate Authority" for your OPC UA network.


The Problem It Solves

In simple setups, OPC UA clients find servers manually by IP or hostname. But in large industrial systems with hundreds of servers across multiple subnets, you need:

  1. Centralized discovery — find any server on any subnet from a single query
  2. Automated PKI — issue, renew, and revoke certificates without manual installs
  3. TrustList distribution — keep all applications' trust lists in sync
  4. Security enforcement — ensure only approved applications communicate

Discovery Architecture

flowchart TB
    subgraph Host1 ["Host A"]
        S1[OPC UA Server 1]
        S2[OPC UA Server 2]
        LDS1[Local Discovery<br/>Server - LDS]
        S1 -.->|Register| LDS1
        S2 -.->|Register| LDS1
    end

    subgraph Host2 ["Host B"]
        S3[OPC UA Server 3]
        LDS2[LDS-ME<br/>with Multicast]
        S3 -.->|Register| LDS2
    end

    GDS["Global Discovery Server<br/>(enterprise-wide)"]
    LDS1 -.->|Register| GDS
    LDS2 -.->|Register| GDS

    Client[OPC UA Client]
    Client -->|QueryApplications| GDS
    Client -->|FindServers| LDS1
    Client -->|FindServersOnNetwork| LDS2

    style GDS fill:#2d6a4f,color:#fff
    style Client fill:#1d3557,color:#fff

Discovery Hierarchy

LevelServiceScopeHow
LocalLDSSame hostFindServers on well-known address
SubnetLDS-MESame multicast subnetmDNS + FindServersOnNetwork
EnterpriseGDSEntire admin domainQueryApplications with filters

Certificate Management — The Core of GDS

The CertificateManager handles the complete lifecycle of Application Instance Certificates:

flowchart LR
    REG[Register<br/>Application] --> ISSUE[Issue<br/>Certificate]
    ISSUE --> RENEW[Renew<br/>Certificate]
    RENEW --> RENEW
    RENEW --> REVOKE[Revoke<br/>Certificate]
    ISSUE --> TL[Update<br/>TrustList]
    TL --> TL

Pull vs Push Management

Pull ManagementPush Management
Who initiatesApplication (acts as Client)CertificateManager (acts as Client)
Application roleClient connecting to CertificateManagerServer exposing ServerConfiguration
Key methodsStartSigningRequest, FinishRequest, GetTrustListCreateSigningRequest, UpdateCertificate, TrustList::Write
AuthenticationApplication cert (ApplicationSelfAdmin)SecurityAdmin credentials
Periodic checkApp polls on UpdateFrequency intervalCertificateManager pushes when needed
Best forApps that can run periodic background tasksEmbedded devices, servers

Pull Management Sequence

sequenceDiagram
    participant App as 📱 Application
    participant CM as 🔐 CertificateManager

    App->>CM: Connect (encrypted + anonymous)
    Note over App,CM: App authenticates via its current cert<br/>(ApplicationSelfAdmin privilege)

    App->>CM: GetCertificateStatus(appId, groupId)
    CM-->>App: updateRequired = true

    App->>App: Generate new key pair + CSR
    App->>CM: StartSigningRequest(appId, groupId, CSR)
    CM-->>App: requestId

    loop Until cert is ready
        App->>CM: FinishRequest(appId, requestId)
        CM-->>App: signedCertificate + issuerCerts
    end

    App->>CM: GetTrustList(appId, groupId)
    CM-->>App: TrustList NodeId
    App->>CM: TrustList::Read
    CM-->>App: TrustListDataType

    App->>App: Persist cert + TrustList
    App->>CM: Disconnect

Push Management Sequence

sequenceDiagram
    participant CM as 🔐 CertificateManager
    participant Srv as 🖥️ OPC UA Server

    CM->>Srv: Connect (SecurityAdmin credentials)

    CM->>Srv: TrustList::Open (write)
    CM->>Srv: TrustList::Write (updated TrustList)
    CM->>Srv: TrustList::CloseAndUpdate

    CM->>Srv: CreateSigningRequest(groupId, typeId)
    Srv-->>CM: CSR (signed with server's private key)

    CM->>CM: Sign CSR with CA

    CM->>Srv: UpdateCertificate(groupId, cert, issuerCerts)
    Srv-->>CM: applyChangesRequired = true

    CM->>Srv: ApplyChanges()
    Note over Srv: Server restarts endpoints<br/>with new cert + TrustList

    CM->>Srv: Disconnect

Information Model Summary

GDS Address Space (DirectoryType)

Directory
├── Applications/            ← Folder with registered app objects
├── FindApplications()       ← Find app by ApplicationUri
├── RegisterApplication()    ← Add new app (returns ApplicationId)
├── UpdateApplication()      ← Update existing registration
├── UnregisterApplication()  ← Remove app (revokes its certs)
├── GetApplication()         ← Get app record by ApplicationId
├── QueryApplications()      ← Search apps with filters
└── QueryServers()           ← Legacy search (returns ServerOnNetwork)

CertificateManager Address Space

CertificateManager
├── CertificateGroups/
│   ├── DefaultApplicationGroup/
│   │   ├── TrustList              ← TrustListType (read/write)
│   │   ├── CertificateTypes       ← allowed cert types
│   │   ├── CertificateExpired     ← alarm
│   │   └── TrustListOutOfDate     ← alarm
│   ├── DefaultHttpsGroup/         ← optional
│   └── DefaultUserTokenGroup/     ← optional
├── StartSigningRequest()          ← Submit CSR
├── StartNewKeyPairRequest()       ← CertMgr generates key pair
├── FinishRequest()                ← Retrieve signed cert
├── GetCertificateGroups()         ← Get groups for an app
├── GetCertificateStatus()         ← Check if renewal needed
├── GetTrustList()                 ← Get TrustList NodeId for an app
└── RevokeCertificate()            ← Revoke a cert

ServerConfiguration (for Push Management)

ServerConfiguration
├── CertificateGroups/
│   ├── DefaultApplicationGroup/
│   │   ├── TrustList
│   │   └── CertificateTypes
│   └── ...
├── ServerCapabilities
├── SupportedPrivateKeyFormats
├── MaxTrustListSize
├── MulticastDnsEnabled
├── CreateSigningRequest()     ← Generate CSR
├── UpdateCertificate()        ← Receive new cert from CertMgr
├── ApplyChanges()             ← Apply cert/TrustList changes
├── CancelChanges()            ← Discard pending changes
└── GetRejectedList()          ← Get untrusted certs

CertificateGroups Explained

A CertificateGroup bundles a TrustList with one or more CertificateTypes:

GroupPurposeCertificateTypes
DefaultApplicationGroupOPC UA secure channelRsaMinApplicationCertificate, RsaSha256ApplicationCertificate, EccApplicationCertificate
DefaultHttpsGroupHTTPS endpointsHttpsCertificate
DefaultUserTokenGroupUser token trust (no certs issued)(empty — TrustList only)

TrustList Structure

TrustListDataType {
    specifiedLists:      bitmask (which fields are present)
    trustedCertificates: ByteString[]  ← app + CA certs you trust
    trustedCrls:         ByteString[]  ← CRLs for trusted CAs
    issuerCertificates:  ByteString[]  ← intermediate CAs
    issuerCrls:          ByteString[]  ← CRLs for intermediate CAs
}

The UpdateFrequency property tells clients how often to check for TrustList updates. A TrustListOutOfDateAlarm fires if a client misses the window.


Roles & Privileges

Role/PrivilegeScope
DiscoveryAdminRegister/update/unregister apps in directory
CertificateAuthorityAdminIssue, revoke certs; update TrustLists
RegistrationAuthorityAdminApprove cert signing requests
SecurityAdminChange security config (Push Management)
ApplicationSelfAdmin (privilege)App can renew its own cert, read its TrustList
ApplicationAdmin (privilege)Manage certs for multiple apps (e.g., DCA)

Key Takeaways

  1. GDS = Discovery + Certificate Management — a single server providing both enterprise directory and PKI services
  2. CertificateManager is the real workhorse — handles cert issuance, renewal, revocation, and TrustList distribution
  3. Pull for clients, Push for servers — but either model works for either role
  4. CertificateGroups organize TrustLists and cert types — apps can have separate groups for OPC UA, HTTPS, and user tokens
  5. ApplicationSelfAdmin pattern — apps authenticate with their existing cert to renew it (no admin password needed)
  6. TrustLists auto-expire — the UpdateFrequency property + alarms ensure trust data stays current
  7. Security first — all methods require encrypted channels; admin actions need role-based access
  8. Part 21 (Onboarding) sits on top — the Registrar authenticates devices, then delegates to the GDS CertificateManager
  9. GDS can wrap existing PKI — designed to front Active Directory, EJBCA, or any CA backend
  10. Scalability built-in — clients are expected to connect briefly, do their work, and disconnect to save resources

Relationship to Other Parts

flowchart TB
    P4[Part 4 - Services<br/>Discovery, SecureChannel]
    P5[Part 5 - Information Model<br/>Base types, FileType]
    P6[Part 6 - Mappings<br/>Transport, well-known addresses]
    P12[Part 12 - GDS<br/>Discovery, CertificateManager<br/>TrustLists]
    P21[Part 21 - Onboarding<br/>Registrar, Tickets<br/>Device Authentication]

    P12 -->|uses Discovery services| P4
    P12 -->|uses BaseObjectType, FileType| P5
    P12 -->|uses transport mappings| P6
    P21 -->|uses CertificateManager| P12

How GDS and Device Onboarding (Part 21) Are Linked

Part 12 provides the infrastructure (CertificateManager, TrustLists, application directory). Part 21 adds the authentication layer that happens before a device is allowed to use that infrastructure.

The Registrar (Part 21) acts as a gatekeeper: it authenticates devices using DeviceIdentity Certificates + Tickets, then registers them with the CertificateManager and issues a short-lived DCA Certificate. The DCA then uses standard Part 12 Pull/Push workflows to get its Application Instance Certificates and TrustLists.

In many deployments, the Registrar and CertificateManager run as the same server sharing a common backend.