OPC-клиент подключается к OPC-серверу и коммуницирует с ним через COM-интерфейсы:
| Data Access Server Required Interfaces | 1.0 | 2.0 | 3.0 |
| OPCServer | |||
| IUnknown | Required | Required | Required |
| IOPCServer | Required | Required | Required |
| IOPCCommon | N/A | Required | Required |
| IConnectionPointContainer | N/A | Required | Required |
| IOPCItemProperties | N/A | Required | N/A |
| IOPCBrowse | N/A | N/A | Required |
| IOPCServerPublicGroups | Optional | Optional | N/A |
| IOPCBrowseServerAddressSpace | Optional | Optional | N/A |
| IOPCItemIO | N/A | N/A | Required |
| OPCGroup | |||
| IUnknown | Required | Required | Required |
| IOPCItemMgt | Required | Required | Required |
| IOPCGroupStateMgt | Required | Required | Required |
| IOPCGroupStateMgt2 | N/A | N/A | Required |
| IOPCPublicGroupStateMgt | Optional | Optional | N/A |
| IOPCSyncIO | Required | Required | Required |
| IOPCSyncIO2 | N/A | N/A | Required |
| IOPCAsyncIO | Required | Optional | N/A |
| IOPCAsyncIO2 | N/A | Required | Required |
| IOPCAsyncIO3 | N/A | N/A | Required |
| IOPCItemDeadbandMgt | N/A | N/A | Required |
| IOPCItemSamplingMgt | N/A | N/A | Optional |
| IConnectionPointContainer | N/A | Required | Required |
| IDataObject | Required | Optional | N/A |
Remote
- TCP подключение
- интерфейс IObjectExporter, метод ServerAlive2 – возвращает security bindings сетевых интерфейсов сервера (IP-адреса)
- интерфейс ISystemActivator, метод RemoteCreateInstance
- переход на случайный высокий порт (плохо для брандмауэров)

- метод AlterContext назначает Context ID запрашиваемому интерфейсу
- 0 = QueryInterface, 1=AddRef, 2=Release – унаследованы от IUnknown (?), дальше согласно спецификации
- IOPCServer.AddGroup = Context ID 5, opnum 3
HRESULT AddGroup(
[in, string] LPCWSTR szName,
[in] BOOL bActive,
[in] DWORD dwRequestedUpdateRate,
[in] OPCHANDLE hClientGroup,
[unique, in] LONG *pTimeBias,
[in] FLOAT * pPercentDeadband,
[in] DWORD dwLCID,
[out] OPCHANDLE * phServerGroup,
[out] DWORD *pRevisedUpdateRate,
[in] REFIID riid,
[out, iid_is(riid)] LPUNKNOWN * ppUnk
);
- IOPCBrowse.Browse
HRESULT Browse(
[in, string] LPWSTR szItemID,
[in,out, string] LPWSTR *pszContinuationPoint,
[in] DWORD dwMaxElementsReturned,
[in] OPCBROWSEFILTER dwBrowseFilter,
[in, string] LPWSTR szElementNameFilter,
[in, string] LPWSTR szVendorFilter,
[in] BOOL bReturnAllProperties,
[in] BOOL bReturnPropertyValues,
[in] DWORD dwPropertyCount,
[in, size_is(dwPropertyCount)] DWORD * pdwPropertyIDs,
[out] BOOL * pbMoreElements,
[out] DWORD * pdwCount,
[out, size_is(,*pdwCount)] OPCBROWSEELEMENT ** ppBrowseElements
);
- IOPCItemMgt.AddItems
HRESULT AddItems(
[in] DWORD dwCount,
[in, size_is(dwCount)] OPCITEMDEF * pItemArray,
[out, size_is(,dwCount)] OPCITEMRESULT ** ppAddResults,
[out, size_is(,dwCount)] HRESULT ** ppErrors
);
- IOPCSyncIO.Read
HRESULT Read(
[in] OPCDATASOURCE dwSource,
[in] DWORD dwCount,
[in, size_is(dwCount)] OPCHANDLE * phServer,
[out, size_is(,dwCount)] OPCITEMSTATE ** ppItemValues,
[out, size_is(,dwCount)] HRESULT ** ppErrors
);

