diff options
author | Roland Dreier <rolandd@cisco.com> | 2005-10-18 17:14:56 -0400 |
---|---|---|
committer | Roland Dreier <rolandd@cisco.com> | 2005-10-18 17:14:56 -0400 |
commit | ba8e9310244180bbc820e865d2e4378809b4a443 (patch) | |
tree | 407dc58bb932a7cd09df5c5b0c13f28cfd7f1c61 /drivers/infiniband | |
parent | d476306f1cc9156ce4b42586aacce70a356ef656 (diff) |
[IB] Fail sysfs queries after device is unregistered
We keep IB device structures around until the last sysfs reference is
gone, but we shouldn't ask the low-level driver to do anything after
the LLD unregisters the device. To handle this, check the reg_state
field and just fail sysfs show() requests if the device has already
been unregistered.
Signed-off-by: Roland Dreier <rolandd@cisco.com>
Diffstat (limited to 'drivers/infiniband')
-rw-r--r-- | drivers/infiniband/core/sysfs.c | 16 |
1 files changed, 16 insertions, 0 deletions
diff --git a/drivers/infiniband/core/sysfs.c b/drivers/infiniband/core/sysfs.c index 211ba3223f65..7ce7a6c782fa 100644 --- a/drivers/infiniband/core/sysfs.c +++ b/drivers/infiniband/core/sysfs.c | |||
@@ -65,6 +65,11 @@ struct port_table_attribute { | |||
65 | int index; | 65 | int index; |
66 | }; | 66 | }; |
67 | 67 | ||
68 | static inline int ibdev_is_alive(const struct ib_device *dev) | ||
69 | { | ||
70 | return dev->reg_state == IB_DEV_REGISTERED; | ||
71 | } | ||
72 | |||
68 | static ssize_t port_attr_show(struct kobject *kobj, | 73 | static ssize_t port_attr_show(struct kobject *kobj, |
69 | struct attribute *attr, char *buf) | 74 | struct attribute *attr, char *buf) |
70 | { | 75 | { |
@@ -74,6 +79,8 @@ static ssize_t port_attr_show(struct kobject *kobj, | |||
74 | 79 | ||
75 | if (!port_attr->show) | 80 | if (!port_attr->show) |
76 | return -EIO; | 81 | return -EIO; |
82 | if (!ibdev_is_alive(p->ibdev)) | ||
83 | return -ENODEV; | ||
77 | 84 | ||
78 | return port_attr->show(p, port_attr, buf); | 85 | return port_attr->show(p, port_attr, buf); |
79 | } | 86 | } |
@@ -581,6 +588,9 @@ static ssize_t show_node_type(struct class_device *cdev, char *buf) | |||
581 | { | 588 | { |
582 | struct ib_device *dev = container_of(cdev, struct ib_device, class_dev); | 589 | struct ib_device *dev = container_of(cdev, struct ib_device, class_dev); |
583 | 590 | ||
591 | if (!ibdev_is_alive(dev)) | ||
592 | return -ENODEV; | ||
593 | |||
584 | switch (dev->node_type) { | 594 | switch (dev->node_type) { |
585 | case IB_NODE_CA: return sprintf(buf, "%d: CA\n", dev->node_type); | 595 | case IB_NODE_CA: return sprintf(buf, "%d: CA\n", dev->node_type); |
586 | case IB_NODE_SWITCH: return sprintf(buf, "%d: switch\n", dev->node_type); | 596 | case IB_NODE_SWITCH: return sprintf(buf, "%d: switch\n", dev->node_type); |
@@ -595,6 +605,9 @@ static ssize_t show_sys_image_guid(struct class_device *cdev, char *buf) | |||
595 | struct ib_device_attr attr; | 605 | struct ib_device_attr attr; |
596 | ssize_t ret; | 606 | ssize_t ret; |
597 | 607 | ||
608 | if (!ibdev_is_alive(dev)) | ||
609 | return -ENODEV; | ||
610 | |||
598 | ret = ib_query_device(dev, &attr); | 611 | ret = ib_query_device(dev, &attr); |
599 | if (ret) | 612 | if (ret) |
600 | return ret; | 613 | return ret; |
@@ -612,6 +625,9 @@ static ssize_t show_node_guid(struct class_device *cdev, char *buf) | |||
612 | struct ib_device_attr attr; | 625 | struct ib_device_attr attr; |
613 | ssize_t ret; | 626 | ssize_t ret; |
614 | 627 | ||
628 | if (!ibdev_is_alive(dev)) | ||
629 | return -ENODEV; | ||
630 | |||
615 | ret = ib_query_device(dev, &attr); | 631 | ret = ib_query_device(dev, &attr); |
616 | if (ret) | 632 | if (ret) |
617 | return ret; | 633 | return ret; |