Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F160432786
D49355.id.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
7 KB
Referenced Files
None
Subscribers
None
D49355.id.diff
View Options
diff --git a/stand/efi/include/efi.h b/stand/efi/include/efi.h
--- a/stand/efi/include/efi.h
+++ b/stand/efi/include/efi.h
@@ -74,14 +74,16 @@
#include "efidef.h"
#include "efidevp.h"
#include "efipciio.h"
-#include "efiprot.h"
#include "eficon.h"
+#include "efiapi.h"
+#include "efipart.h"
+#include "efigpt.h"
+#include "efiprot.h"
#include "eficonsctl.h"
#include "efiser.h"
#include "efi_nii.h"
#include "efipxebc.h"
#include "efinet.h"
-#include "efiapi.h"
#include "efifs.h"
#include "efierr.h"
#include "efigop.h"
@@ -90,6 +92,7 @@
#include "efitcp.h"
#include "efipoint.h"
#include "efiuga.h"
+#include "efichar.h"
#include <sys/types.h>
/*
diff --git a/stand/efi/include/efilib.h b/stand/efi/include/efilib.h
--- a/stand/efi/include/efilib.h
+++ b/stand/efi/include/efilib.h
@@ -40,6 +40,7 @@
extern struct devsw efipart_fddev;
extern struct devsw efipart_cddev;
extern struct devsw efipart_hddev;
+extern struct devsw efipart_label;
extern struct devsw efihttp_dev;
extern struct devsw efinet_dev;
extern struct netif_driver efinetif;
@@ -58,6 +59,7 @@
uint32_t pd_unit; /* unit number */
uint32_t pd_open; /* reference counter */
void *pd_bcache; /* buffer cache data */
+ char pd_volname[36*2];
struct pdinfo *pd_parent; /* Linked items (eg partitions) */
struct devsw *pd_devsw; /* Back pointer to devsw */
} pdinfo_t;
diff --git a/stand/efi/include/efiprot.h b/stand/efi/include/efiprot.h
--- a/stand/efi/include/efiprot.h
+++ b/stand/efi/include/efiprot.h
@@ -659,4 +659,41 @@
EFI_GET_BOOT_HARTID GetBootHartId;
} RISCV_EFI_BOOT_PROTOCOL;
+//
+// Partition Info Protocol
+//
+
+#define PARTITION_INFO_PROTOCOL \
+ { 0x8cf2f62c, 0xbc9b, 0x4821, {0x80, 0x8d, 0xec, 0x9e, 0xc4, 0x21, 0xa1, 0xa0} }
+
+INTERFACE_DECL(_EFI_PARTITION_INFO);
+
+#define EFI_PARTITION_INFO_INTERFACE_REVISION 0x0001000
+#define PARTITION_TYPE_OTHER 0x00
+#define PARTITION_TYPE_MBR 0x01
+#define PARTITION_TYPE_GPT 0x02
+
+#pragma pack(1)
+
+typedef struct _EFI_PARTITION_INFO {
+
+ UINT32 Revision;
+ UINT32 Type;
+ UINT8 System;
+ UINT8 Reserved[7];
+ union {
+ ///
+ /// MBR data
+ ///
+ MBR_PARTITION_RECORD Mbr;
+
+ ///
+ /// GPT data
+ ///
+ EFI_PARTITION_ENTRY Gpt;
+ } Info;
+} EFI_PARTITION_INFO;
+
+#pragma pack()
+
#endif
diff --git a/stand/efi/libefi/efipart.c b/stand/efi/libefi/efipart.c
--- a/stand/efi/libefi/efipart.c
+++ b/stand/efi/libefi/efipart.c
@@ -35,11 +35,10 @@
#include <efi.h>
#include <efilib.h>
-#include <efiprot.h>
-#include <efichar.h>
#include <disk.h>
static EFI_GUID blkio_guid = BLOCK_IO_PROTOCOL;
+static EFI_GUID partinfo_guid = PARTITION_INFO_PROTOCOL;
typedef bool (*pd_test_cb_t)(pdinfo_t *, pdinfo_t *);
static int efipart_initfd(void);
@@ -58,6 +57,12 @@
static int efipart_printcd(int);
static int efipart_printhd(int);
+static int efipart_get_volname(EFI_HANDLE h, char *dest, int size);
+static int label_parsedev(struct devdesc **idev, const char *devspec, const char **path);
+
+static char *nullfmt(struct devdesc *vdev);
+static int nullinit(void);
+
/* EISA PNP ID's for floppy controllers */
#define PNP0604 0x604
#define PNP0700 0x700
@@ -104,6 +109,20 @@
.dv_parsedev = disk_parsedev,
};
+struct devsw efipart_label = {
+ .dv_name = "label",
+ .dv_type = DEVT_LABEL,
+ .dv_init = nullinit,
+ .dv_strategy = efipart_strategy,
+ .dv_open = efipart_open,
+ .dv_close = efipart_close,
+ .dv_ioctl = efipart_ioctl,
+ .dv_print = efipart_printhd,
+ .dv_cleanup = nullsys,
+ .dv_fmtdev = nullfmt,
+ .dv_parsedev = label_parsedev,
+};
+
static pdinfo_list_t fdinfo = STAILQ_HEAD_INITIALIZER(fdinfo);
static pdinfo_list_t cdinfo = STAILQ_HEAD_INITIALIZER(cdinfo);
static pdinfo_list_t hdinfo = STAILQ_HEAD_INITIALIZER(hdinfo);
@@ -406,6 +425,8 @@
pd->pd_handle = hin[i];
pd->pd_devpath = devpath;
pd->pd_blkio = blkio;
+ /* Do not fail here */
+ efipart_get_volname(hin[i], pd->pd_volname, sizeof(pd->pd_volname));
STAILQ_INSERT_TAIL(&pdinfo, pd, pd_link);
}
@@ -419,6 +440,20 @@
return (0);
}
+static int
+efipart_get_volname(EFI_HANDLE h, char *dest, int size)
+{
+ EFI_PARTITION_INFO *partinfo;
+ int status;
+
+ status = OpenProtocolByHandle(h, &partinfo_guid, (void **)&partinfo);
+ if (EFI_ERROR(status)) {
+ return (efi_status_to_errno(status));
+ }
+ cpy16to8(partinfo->Info.Gpt.PartitionName, dest, size);
+ return (0);
+}
+
/*
* Get node identified by pd_test() from plist.
*/
@@ -1249,3 +1284,99 @@
free(blkbuf);
return (rc);
}
+
+static pdinfo_t *
+label_lookup_part(const char *label, struct devsw **dev)
+{
+ pdinfo_t *dp, *pp;
+
+ /*
+ * Check hard disks, then cd, then floppy
+ */
+ STAILQ_FOREACH(dp, &hdinfo, pd_link) {
+ if (!strcmp(label, dp->pd_volname)) {
+ *dev = &efipart_hddev;
+ return (dp);
+ }
+ STAILQ_FOREACH(pp, &dp->pd_part, pd_link) {
+ if (!strcmp(label, pp->pd_volname)) {
+ *dev = &efipart_hddev;
+ return (pp);
+ }
+ }
+ }
+ STAILQ_FOREACH(dp, &cdinfo, pd_link) {
+ if (!strcmp(label, dp->pd_volname)) {
+ *dev = &efipart_cddev;
+ return (dp);
+ }
+ STAILQ_FOREACH(pp, &dp->pd_part, pd_link) {
+ if (!strcmp(label, pp->pd_volname)) {
+ *dev = &efipart_cddev;
+ return (pp);
+ }
+ }
+ }
+ STAILQ_FOREACH(dp, &fdinfo, pd_link) {
+ if (!strcmp(label, dp->pd_volname)) {
+ *dev = &efipart_fddev;
+ return (dp);
+ }
+ }
+ return (NULL);
+}
+
+static int
+label_parsedev(struct devdesc **idev, const char *devspec, const char **path)
+{
+ pdinfo_t *part;
+ const char *devspeci, *devspecp;
+ char *label;
+ struct disk_devdesc *dev;
+
+ if (strncmp(devspec, "label:", strlen("label:"))) {
+ return (EINVAL);
+ }
+ devspeci = devspec + strlen("label:");
+ devspecp = strchr(devspeci, ':');
+ if (devspecp == NULL) {
+ return (EINVAL);
+ }
+ label = malloc(devspecp - devspeci + 1);
+ if (label == NULL) {
+ return (ENOMEM);
+ }
+ memcpy(label, devspeci, devspecp - devspeci);
+ label[devspecp - devspeci] = 0;
+
+ dev = calloc(sizeof(*dev), 1);
+ if (dev == NULL)
+ return (ENOMEM);
+
+ part = label_lookup_part(label, &dev->dd.d_dev);
+ if (part == NULL) {
+ return (ENOENT);
+ }
+
+ dev->dd.d_unit = part->pd_parent->pd_unit;
+ dev->d_slice = part->pd_unit;
+ dev->d_partition = D_PARTISGPT;
+ *idev = &dev->dd;
+ if (path != NULL) {
+ *path = devspecp + 1;
+ }
+
+ return (0);
+}
+
+static char *
+nullfmt(struct devdesc *vdev)
+{
+ return ("");
+}
+
+static int
+nullinit(void)
+{
+ return (0);
+}
diff --git a/stand/efi/loader/conf.c b/stand/efi/loader/conf.c
--- a/stand/efi/loader/conf.c
+++ b/stand/efi/loader/conf.c
@@ -40,6 +40,7 @@
&efipart_fddev,
&efipart_cddev,
&efipart_hddev,
+ &efipart_label,
&efihttp_dev, /* ordering with efinet_dev matters */
#if defined(LOADER_NET_SUPPORT)
&efinet_dev,
diff --git a/stand/libsa/dev.c b/stand/libsa/dev.c
--- a/stand/libsa/dev.c
+++ b/stand/libsa/dev.c
@@ -139,7 +139,8 @@
if (err != 0)
return (err);
- idev->d_dev = dv;
+ if (idev->d_dev == NULL)
+ idev->d_dev = dv;
if (dev != NULL)
*dev = idev;
else
diff --git a/stand/libsa/stand.h b/stand/libsa/stand.h
--- a/stand/libsa/stand.h
+++ b/stand/libsa/stand.h
@@ -153,6 +153,7 @@
#define DEVT_CD 3
#define DEVT_ZFS 4
#define DEVT_FD 5
+#define DEVT_LABEL 6
int (*dv_init)(void); /* early probe call */
int (*dv_strategy)(void *devdata, int rw, daddr_t blk,
size_t size, char *buf, size_t *rsize);
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Thu, Jun 25, 9:13 AM (3 h, 12 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
34220723
Default Alt Text
D49355.id.diff (7 KB)
Attached To
Mode
D49355: stand: add ability to reference partitions by label
Attached
Detach File
Event Timeline
Log In to Comment