VOID BthEchoConnectionObjectRemoteDisconnectSynchronously( _In_ PBTHECHOSAMPLE_DEVICE_CONTEXT_HEADER DevCtxHdr, _In_ PBTHECHO_CONNECTION Connection ) /*++ Description: This routine disconnects the connection synchronously Arguments: DevCtxHdr - Device context header Connection - Connection which is to be disconnected --*/ { PAGED_CODE(); BthEchoConnectionObjectRemoteDisconnect(DevCtxHdr, Connection); KeWaitForSingleObject(&Connection->DisconnectEvent, Executive, KernelMode, FALSE, NULL ); }
VOID BthEchoCliRemoteConnectCompletion( __in WDFREQUEST Request, __in WDFIOTARGET Target, __in PWDF_REQUEST_COMPLETION_PARAMS Params, __in WDFCONTEXT Context ) /*++ Description: Completion routine for Create request which we format as open channel BRB and send down the stack. We complete the Create request in this routine. We receive open channel BRB as the context. This BRB is part of the request context and doesn't need to be freed explicitly. Connection is part of the context in the BRB. Arguments: Request - Create request that we formatted with open channel BRB Target - Target to which we sent the request Params - Completion params Context - We receive BRB as the context Return Value: NTSTATUS Status code. --*/ { NTSTATUS status; struct _BRB_L2CA_OPEN_CHANNEL *brb; PBTHECHOSAMPLE_CLIENT_CONTEXT DevCtx; PBTHECHO_CONNECTION connection; DevCtx = GetClientDeviceContext(WdfIoTargetGetDevice(Target)); status = Params->IoStatus.Status; TraceEvents(TRACE_LEVEL_INFORMATION, DBG_CONNECT, "Connection completion, status: %!STATUS!", status); brb = (struct _BRB_L2CA_OPEN_CHANNEL *) Context; connection = (PBTHECHO_CONNECTION) brb->Hdr.ClientContext[0]; // // In the client we don't check for ConnectionStateDisconnecting state // because only file close generates disconnect which // cannot happen before create completes. And we complete Create // only after we process this completion. // if(NT_SUCCESS(status)) { connection->OutMTU = brb->OutResults.Params.Mtu; connection->InMTU = brb->InResults.Params.Mtu; connection->ChannelHandle = brb->ChannelHandle; connection->RemoteAddress = brb->BtAddress; connection->ConnectionState = ConnectionStateConnected; TraceEvents(TRACE_LEVEL_INFORMATION, DBG_CONNECT, "Connection established to server"); // // Call the function in device.c (BthEchoCliConnectionStateConnected) // for any post processing after connection has been established // status = BthEchoCliConnectionStateConnected(WdfRequestGetFileObject(Request), connection); if (!NT_SUCCESS(status)) { // // If such post processing fails we disconnect // BthEchoConnectionObjectRemoteDisconnect( &(DevCtx->Header), connection ); } } else { connection->ConnectionState = ConnectionStateConnectFailed; } // // Complete the Create request // WdfRequestComplete(Request, status); return; }
void BthEchoCliIndicationCallback( __in PVOID Context, __in INDICATION_CODE Indication, __in PINDICATION_PARAMETERS Parameters ) /*++ Description: Indication callback passed to bth stack while sending open channel BRB Bth stack sends notification related to the connection. Arguments: Context - We receive data connection as the context Indication - Type of indication Parameters - Parameters of indication --*/ { PBTHECHO_CONNECTION connection = (PBTHECHO_CONNECTION) Context; UNREFERENCED_PARAMETER(Parameters); // // Only supporting connect and disconnect // switch(Indication) { // // We don't add/release reference to anything because our connection // is scoped within file object lifetime // case IndicationAddReference: case IndicationReleaseReference: break; case IndicationRemoteConnect: { // // We don't expect connection // ASSERT(FALSE); break; } case IndicationRemoteDisconnect: { // // This is an indication that server has disconnected // In response we disconnect from our end // BthEchoConnectionObjectRemoteDisconnect( connection->DevCtxHdr, connection ); break; } case IndicationRemoteConfigRequest: case IndicationRemoteConfigResponse: case IndicationFreeExtraOptions: break; } }