diff options
| author | Michael Brown | 2008-10-03 01:07:52 +0200 |
|---|---|---|
| committer | Michael Brown | 2008-11-11 06:31:06 +0100 |
| commit | d9751edafa08b2ec3779004d4209400b95884cd4 (patch) | |
| tree | 532aaeda86668006aee5fc6994e6f0b773c2a427 /src/drivers/net | |
| parent | [ne2k_isa] Restore support for ne2k isa cards (diff) | |
| download | ipxe-d9751edafa08b2ec3779004d4209400b95884cd4.tar.gz ipxe-d9751edafa08b2ec3779004d4209400b95884cd4.tar.xz ipxe-d9751edafa08b2ec3779004d4209400b95884cd4.zip | |
[infiniband] Flush uncompleted work queue entries at QP teardown
Avoid leaking I/O buffers in ib_destroy_qp() by completing any
outstanding work queue entries with a generic error code. This
requires the completion handlers to be available to ib_destroy_qp(),
which is done by making them static configuration parameters of the CQ
(set by ib_create_cq()) rather than being provided on each call to
ib_poll_cq().
This mimics the functionality of netdev_{tx,rx}_flush(). The netdev
flush functions would previously have been catching any I/O buffers
leaked by the IPoIB data queue (though not by the IPoIB metadata
queue).
Diffstat (limited to 'src/drivers/net')
| -rw-r--r-- | src/drivers/net/ipoib.c | 21 |
1 files changed, 16 insertions, 5 deletions
diff --git a/src/drivers/net/ipoib.c b/src/drivers/net/ipoib.c index 812c11c95..a56ceb89e 100644 --- a/src/drivers/net/ipoib.c +++ b/src/drivers/net/ipoib.c @@ -278,13 +278,21 @@ static void ipoib_destroy_qset ( struct ipoib_device *ipoib, * * @v ipoib IPoIB device * @v qset Queue set + * @v num_cqes Number of completion queue entries + * @v num_send_wqes Number of send work queue entries + * @v complete_send Send completion handler + * @v num_recv_wqes Number of receive work queue entries + * @v complete_recv Receive completion handler + * @v qkey Queue key * @ret rc Return status code */ static int ipoib_create_qset ( struct ipoib_device *ipoib, struct ipoib_queue_set *qset, unsigned int num_cqes, unsigned int num_send_wqes, + ib_completer_t complete_send, unsigned int num_recv_wqes, + ib_completer_t complete_recv, unsigned long qkey ) { struct ib_device *ibdev = ipoib->ibdev; int rc; @@ -297,7 +305,8 @@ static int ipoib_create_qset ( struct ipoib_device *ipoib, qset->recv_max_fill = num_recv_wqes; /* Allocate completion queue */ - qset->cq = ib_create_cq ( ibdev, num_cqes ); + qset->cq = ib_create_cq ( ibdev, num_cqes, complete_send, + complete_recv ); if ( ! qset->cq ) { DBGC ( ipoib, "IPoIB %p could not allocate completion queue\n", ipoib ); @@ -759,10 +768,8 @@ static void ipoib_poll ( struct net_device *netdev ) { struct ipoib_device *ipoib = netdev->priv; struct ib_device *ibdev = ipoib->ibdev; - ib_poll_cq ( ibdev, ipoib->meta.cq, ipoib_meta_complete_send, - ipoib_meta_complete_recv ); - ib_poll_cq ( ibdev, ipoib->data.cq, ipoib_data_complete_send, - ipoib_data_complete_recv ); + ib_poll_cq ( ibdev, ipoib->meta.cq ); + ib_poll_cq ( ibdev, ipoib->data.cq ); ipoib_refill_recv ( ipoib, &ipoib->meta ); ipoib_refill_recv ( ipoib, &ipoib->data ); } @@ -847,7 +854,9 @@ static int ipoib_open ( struct net_device *netdev ) { if ( ( rc = ipoib_create_qset ( ipoib, &ipoib->meta, IPOIB_META_NUM_CQES, IPOIB_META_NUM_SEND_WQES, + ipoib_meta_complete_send, IPOIB_META_NUM_RECV_WQES, + ipoib_meta_complete_recv, IB_GLOBAL_QKEY ) ) != 0 ) { DBGC ( ipoib, "IPoIB %p could not allocate metadata QP: %s\n", ipoib, strerror ( rc ) ); @@ -858,7 +867,9 @@ static int ipoib_open ( struct net_device *netdev ) { if ( ( rc = ipoib_create_qset ( ipoib, &ipoib->data, IPOIB_DATA_NUM_CQES, IPOIB_DATA_NUM_SEND_WQES, + ipoib_data_complete_send, IPOIB_DATA_NUM_RECV_WQES, + ipoib_data_complete_recv, IB_GLOBAL_QKEY ) ) != 0 ) { DBGC ( ipoib, "IPoIB %p could not allocate data QP: %s\n", ipoib, strerror ( rc ) ); |
