diff --git a/src/include/gpxe/infiniband.h b/src/include/gpxe/infiniband.h index 771d2a07..69bc69b5 100644 --- a/src/include/gpxe/infiniband.h +++ b/src/include/gpxe/infiniband.h @@ -368,6 +368,8 @@ struct ib_device { struct refcnt refcnt; /** List of Infiniband devices */ struct list_head list; + /** List of open Infiniband devices */ + struct list_head open_list; /** Underlying device */ struct device *dev; /** List of completion queues */ @@ -473,6 +475,7 @@ extern struct ib_device * alloc_ibdev ( size_t priv_size ); extern int register_ibdev ( struct ib_device *ibdev ); extern void unregister_ibdev ( struct ib_device *ibdev ); extern struct ib_device * find_ibdev ( struct ib_gid *gid ); +extern struct ib_device * last_opened_ibdev ( void ); extern void ib_link_state_changed ( struct ib_device *ibdev ); extern void ib_poll_eq ( struct ib_device *ibdev ); extern struct list_head ib_devices; diff --git a/src/net/infiniband.c b/src/net/infiniband.c index 45f38d9c..cd7deae2 100644 --- a/src/net/infiniband.c +++ b/src/net/infiniband.c @@ -45,6 +45,9 @@ FILE_LICENCE ( GPL2_OR_LATER ); /** List of Infiniband devices */ struct list_head ib_devices = LIST_HEAD_INIT ( ib_devices ); +/** List of open Infiniband devices, in reverse order of opening */ +static struct list_head open_ib_devices = LIST_HEAD_INIT ( open_ib_devices ); + /*************************************************************************** * * Completion queues @@ -565,6 +568,9 @@ int ib_open ( struct ib_device *ibdev ) { goto err_open; } + /* Add to head of open devices list */ + list_add ( &ibdev->open_list, &open_ib_devices ); + assert ( ibdev->open_count == 1 ); return 0; @@ -593,6 +599,7 @@ void ib_close ( struct ib_device *ibdev ) { /* Close device if this was the last remaining requested opening */ if ( ibdev->open_count == 0 ) { + list_del ( &ibdev->open_list ); ib_destroy_mi ( ibdev, ibdev->gsi ); ib_destroy_sma ( ibdev, ibdev->smi ); ib_destroy_mi ( ibdev, ibdev->smi ); @@ -898,3 +905,19 @@ struct ib_device * find_ibdev ( struct ib_gid *gid ) { } return NULL; } + +/** + * Get most recently opened Infiniband device + * + * @ret ibdev Most recently opened Infiniband device, or NULL + */ +struct ib_device * last_opened_ibdev ( void ) { + struct ib_device *ibdev; + + list_for_each_entry ( ibdev, &open_ib_devices, open_list ) { + assert ( ibdev->open_count != 0 ); + return ibdev; + } + + return NULL; +} diff --git a/src/net/netdevice.c b/src/net/netdevice.c index 3bb0574d..f019eeb2 100644 --- a/src/net/netdevice.c +++ b/src/net/netdevice.c @@ -43,7 +43,7 @@ FILE_LICENCE ( GPL2_OR_LATER ); struct list_head net_devices = LIST_HEAD_INIT ( net_devices ); /** List of open network devices, in reverse order of opening */ -struct list_head open_net_devices = LIST_HEAD_INIT ( open_net_devices ); +static struct list_head open_net_devices = LIST_HEAD_INIT ( open_net_devices ); /** Default link status code */ #define EUNKNOWN_LINK_STATUS EINPROGRESS