summaryrefslogtreecommitdiff
path: root/sys/dev/softraid.c
diff options
context:
space:
mode:
authorJoel Sing <jsing@cvs.openbsd.org>2011-09-19 21:47:38 +0000
committerJoel Sing <jsing@cvs.openbsd.org>2011-09-19 21:47:38 +0000
commitcffd557b24ccfe493733ce3d4c06f22eb59539b7 (patch)
tree9a047e0ebb3814ef8e0a7996f8879ac2e1d37e4b /sys/dev/softraid.c
parent0a8196486fe7e0fd56f376478e5d4d73dbbed5b3 (diff)
If the rootduid matches a softraid chunk of a bootable softraid volume,
map the rootduid to the DUID of the softraid volume. This means that regardless of where the kernel is loaded from we always get the softraid volume as the root device, providing we booted from one of its chunks. If we boot from any other disk then the rootduid remains unchanged. With this diff it is now possible to have the root filesystem on softraid, however at this stage the kernel still needs to be loaded from a separate FFS partition. ok deraadt@
Diffstat (limited to 'sys/dev/softraid.c')
-rw-r--r--sys/dev/softraid.c47
1 files changed, 46 insertions, 1 deletions
diff --git a/sys/dev/softraid.c b/sys/dev/softraid.c
index 9a5dd70c291..4d4bf1a7b80 100644
--- a/sys/dev/softraid.c
+++ b/sys/dev/softraid.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: softraid.c,v 1.250 2011/09/19 21:39:31 jsing Exp $ */
+/* $OpenBSD: softraid.c,v 1.251 2011/09/19 21:47:37 jsing Exp $ */
/*
* Copyright (c) 2007, 2008, 2009 Marco Peereboom <marco@peereboom.us>
* Copyright (c) 2008 Chris Kuethe <ckuethe@openbsd.org>
@@ -120,6 +120,7 @@ void sr_uuid_get(struct sr_uuid *);
void sr_uuid_print(struct sr_uuid *, int);
void sr_checksum_print(u_int8_t *);
int sr_boot_assembly(struct sr_softc *);
+void sr_map_root(struct sr_softc *);
int sr_already_assembled(struct sr_discipline *);
int sr_hotspare(struct sr_softc *, dev_t);
void sr_hotspare_rebuild(struct sr_discipline *);
@@ -1475,6 +1476,48 @@ unwind:
return (rv);
}
+void
+sr_map_root(struct sr_softc *sc)
+{
+ struct sr_meta_opt_item *omi;
+ struct sr_meta_boot *sbm;
+ u_char duid[8];
+ int i, j;
+
+ DNPRINTF(SR_D_MISC, "%s: sr_map_root\n", DEVNAME(sc));
+ bzero(duid, sizeof(duid));
+ if (bcmp(rootduid, duid, sizeof(duid)) == 0) {
+ DNPRINTF(SR_D_MISC, "%s: root duid is zero\n", DEVNAME(sc));
+ return;
+ }
+
+ for (i = 0; i < SR_MAX_LD; i++) {
+ if (sc->sc_dis[i] == NULL)
+ continue;
+ SLIST_FOREACH(omi, &sc->sc_dis[i]->sd_meta_opt, omi_link) {
+ if (omi->omi_som->som_type != SR_OPT_BOOT)
+ continue;
+ sbm = (struct sr_meta_boot *)omi->omi_som;
+ for (j = 0; j < SR_MAX_BOOT_DISKS; j++) {
+ if (bcmp(rootduid, sbm->sbm_boot_duid[j],
+ sizeof(rootduid)) == 0) {
+ bcopy(sbm->sbm_root_duid, rootduid,
+ sizeof(rootduid));
+ DNPRINTF(SR_D_MISC, "%s: root duid "
+ "mapped to %02hx%02hx%02hx%02hx"
+ "%02hx%02hx%02hx%02hx\n",
+ DEVNAME(sc), rootduid[0],
+ rootduid[1], rootduid[2],
+ rootduid[3], rootduid[4],
+ rootduid[5], rootduid[6],
+ rootduid[7]);
+ return;
+ }
+ }
+ }
+ }
+}
+
int
sr_meta_native_probe(struct sr_softc *sc, struct sr_chunk *ch_entry)
{
@@ -1751,6 +1794,8 @@ sr_attach(struct device *parent, struct device *self, void *aux)
sc->sc_shutdownhook = shutdownhook_establish(sr_shutdownhook, sc);
sr_boot_assembly(sc);
+
+ sr_map_root(sc);
}
int