private bool StartMonitoring() { // Start the connecting process. Connecting will be set to FALSE once IsConnected is assigned a value. ConnectionState = ConnectionStates.Connecting; _ignoreConnectionCallback = false; DEBUGLogger.WriteLine("Waiting for connection response..."); // Store a reference to the delegate instance in a private class field before passing it to the native code - // to prevent the garbage collector from collecting it! _handleCommsEvent = DevLink_Connection_CallBack; // Create the wait-handle. This thread will wait till the callback returns, or the timeout expires. _waitConnectionOrTimeoutHandle = new AutoResetEvent(false); // Call the DevLink method to connect: long iRet = DLOpen((uint)_iPOID, IpAddress, _password, null, null, _handleCommsEvent); // TODO: does it make sense to check for the return value here??? DEBUGLogger.WriteLine("DLOpen: iPOID = " + _iPOID + "; iRet = " + iRet); // There is a sliiight possibility that HandleCommsEvent is called and returns before we get to the "...WaitOne()" call below. // But we're not going to bother with this - if so, WaitOne will just wait till the timeout. // (If we decide to check the ConnectionState here, before calling WaitOne, nothing will prevent it from changing // juuust after our check and before the WaitOne call (unless we lock()).) // Now wait till the Connection-Callback returns, or the timeout expires: _waitConnectionOrTimeoutHandle.WaitOne(_connectionTimeoutSec); // this should return 'false' in case of timeout, but we don't need the result // OK, the event was signaled - let's see what this means for the Connection State... lock (_connectionLock) { if (_connectionCallbackMessage.Length > 0) { DEBUGLogger.WriteLine(_connectionCallbackMessage); } switch (ConnectionState) { case ConnectionStates.Connected: DEBUGLogger.WriteLine("Connection within timeout!..."); break; case ConnectionStates.Failed: DEBUGLogger.WriteLine("Connection problems! ConnectionState: " + ConnectionState.ToString()); break; case ConnectionStates.Connecting: ConnectionState = ConnectionStates.TimedOut; DEBUGLogger.WriteLine("Connection Timeout expired!..."); break; case ConnectionStates.Disconnected: DEBUGLogger.WriteLine("Unexpected connection state in StartMonitoring() - Disconnected"); break; } // We got a response OR the waiting timed out. Either way, we're done with the CallBack, so let it know: _ignoreConnectionCallback = true; } // un-locking if (ConnectionState == ConnectionStates.Connected) { // Start the DevLink processing: // TODO: Maybe move this to the lock..??? Process(); } else { // There was a connection error, or we gave up waiting // (but DevLink does not know it, and could still call the callback if the timeout interval turned out to be too small) // We don't want surprises, so we'd better close the connection, just in case: CloseConnection(); } // We should not need this anymore, so close it: _waitConnectionOrTimeoutHandle.Close(); return(ConnectionState == ConnectionStates.Connected); }
private static extern long DLOpen(uint pbxh, string pbx_address, string pbx_password, string reserved1, string reserved2, COMMSEVENT cb);