diff options
author | pjd <pjd@FreeBSD.org> | 2007-05-06 01:39:39 +0000 |
---|---|---|
committer | pjd <pjd@FreeBSD.org> | 2007-05-06 01:39:39 +0000 |
commit | 1effa32b6605b4852fd2e5c00bd93f04f0e3bf60 (patch) | |
tree | 155527b23b9a27cd3b08983c2dbd01ca5b09866d /cddl/contrib | |
parent | a360ad79b03fc86ad14ee529259ec67558935c3c (diff) | |
download | FreeBSD-src-1effa32b6605b4852fd2e5c00bd93f04f0e3bf60.zip FreeBSD-src-1effa32b6605b4852fd2e5c00bd93f04f0e3bf60.tar.gz |
Use provider's ident to handle situations when disks are moved around
and show up with different names: first try to open provider using
remembered name and compare its ident, if equal, this is our provider,
if not equal or there is no provider with such name, find provider with
remembered ident and don't care about the name.
Diffstat (limited to 'cddl/contrib')
-rw-r--r-- | cddl/contrib/opensolaris/cmd/zpool/zpool_vdev.c | 53 |
1 files changed, 43 insertions, 10 deletions
diff --git a/cddl/contrib/opensolaris/cmd/zpool/zpool_vdev.c b/cddl/contrib/opensolaris/cmd/zpool/zpool_vdev.c index de07723..cfed1f0 100644 --- a/cddl/contrib/opensolaris/cmd/zpool/zpool_vdev.c +++ b/cddl/contrib/opensolaris/cmd/zpool/zpool_vdev.c @@ -159,18 +159,14 @@ out: static boolean_t is_provider(const char *name) { - off_t mediasize; int fd; - fd = open(name, O_RDONLY); - if (fd == -1) - return (B_FALSE); - if (ioctl(fd, DIOCGMEDIASIZE, &mediasize) == -1) { - close(fd); - return (B_FALSE); + fd = g_open(name, 0); + if (fd >= 0) { + g_close(fd); + return (B_TRUE); } - close(fd); - return (B_TRUE); + return (B_FALSE); } /* @@ -183,9 +179,11 @@ is_provider(const char *name) nvlist_t * make_leaf_vdev(const char *arg) { - char path[MAXPATHLEN]; + char ident[DISK_IDENT_SIZE], path[MAXPATHLEN]; + struct stat64 statbuf; nvlist_t *vdev = NULL; char *type = NULL; + boolean_t wholedisk = B_FALSE; if (strncmp(arg, _PATH_DEV, sizeof(_PATH_DEV) - 1) == 0) strlcpy(path, arg, sizeof (path)); @@ -212,6 +210,41 @@ make_leaf_vdev(const char *arg) verify(nvlist_add_uint64(vdev, ZPOOL_CONFIG_WHOLE_DISK, (uint64_t)B_FALSE) == 0); + /* + * For a whole disk, defer getting its devid until after labeling it. + */ + if (1 || (S_ISBLK(statbuf.st_mode) && !wholedisk)) { + /* + * Get the devid for the device. + */ + int fd; + ddi_devid_t devid; + char *minor = NULL, *devid_str = NULL; + + if ((fd = open(path, O_RDONLY)) < 0) { + (void) fprintf(stderr, gettext("cannot open '%s': " + "%s\n"), path, strerror(errno)); + nvlist_free(vdev); + return (NULL); + } + + if (devid_get(fd, &devid) == 0) { + if (devid_get_minor_name(fd, &minor) == 0 && + (devid_str = devid_str_encode(devid, minor)) != + NULL) { + verify(nvlist_add_string(vdev, + ZPOOL_CONFIG_DEVID, devid_str) == 0); + } + if (devid_str != NULL) + devid_str_free(devid_str); + if (minor != NULL) + devid_str_free(minor); + devid_free(devid); + } + + (void) close(fd); + } + return (vdev); } |