summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJerry Jelinek <jerry.jelinek@joyent.com>2020-02-03 12:58:04 +0000
committerJerry Jelinek <jerry.jelinek@joyent.com>2020-02-03 12:58:04 +0000
commitb69deb59db49c8958cbaea43a0d6bf9029f5b19e (patch)
tree4961beb6bfb113069d54b6dfb460e9b51bf0a0a9
parentf0dcd619b1421138ac11033df8e0cf904ba1efcf (diff)
parent8a2b682e57a046b828f37bcde1776f131ef4629f (diff)
downloadillumos-joyent-b69deb59db49c8958cbaea43a0d6bf9029f5b19e.tar.gz
[illumos-gate merge]
commit 8a2b682e57a046b828f37bcde1776f131ef4629f 12206 Want datalink properties in topo commit 1b500975aaacf8b5d0e18c9a117bf5560069ffc3 4454 ldi notifications trigger vdev_disk_free() without spa_config_lock() commit 4e995f2a014b6efa1fa6b0cf17c7f63ed51acf69 12256 reboot(1m) looks for 32-bit kernel only
-rw-r--r--usr/src/cmd/halt/halt.c15
-rw-r--r--usr/src/lib/fm/topo/libtopo/common/topo_hc.h14
-rw-r--r--usr/src/lib/fm/topo/modules/common/nic/topo_nic.c220
-rw-r--r--usr/src/lib/fm/topo/modules/common/shared/topo_port.c13
-rw-r--r--usr/src/lib/fm/topo/modules/common/shared/topo_port.h4
-rw-r--r--usr/src/lib/fm/topo/modules/common/shared/topo_transceiver.h2
-rw-r--r--usr/src/uts/common/fs/zfs/vdev_disk.c67
7 files changed, 279 insertions, 56 deletions
diff --git a/usr/src/cmd/halt/halt.c b/usr/src/cmd/halt/halt.c
index 0f096c6638..ca0ed8e77f 100644
--- a/usr/src/cmd/halt/halt.c
+++ b/usr/src/cmd/halt/halt.c
@@ -646,6 +646,19 @@ validate_disk(char *arg, char *mountpoint)
if (rc != 0)
return (rc);
+ /*
+ * Check for the usual case: 64-bit kernel
+ */
+ (void) snprintf(kernpath, MAXPATHLEN,
+ "%s/platform/i86pc/kernel/amd64/unix", mountpoint);
+ if (stat64(kernpath, &statbuf) == 0)
+ return (0);
+
+ /*
+ * We no longer build 32-bit kernel but in a case we are trying to boot
+ * some ancient filesystem with 32-bit only kernel we should be able to
+ * proceed too
+ */
(void) snprintf(kernpath, MAXPATHLEN, "%s/platform/i86pc/kernel/unix",
mountpoint);
@@ -1151,7 +1164,7 @@ parse_fastboot_args(char *bootargs_buf, size_t buf_size,
} else if (mplen != 0) {
/*
* No unix argument, but mountpoint is not empty, use
- * /platform/i86pc/$ISADIR/kernel/unix as default.
+ * /platform/i86pc/kernel/$ISADIR/unix as default.
*/
char isa[20];
diff --git a/usr/src/lib/fm/topo/libtopo/common/topo_hc.h b/usr/src/lib/fm/topo/libtopo/common/topo_hc.h
index 8f245c1cf0..19b60b004d 100644
--- a/usr/src/lib/fm/topo/libtopo/common/topo_hc.h
+++ b/usr/src/lib/fm/topo/libtopo/common/topo_hc.h
@@ -183,6 +183,7 @@ extern "C" {
#define TOPO_PROP_PORT_TYPE "type"
#define TOPO_PROP_PORT_TYPE_SFF "sff"
#define TOPO_PROP_PORT_TYPE_USB "usb"
+#define TOPO_PROP_PORT_TYPE_UNKNOWN "unknown"
#define TOPO_PGROUP_TRANSCEIVER "transceiver"
#define TOPO_PROP_TRANSCEIVER_TYPE "type"
@@ -290,6 +291,19 @@ extern "C" {
#define TOPO_PROP_UFM_SLOT_MODE "ufm-slot-mode"
#define TOPO_PROP_UFM_SLOT_ACTIVE "ufm-slot-active"
+#define TOPO_PGROUP_DATALINK "datalink"
+#define TOPO_PGROUP_DATALINK_PMAC "primary-mac-address"
+#define TOPO_PGROUP_DATALINK_LINK_SPEED "link-speed"
+#define TOPO_PGROUP_DATALINK_LINK_STATUS "link-status"
+#define TOPO_PGROUP_DATALINK_LINK_STATUS_UP "up"
+#define TOPO_PGROUP_DATALINK_LINK_STATUS_DOWN "down"
+#define TOPO_PGROUP_DATALINK_LINK_STATUS_UNKNOWN "unknown"
+#define TOPO_PGROUP_DATALINK_LINK_DUPLEX "link-duplex"
+#define TOPO_PGROUP_DATALINK_LINK_DUPLEX_FULL "full"
+#define TOPO_PGROUP_DATALINK_LINK_DUPLEX_HALF "half"
+#define TOPO_PGROUP_DATALINK_LINK_DUPLEX_UNKNOWN "unknown"
+#define TOPO_PGROUP_DATALINK_LINK_NAME "link-name"
+
#ifdef __cplusplus
}
#endif
diff --git a/usr/src/lib/fm/topo/modules/common/nic/topo_nic.c b/usr/src/lib/fm/topo/modules/common/nic/topo_nic.c
index 51c37142c5..cd272a0c73 100644
--- a/usr/src/lib/fm/topo/modules/common/nic/topo_nic.c
+++ b/usr/src/lib/fm/topo/modules/common/nic/topo_nic.c
@@ -11,6 +11,7 @@
/*
* Copyright (c) 2017, Joyent, Inc.
+ * Copyright 2020 Robert Mustacchi
*/
/*
@@ -23,10 +24,12 @@
#include <libdevinfo.h>
#include <libdladm.h>
#include <libdllink.h>
+#include <libdlstat.h>
#include <libsff.h>
#include <unistd.h>
#include <sys/dld_ioc.h>
#include <sys/dld.h>
+#include <sys/mac.h>
#include <sys/fm/protocol.h>
#include <fm/topo_mod.h>
@@ -38,13 +41,199 @@
#include "topo_nic.h"
+typedef enum {
+ NIC_PORT_UNKNOWN,
+ NIC_PORT_SFF
+} nic_port_type_t;
+
+static const topo_pgroup_info_t datalink_pgroup = {
+ TOPO_PGROUP_DATALINK,
+ TOPO_STABILITY_PRIVATE,
+ TOPO_STABILITY_PRIVATE,
+ 1
+};
+
+typedef struct nic_port_mac {
+ char npm_mac[ETHERADDRSTRL];
+ boolean_t npm_valid;
+ topo_mod_t *npm_mod;
+} nic_port_mac_t;
+
+/*
+ * The first MAC address is always the primary MAC address, so we only worry
+ * about the first. Thus this function always returns B_FALSE, to terminate
+ * iteration.
+ */
+static boolean_t
+nic_port_datalink_mac_cb(void *arg, dladm_macaddr_attr_t *attr)
+{
+ nic_port_mac_t *mac = arg;
+
+ if (attr->ma_addrlen != ETHERADDRL) {
+ topo_mod_dprintf(mac->npm_mod,
+ "found address with bad length: %u\n", attr->ma_addrlen);
+ return (B_FALSE);
+ }
+
+ (void) snprintf(mac->npm_mac, sizeof (mac->npm_mac),
+ "%02x:%02x:%02x:%02x:%02x:%02x",
+ attr->ma_addr[0], attr->ma_addr[1], attr->ma_addr[2],
+ attr->ma_addr[3], attr->ma_addr[4], attr->ma_addr[5]);
+ mac->npm_valid = B_TRUE;
+ return (B_FALSE);
+}
+
+static int
+nic_port_datalink_props(topo_mod_t *mod, tnode_t *port, dladm_handle_t handle,
+ datalink_id_t linkid)
+{
+ int err;
+ dladm_status_t status;
+ uint64_t ifspeed;
+ link_duplex_t duplex;
+ link_state_t state;
+ const char *duplex_str, *state_str;
+ datalink_class_t dlclass;
+ uint32_t media;
+ char dlname[MAXLINKNAMELEN * 2];
+ char dlerr[DLADM_STRSIZE];
+ nic_port_mac_t mac;
+
+ status = dladm_datalink_id2info(handle, linkid, NULL, &dlclass, &media,
+ dlname, sizeof (dlname));
+ if (status != DLADM_STATUS_OK) {
+ topo_mod_dprintf(mod, "failed to get link info: %s\n",
+ dladm_status2str(status, dlerr));
+ return (topo_mod_seterrno(mod, EMOD_UKNOWN_ENUM));
+ }
+
+ if (dlclass != DATALINK_CLASS_PHYS) {
+ return (0);
+ }
+
+ status = dladm_get_single_mac_stat(handle, linkid, "ifspeed",
+ KSTAT_DATA_UINT64, &ifspeed);
+ if (status != DLADM_STATUS_OK) {
+ topo_mod_dprintf(mod, "failed to get ifspeed: %s\n",
+ dladm_status2str(status, dlerr));
+ return (topo_mod_seterrno(mod, EMOD_UKNOWN_ENUM));
+ }
+
+ status = dladm_get_single_mac_stat(handle, linkid, "link_duplex",
+ KSTAT_DATA_UINT32, &duplex);
+ if (status != DLADM_STATUS_OK) {
+ topo_mod_dprintf(mod, "failed to get link_duplex: %s\n",
+ dladm_status2str(status, dlerr));
+ return (topo_mod_seterrno(mod, EMOD_UKNOWN_ENUM));
+ }
+
+ switch (duplex) {
+ case LINK_DUPLEX_HALF:
+ duplex_str = TOPO_PGROUP_DATALINK_LINK_DUPLEX_HALF;
+ break;
+ case LINK_DUPLEX_FULL:
+ duplex_str = TOPO_PGROUP_DATALINK_LINK_DUPLEX_FULL;
+ break;
+ default:
+ duplex_str = TOPO_PGROUP_DATALINK_LINK_DUPLEX_UNKNOWN;
+ break;
+ }
+
+ status = dladm_get_single_mac_stat(handle, linkid, "link_state",
+ KSTAT_DATA_UINT32, &state);
+ if (status != DLADM_STATUS_OK) {
+ topo_mod_dprintf(mod, "failed to get link_duplex: %s\n",
+ dladm_status2str(status, dlerr));
+ return (topo_mod_seterrno(mod, status));
+ }
+
+ switch (state) {
+ case LINK_STATE_UP:
+ state_str = TOPO_PGROUP_DATALINK_LINK_STATUS_UP;
+ break;
+ case LINK_STATE_DOWN:
+ state_str = TOPO_PGROUP_DATALINK_LINK_STATUS_DOWN;
+ break;
+ default:
+ state_str = TOPO_PGROUP_DATALINK_LINK_STATUS_UNKNOWN;
+ break;
+ }
+
+ /*
+ * Override the duplex if the link is down. Some devices will leave it
+ * set at half as opposed to unknown.
+ */
+ if (state == LINK_STATE_DOWN || state == LINK_STATE_UNKNOWN) {
+ duplex_str = TOPO_PGROUP_DATALINK_LINK_DUPLEX_UNKNOWN;
+ }
+
+ mac.npm_mac[0] = '\0';
+ mac.npm_valid = B_FALSE;
+ mac.npm_mod = mod;
+ if (media == DL_ETHER) {
+ (void) dladm_walk_macaddr(handle, linkid, &mac,
+ nic_port_datalink_mac_cb);
+ }
+
+ if (topo_pgroup_create(port, &datalink_pgroup, &err) != 0) {
+ topo_mod_dprintf(mod, "falied to create property group %s: "
+ "%s\n", TOPO_PGROUP_DATALINK, topo_strerror(err));
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ if (topo_prop_set_uint64(port, TOPO_PGROUP_DATALINK,
+ TOPO_PGROUP_DATALINK_LINK_SPEED, TOPO_PROP_IMMUTABLE, ifspeed,
+ &err) != 0) {
+ topo_mod_dprintf(mod, "failed to set %s property: %s\n",
+ TOPO_PGROUP_DATALINK_LINK_SPEED, topo_strerror(err));
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ if (topo_prop_set_string(port, TOPO_PGROUP_DATALINK,
+ TOPO_PGROUP_DATALINK_LINK_DUPLEX, TOPO_PROP_IMMUTABLE, duplex_str,
+ &err) != 0) {
+ topo_mod_dprintf(mod, "failed to set %s property: %s\n",
+ TOPO_PGROUP_DATALINK_LINK_DUPLEX, topo_strerror(err));
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ if (topo_prop_set_string(port, TOPO_PGROUP_DATALINK,
+ TOPO_PGROUP_DATALINK_LINK_STATUS, TOPO_PROP_IMMUTABLE, state_str,
+ &err) != 0) {
+ topo_mod_dprintf(mod, "failed to set %s property: %s\n",
+ TOPO_PGROUP_DATALINK_LINK_STATUS, topo_strerror(err));
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ if (topo_prop_set_string(port, TOPO_PGROUP_DATALINK,
+ TOPO_PGROUP_DATALINK_LINK_NAME, TOPO_PROP_IMMUTABLE, dlname,
+ &err) != 0) {
+ topo_mod_dprintf(mod, "failed to set %s propery: %s\n",
+ TOPO_PGROUP_DATALINK_LINK_NAME, topo_strerror(err));
+ return (topo_mod_seterrno(mod, err));
+ }
+
+ if (mac.npm_valid) {
+ if (topo_prop_set_string(port, TOPO_PGROUP_DATALINK,
+ TOPO_PGROUP_DATALINK_PMAC, TOPO_PROP_IMMUTABLE,
+ mac.npm_mac, &err) != 0) {
+ topo_mod_dprintf(mod, "failed to set %s propery: %s\n",
+ TOPO_PGROUP_DATALINK_PMAC, topo_strerror(err));
+ return (topo_mod_seterrno(mod, err));
+ }
+ }
+
+
+ return (0);
+}
+
/*
* Create an instance of a transceiver with the specified id. We must create
* both its port and the transceiver node.
*/
static int
nic_create_transceiver(topo_mod_t *mod, tnode_t *pnode, dladm_handle_t handle,
- datalink_id_t linkid, uint_t tranid)
+ datalink_id_t linkid, uint_t tranid, nic_port_type_t port_type)
{
int ret;
tnode_t *port;
@@ -55,9 +244,21 @@ nic_create_transceiver(topo_mod_t *mod, tnode_t *pnode, dladm_handle_t handle,
char *vendor = NULL, *part = NULL, *rev = NULL, *serial = NULL;
nvlist_t *nvl = NULL;
- if ((ret = port_create_sff(mod, pnode, tranid, &port)) != 0)
+ switch (port_type) {
+ case NIC_PORT_UNKNOWN:
+ ret = port_create_unknown(mod, pnode, tranid, &port);
+ break;
+ case NIC_PORT_SFF:
+ ret = port_create_sff(mod, pnode, tranid, &port);
+ break;
+ }
+
+ if ((ret = nic_port_datalink_props(mod, port, handle, linkid)) != 0)
return (ret);
+ if (port_type != NIC_PORT_SFF)
+ return (0);
+
bzero(&dgt, sizeof (dgt));
dgt.dgt_linkid = linkid;
dgt.dgt_tran_id = tranid;
@@ -139,6 +340,7 @@ nic_enum(topo_mod_t *mod, tnode_t *pnode, const char *name,
dld_ioc_gettran_t dgt;
uint_t ntrans, i;
char dname[MAXNAMELEN];
+ nic_port_type_t pt;
if (strcmp(name, NIC) != 0) {
topo_mod_dprintf(mod, "nic_enum: asked to enumerate unknown "
@@ -172,9 +374,13 @@ nic_enum(topo_mod_t *mod, tnode_t *pnode, const char *name,
dgt.dgt_tran_id = DLDIOC_GETTRAN_GETNTRAN;
if (ioctl(dladm_dld_fd(handle), DLDIOC_GETTRAN, &dgt) != 0) {
- if (errno == ENOTSUP)
- return (0);
- return (-1);
+ if (errno != ENOTSUP) {
+ return (-1);
+ }
+ pt = NIC_PORT_UNKNOWN;
+ dgt.dgt_tran_id = 1;
+ } else {
+ pt = NIC_PORT_SFF;
}
ntrans = dgt.dgt_tran_id;
@@ -185,8 +391,10 @@ nic_enum(topo_mod_t *mod, tnode_t *pnode, const char *name,
return (-1);
for (i = 0; i < ntrans; i++) {
- if (nic_create_transceiver(mod, pnode, handle, linkid, i) != 0)
+ if (nic_create_transceiver(mod, pnode, handle, linkid, i,
+ pt) != 0) {
return (-1);
+ }
}
return (0);
diff --git a/usr/src/lib/fm/topo/modules/common/shared/topo_port.c b/usr/src/lib/fm/topo/modules/common/shared/topo_port.c
index 5dfd947c0e..d6cbd7423e 100644
--- a/usr/src/lib/fm/topo/modules/common/shared/topo_port.c
+++ b/usr/src/lib/fm/topo/modules/common/shared/topo_port.c
@@ -155,3 +155,16 @@ port_create_usb(topo_mod_t *mod, tnode_t *pnode, topo_instance_t inst,
*nodep = tn;
return (0);
}
+
+int
+port_create_unknown(topo_mod_t *mod, tnode_t *pnode, topo_instance_t inst,
+ tnode_t **nodep)
+{
+ tnode_t *tn;
+
+ tn = port_create_common(mod, pnode, inst, TOPO_PROP_PORT_TYPE_UNKNOWN);
+ if (tn == NULL)
+ return (-1);
+ *nodep = tn;
+ return (0);
+}
diff --git a/usr/src/lib/fm/topo/modules/common/shared/topo_port.h b/usr/src/lib/fm/topo/modules/common/shared/topo_port.h
index df85ff84fd..861ea8d8e5 100644
--- a/usr/src/lib/fm/topo/modules/common/shared/topo_port.h
+++ b/usr/src/lib/fm/topo/modules/common/shared/topo_port.h
@@ -20,6 +20,8 @@
* Routines to manage and create ports.
*/
+#include <fm/topo_mod.h>
+
#ifdef __cplusplus
extern "C" {
#endif
@@ -30,6 +32,8 @@ extern int port_create_sff(topo_mod_t *, tnode_t *, topo_instance_t,
tnode_t **);
extern int port_create_usb(topo_mod_t *, tnode_t *, topo_instance_t,
tnode_t **);
+extern int port_create_unknown(topo_mod_t *, tnode_t *, topo_instance_t,
+ tnode_t **);
#ifdef __cplusplus
}
diff --git a/usr/src/lib/fm/topo/modules/common/shared/topo_transceiver.h b/usr/src/lib/fm/topo/modules/common/shared/topo_transceiver.h
index f371598739..b0bfbc2024 100644
--- a/usr/src/lib/fm/topo/modules/common/shared/topo_transceiver.h
+++ b/usr/src/lib/fm/topo/modules/common/shared/topo_transceiver.h
@@ -20,6 +20,8 @@
* Routines to manage and create ports.
*/
+#include <fm/topo_mod.h>
+
#ifdef __cplusplus
extern "C" {
#endif
diff --git a/usr/src/uts/common/fs/zfs/vdev_disk.c b/usr/src/uts/common/fs/zfs/vdev_disk.c
index f8604896ca..9408ec68fb 100644
--- a/usr/src/uts/common/fs/zfs/vdev_disk.c
+++ b/usr/src/uts/common/fs/zfs/vdev_disk.c
@@ -22,7 +22,7 @@
* Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
* Copyright (c) 2012, 2018 by Delphix. All rights reserved.
* Copyright 2016 Nexenta Systems, Inc. All rights reserved.
- * Copyright 2019 Joyent, Inc.
+ * Copyright 2020 Joyent, Inc.
*/
#include <sys/zfs_context.h>
@@ -128,10 +128,9 @@ vdev_disk_free(vdev_t *vd)
vd->vdev_tsd = NULL;
}
-/* ARGSUSED */
static int
-vdev_disk_off_notify(ldi_handle_t lh, ldi_ev_cookie_t ecookie, void *arg,
- void *ev_data)
+vdev_disk_off_notify(ldi_handle_t lh __unused, ldi_ev_cookie_t ecookie,
+ void *arg, void *ev_data __unused)
{
vdev_t *vd = (vdev_t *)arg;
vdev_disk_t *dvd = vd->vdev_tsd;
@@ -143,19 +142,15 @@ vdev_disk_off_notify(ldi_handle_t lh, ldi_ev_cookie_t ecookie, void *arg,
return (LDI_EV_SUCCESS);
/*
- * All LDI handles must be closed for the state change to succeed, so
- * call on vdev_disk_close() to do this.
- *
- * We inform vdev_disk_close that it is being called from offline
- * notify context so it will defer cleanup of LDI event callbacks and
- * freeing of vd->vdev_tsd to the offline finalize or a reopen.
+ * Tell any new threads that stumble upon this vdev that they should not
+ * try to do I/O.
*/
dvd->vd_ldi_offline = B_TRUE;
- vdev_disk_close(vd);
/*
- * Now that the device is closed, request that the spa_async_thread
- * mark the device as REMOVED and notify FMA of the removal.
+ * Request that the spa_async_thread mark the device as REMOVED and
+ * notify FMA of the removal. This should also trigger a vdev_close()
+ * in the async thread.
*/
zfs_post_remove(vd->vdev_spa, vd);
vd->vdev_remove_wanted = B_TRUE;
@@ -164,10 +159,9 @@ vdev_disk_off_notify(ldi_handle_t lh, ldi_ev_cookie_t ecookie, void *arg,
return (LDI_EV_SUCCESS);
}
-/* ARGSUSED */
static void
-vdev_disk_off_finalize(ldi_handle_t lh, ldi_ev_cookie_t ecookie,
- int ldi_result, void *arg, void *ev_data)
+vdev_disk_off_finalize(ldi_handle_t lh __unused, ldi_ev_cookie_t ecookie,
+ int ldi_result, void *arg, void *ev_data __unused)
{
vdev_t *vd = (vdev_t *)arg;
vdev_disk_t *dvd = vd->vdev_tsd;
@@ -180,12 +174,6 @@ vdev_disk_off_finalize(ldi_handle_t lh, ldi_ev_cookie_t ecookie,
return;
/*
- * We have already closed the LDI handle in notify.
- * Clean up the LDI event callbacks and free vd->vdev_tsd.
- */
- vdev_disk_free(vd);
-
- /*
* Request that the vdev be reopened if the offline state change was
* unsuccessful.
*/
@@ -201,10 +189,9 @@ static ldi_ev_callback_t vdev_disk_off_callb = {
.cb_finalize = vdev_disk_off_finalize
};
-/* ARGSUSED */
static void
-vdev_disk_dgrd_finalize(ldi_handle_t lh, ldi_ev_cookie_t ecookie,
- int ldi_result, void *arg, void *ev_data)
+vdev_disk_dgrd_finalize(ldi_handle_t lh __unused, ldi_ev_cookie_t ecookie,
+ int ldi_result, void *arg, void *ev_data __unused)
{
vdev_t *vd = (vdev_t *)arg;
@@ -329,17 +316,8 @@ vdev_disk_open(vdev_t *vd, uint64_t *psize, uint64_t *max_psize,
* just update the physical size of the device.
*/
if (dvd != NULL) {
- if (dvd->vd_ldi_offline && dvd->vd_lh == NULL) {
- /*
- * If we are opening a device in its offline notify
- * context, the LDI handle was just closed. Clean
- * up the LDI event callbacks and free vd->vdev_tsd.
- */
- vdev_disk_free(vd);
- } else {
- ASSERT(vd->vdev_reopening);
- goto skip_open;
- }
+ ASSERT(vd->vdev_reopening);
+ goto skip_open;
}
/*
@@ -772,14 +750,6 @@ vdev_disk_close(vdev_t *vd)
}
vd->vdev_delayed_close = B_FALSE;
- /*
- * If we closed the LDI handle due to an offline notify from LDI,
- * don't free vd->vdev_tsd or unregister the callbacks here;
- * the offline finalize callback or a reopen will take care of it.
- */
- if (dvd->vd_ldi_offline)
- return;
-
vdev_disk_free(vd);
}
@@ -813,7 +783,8 @@ vdev_disk_ldi_physio(ldi_handle_t vd_lh, caddr_t data,
static int
vdev_disk_dumpio(vdev_t *vd, caddr_t data, size_t size,
- uint64_t offset, uint64_t origoffset, boolean_t doread, boolean_t isdump)
+ uint64_t offset, uint64_t origoffset __unused, boolean_t doread,
+ boolean_t isdump)
{
vdev_disk_t *dvd = vd->vdev_tsd;
int flags = doread ? B_READ : B_WRITE;
@@ -821,11 +792,9 @@ vdev_disk_dumpio(vdev_t *vd, caddr_t data, size_t size,
/*
* If the vdev is closed, it's likely in the REMOVED or FAULTED state.
* Nothing to be done here but return failure.
- *
- * XXX-mg there is still a race here with off_notify
*/
if (dvd == NULL || dvd->vd_ldi_offline) {
- return (EIO);
+ return (SET_ERROR(ENXIO));
}
ASSERT(vd->vdev_ops == &vdev_disk_ops);
@@ -909,7 +878,7 @@ vdev_disk_io_start(zio_t *zio)
* If the vdev is closed, it's likely in the REMOVED or FAULTED state.
* Nothing to be done here but return failure.
*/
- if (dvd == NULL || (dvd->vd_ldi_offline && dvd->vd_lh == NULL)) {
+ if (dvd == NULL || dvd->vd_ldi_offline) {
zio->io_error = ENXIO;
zio_interrupt(zio);
return;