Given a duid, I want to be able to delete a disk.

There seems to be no elegant way to get just the disk ("sd0") from a
duid. I didn't like my code using opendev, so I've tried sysctl. Looks
better imho. Still, is there a better way?

Index: bioctl.c
===================================================================
RCS file: /srv/boron/data/vcs/cvs/openbsd/src/sbin/bioctl/bioctl.c,v
retrieving revision 1.98
diff -u -p -r1.98 bioctl.c
--- bioctl.c    1 Dec 2010 19:40:18 -0000       1.98
+++ bioctl.c    29 Dec 2010 14:46:30 -0000
@@ -32,6 +32,7 @@
 #include <sys/param.h>
 #include <sys/types.h>
 #include <sys/stat.h>
+#include <sys/sysctl.h>
 #include <dev/biovar.h>
 #include <dev/softraidvar.h>
 
@@ -941,13 +942,38 @@ void
 bio_deleteraid(char *dev)
 {
        struct bioc_deleteraid  bd;
+       char *disknames = NULL;
        memset(&bd, 0, sizeof(bd));
 
+       if (isduid(dev, OPENDEV_PART)) {
+               int mib[2];
+               size_t len;
+               char *duid, *name;
+
+               mib[0] = CTL_HW;
+               mib[1] = HW_DISKNAMES;
+               if (sysctl(mib, 2, NULL, &len, NULL, 0) == -1)
+                       err(1, "sysctl");
+               if ((disknames = malloc(len)) == NULL)
+                       err(1, "malloc");
+               if (sysctl(mib, 2, disknames, &len, NULL, 0) == -1)
+                       err(1, "sysctl");
+
+               duid = disknames;
+               while ((name = strsep(&duid, ":,")) != NULL)
+                       if (duid && strcmp(dev, duid) == 0) {
+                               dev = name;
+                               break;
+                       }
+       }
+
        bd.bd_cookie = bd.bd_cookie;
        /* XXX make this a dev_t instead of a string */
        strlcpy(bd.bd_dev, dev, sizeof bd.bd_dev);
        if (ioctl(devh, BIOCDELETERAID, &bd))
                errx(1, "delete volume %s failed", dev);
+
+       free(disknames);
 }
 
 void

Reply via email to