//******************************************************************* void COpcC_Client::DoOpcDisconnect() { CWaitCursor wait; HRESULT hr = S_OK; if( opcServer.IsOk() && opcGroup.IsOk() ) { if( dwShutdownConnection ) { IConnectionPointContainer *pCPC = 0; hr = opcServer.QueryInterface(IID_IConnectionPointContainer, (void**)&pCPC); if( SUCCEEDED(hr) ) { IConnectionPoint *pCallbackCP = 0; hr = pCPC->FindConnectionPoint(IID_IOPCShutdown, &pCallbackCP); if( SUCCEEDED(hr) ) { hr = pCallbackCP->Unadvise(dwShutdownConnection); pCallbackCP->Release(); } pCPC->Release(); } } if( usingCP ) { // OPC 2.0 ConnectionPoints IConnectionPointContainer *pCPC = 0; hr = opcGroup.QueryInterface(IID_IConnectionPointContainer, (void**)&pCPC); if( SUCCEEDED(hr) && dwConnection1 ) // This server supports 2.0 { IConnectionPoint *pCallbackCP = 0; hr = pCPC->FindConnectionPoint(IID_IOPCDataCallback, &pCallbackCP); if( SUCCEEDED(hr) ) { hr = pCallbackCP->Unadvise(dwConnection1); pCallbackCP->Release(); } pCPC->Release(); } } else // call IDataObject::DUnadvise to turn off data notification { DataObject dataObject; HRESULT hr = dataObject.Attach( opcGroup ); if( SUCCEEDED(hr) ) { if( dwConnection1 ) hr = dataObject.DUnadvise(dwConnection1); if( dwConnection2 ) hr = dataObject.DUnadvise(dwConnection2); dataObject.Detach(); } } opcServer.RemoveGroup(groupHandle, FALSE); } opcGroup.Detach(); opcServer.Detach(); Sleep( 100 ); // now that the group is released and unadvised, no more data will // be sent from the server. It is safe to delete the items while( !items.IsEmpty() ) delete items.RemoveTail(); }