We need to return all MADs to IBAL before calling close_al.  To protect
against queuing MADs during deregistration, set the MAD service handle
to NULL when deregistering and check that it is still valid before queuing
any received MADs.

This fixes a hanging when using ctrl-C to kill a process running ibping.

Signed-off-by: Sean Hefty <[email protected]>
---
diff -up -r -X \mshefty\scm\winof\trunk\docs\dontdiff.txt -I '\$Id:' 
trunk\core\winmad/kernel/wm_provider.c
branches\winverbs\core\winmad/kernel/wm_provider.c
--- trunk\core\winmad/kernel/wm_provider.c      2009-02-23 15:49:36.385049200 
-0800
+++ branches\winverbs\core\winmad/kernel/wm_provider.c  2009-05-05 
11:54:32.247285400 -0700
@@ -92,11 +92,13 @@ static ib_mad_element_t *WmRemoveMad(WM_
        return mad;
 }
 
-void WmProviderFlushReceives(WM_PROVIDER *pProvider, WM_REGISTRATION 
*pRegistration)
+void WmProviderDeregister(WM_PROVIDER *pProvider, WM_REGISTRATION 
*pRegistration)
 {
        ib_mad_element_t        *mad, *next, *list;
 
        WdfObjectAcquireLock(pProvider->ReadQueue);
+       pRegistration->hService = NULL;
+
        list = pProvider->MadHead;
        pProvider->MadHead = NULL;
 
@@ -372,20 +374,24 @@ void WmReceiveHandler(ib_mad_svc_handle_
        size_t                  len = 0;
 
        UNREFERENCED_PARAMETER(hService);
+       reg = (WM_REGISTRATION *) pMad->send_context1;
 
        WdfObjectAcquireLock(prov->ReadQueue);
+       if (reg->hService == NULL) {
+               reg->pDevice->IbInterface.put_mad(pMad);
+               goto unlock;
+       }
+       
        status = WdfIoQueueRetrieveNextRequest(prov->ReadQueue, &request);
        if (!NT_SUCCESS(status)) {
                WmInsertMad(prov, pMad);
-               WdfObjectReleaseLock(prov->ReadQueue);
-               return;
+               goto unlock;
        }
 
        status = WdfRequestRetrieveOutputBuffer(request, sizeof(WM_IO_MAD), 
&wmad, &len);
        if (!NT_SUCCESS(status)) {
-               reg = (WM_REGISTRATION *) pMad->send_context1;
                reg->pDevice->IbInterface.put_mad(pMad);
-               goto out;
+               goto complete;
        }
 
        status = WmCopyRead(prov, wmad, pMad, &len);
@@ -395,10 +401,11 @@ void WmReceiveHandler(ib_mad_svc_handle_
        } else {
                WmInsertMad(prov, pMad);
        }
-       WdfObjectReleaseLock(prov->ReadQueue);
 
-out:
-       WdfRequestCompleteWithInformation(request, status, len);        
+complete:
+       WdfRequestCompleteWithInformation(request, status, len);
+unlock:
+       WdfObjectReleaseLock(prov->ReadQueue);
 }
 
 void WmSendHandler(ib_mad_svc_handle_t hService, void *Context,
diff -up -r -X \mshefty\scm\winof\trunk\docs\dontdiff.txt -I '\$Id:' 
trunk\core\winmad/kernel/wm_provider.h
branches\winverbs\core\winmad/kernel/wm_provider.h
--- trunk\core\winmad/kernel/wm_provider.h      2008-12-03 11:27:53.296244000 
-0800
+++ branches\winverbs\core\winmad/kernel/wm_provider.h  2009-05-05 
11:54:32.106658600 -0700
@@ -75,8 +75,8 @@ void WmReceiveHandler(ib_mad_svc_handle_
                                          ib_mad_element_t *pMad);
 void WmSendHandler(ib_mad_svc_handle_t hService, void *Context,
                                   ib_mad_element_t *pMad);
-void WmProviderFlushReceives(WM_PROVIDER *pProvider,
-                                                        struct 
_WM_REGISTRATION *pRegistration);
+void WmProviderDeregister(WM_PROVIDER *pProvider,
+                                                 struct _WM_REGISTRATION 
*pRegistration);
 void WmProviderCancel(WM_PROVIDER *pProvider, WDFREQUEST Request);
 
 #endif // _WM_PROVIDER_H_
diff -up -r -X \mshefty\scm\winof\trunk\docs\dontdiff.txt -I '\$Id:' 
trunk\core\winmad/kernel/wm_reg.c
branches\winverbs\core\winmad/kernel/wm_reg.c
--- trunk\core\winmad/kernel/wm_reg.c   2008-12-11 11:43:51.437500000 -0800
+++ branches\winverbs\core\winmad/kernel/wm_reg.c       2009-05-05 
11:54:32.356661800 -0700
@@ -274,12 +274,12 @@ void WmRegRemoveHandler(WM_REGISTRATION 
                return;
        }
 
+       WmProviderDeregister(pRegistration->pProvider, pRegistration);
        pRegistration->pDevice->IbInterface.destroy_qp(pRegistration->hQp, 
NULL);
        pRegistration->pDevice->IbInterface.dealloc_pd(pRegistration->hPd, 
NULL);
        pRegistration->pDevice->IbInterface.close_ca(pRegistration->hCa, NULL);
        pRegistration->pDevice->IbInterface.close_al(pRegistration->hIbal);
 
-       WmProviderFlushReceives(pRegistration->pProvider, pRegistration);
        WmIbDevicePut(pRegistration->pDevice);
        pRegistration->pDevice = NULL;
 }

_______________________________________________
ofw mailing list
[email protected]
http://lists.openfabrics.org/cgi-bin/mailman/listinfo/ofw

Reply via email to