summaryrefslogtreecommitdiffstats
path: root/src/detection/bootmgr/bootmgr_bsd.c
diff options
context:
space:
mode:
authorsumuel <samuel@yakubos.org>2026-08-17 20:44:55 +0000
committersumuel <samuel@yakubos.org>2026-08-17 20:44:55 +0000
commit76424950e373d3b04ac3dd13019151bfba3e8423 (patch)
tree4c3cfdbda039e592b9186be3e28f8d7cfd439e8a /src/detection/bootmgr/bootmgr_bsd.c
Add the files
Diffstat (limited to 'src/detection/bootmgr/bootmgr_bsd.c')
-rw-r--r--src/detection/bootmgr/bootmgr_bsd.c62
1 files changed, 62 insertions, 0 deletions
diff --git a/src/detection/bootmgr/bootmgr_bsd.c b/src/detection/bootmgr/bootmgr_bsd.c
new file mode 100644
index 0000000..cfaa41d
--- /dev/null
+++ b/src/detection/bootmgr/bootmgr_bsd.c
@@ -0,0 +1,62 @@
+#include "bootmgr.h"
+#include "efi_helper.h"
+#include "common/io.h"
+
+#ifdef __OpenBSD__
+ #include <dev/efi/efiio.h>
+#else
+ #include <sys/efiio.h>
+#endif
+#include <sys/ioctl.h>
+#include <fcntl.h>
+#include <stdalign.h>
+
+#ifdef __NetBSD__
+typedef uint16_t efi_char;
+#endif
+
+#ifndef EFI_GLOBAL_VARIABLE
+ #define EFI_GLOBAL_VARIABLE { 0x8be4df61, 0x93ca, 0x11d2, 0xaa, 0x0d, { 0x00, 0xe0, 0x98, 0x03, 0x2b, 0x8c } }
+#endif
+
+const char* ffDetectBootmgr(FFBootmgrResult* result) {
+ FF_AUTO_CLOSE_FD int efifd = open("/dev/efi", O_RDWR | O_CLOEXEC);
+ if (efifd < 0) {
+ return "open(/dev/efi) failed";
+ }
+
+ alignas(uint16_t) uint8_t buffer[2048];
+ struct efi_var_ioc ioc = {
+ .vendor = EFI_GLOBAL_VARIABLE,
+ .data = buffer,
+ };
+
+ ioc.datasize = sizeof(buffer);
+ ioc.name = (efi_char[]) { 'B', 'o', 'o', 't', 'C', 'u', 'r', 'r', 'e', 'n', 't', '\0' };
+ ioc.namesize = sizeof("BootCurrent") * 2;
+ if (ioctl(efifd, EFIIOC_VAR_GET, &ioc) < 0 || ioc.datasize != 2) {
+ return "ioctl(EFIIOC_VAR_GET, BootCurrent) failed";
+ }
+
+ result->order = *(uint16_t*) buffer;
+
+ unsigned char hex[5];
+ snprintf((char*) hex, sizeof(hex), "%04X", result->order);
+ ioc.datasize = sizeof(buffer);
+ ioc.name = (efi_char[]) { 'B', 'o', 'o', 't', hex[0], hex[1], hex[2], hex[3], '\0' };
+ ioc.namesize = sizeof("Boot####") * 2;
+ if (ioctl(efifd, EFIIOC_VAR_GET, &ioc) < 0 || ioc.datasize == sizeof(buffer)) {
+ return "ioctl(EFIIOC_VAR_GET, Boot####) failed";
+ }
+
+ ffEfiFillLoadOption((FFEfiLoadOption*) buffer, result);
+
+ ioc.name = (efi_char[]) { 'S', 'e', 'c', 'u', 'r', 'e', 'B', 'o', 'o', 't', '\0' };
+ ioc.namesize = sizeof("SecureBoot") * 2;
+ ioc.datasize = sizeof(buffer);
+ if (ioctl(efifd, EFIIOC_VAR_GET, &ioc) == 0 && ioc.datasize == 1) {
+ result->secureBoot = !!buffer[0];
+ }
+
+ return NULL;
+}