diff --git a/docs/DISCOVERABLE_PARTITIONS.md b/docs/DISCOVERABLE_PARTITIONS.md index 02ff1f6de3..af19b33a32 100644 --- a/docs/DISCOVERABLE_PARTITIONS.md +++ b/docs/DISCOVERABLE_PARTITIONS.md @@ -306,11 +306,9 @@ installation processes of Linux a bit more robust and self-descriptive. ### Why did you only define the root partition for these listed architectures? -The automatic discovery of the root partition is defined to operate on the disk -containing the current EFI System Partition (ESP). Since EFI only exists on -x86, x86-64, ia64, ARM, LoongArch and RISC-V so far, we only defined root -partition UUIDs for these architectures. Should EFI become more common on -other architectures, we can define additional UUIDs for them. +Please submit a patch that adds appropriate partition type UUIDs for the +architecture of your choice should they be missing so far. The only reason they +aren't defined yet is that nobody submitted them yet. ### Why define distinct root partition UUIDs for the various architectures? diff --git a/docs/PORTING_TO_NEW_ARCHITECTURES.md b/docs/PORTING_TO_NEW_ARCHITECTURES.md new file mode 100644 index 0000000000..964eccb854 --- /dev/null +++ b/docs/PORTING_TO_NEW_ARCHITECTURES.md @@ -0,0 +1,61 @@ +--- +title: Porting to New Architectures +category: Contributing +layout: default +SPDX-License-Identifier: LGPL-2.1-or-later +--- + +# Porting systemd to New Architectures + +Here's a brief checklist of things to implement when porting systemd to a new +architecture. + +1. Patch + [src/basic/architecture.h](https://github.com/systemd/systemd/blob/main/src/basic/architecture.h) + and + [src/basic/architecture.c](https://github.com/systemd/systemd/blob/main/src/basic/architecture.c) + to make your architecture known to systemd. Besides an `ARCHITECTURE_XYZ` + enumeration entry you need to provide an implementation of + `native_architecture()` and `uname_architecture()`. + +2. Patch + [src/shared/gpt.h](https://github.com/systemd/systemd/blob/main/src/shared/gpt.h) + and + [src/shared/gpt.c](https://github.com/systemd/systemd/blob/main/src/shared/gpt.c) + and define a new set of GPT partition type UUIDs for the root file system, + `/usr/` file system, and the matching Verity and Verity signature + partitions. Use `systemd-id128 new -p` to generate new suitable UUIDs you + can use for this. Make sure to register your new types in the various + functions in `gpt.c`. Also make sure to update the tables in + `docs/DISCOVERABLE_PARTITIONS.md` and `man/systemd-gpt-auto-generator.xml` + accordingly. + +3. If your architecture supports UEFI, make sure to update the `efi_arch` + variable logic in `meson.build` to be set to the right architecture string + as defined by the UEFI specification. (This ensures that `systemd-boot` will + be built as the appropriately named `BOOT.EFI` binary.) Also, if your + architecture uses a special boot protocol for the Linux kernel make sure to + implement it in `src/boot/efi/linux*.c`, so that the `systemd-stub` EFI stub + can work. + +4. Make sure to register the right system call numbers for your architecture in + `src/basic/missing_syscall_def.h`. systemd uses various system calls the + Linux kernel provides that are currently not wrapped by glibc (or are only + in very new glibc), and we need to know the right numbers for them. It might + also be necessary to tweak `src/basic/raw-clone.h`. + +5. Make sure the code in `src/shared/seccomp-util.c` properly understands the + local architecture and its system call quirks. + +6. If your architecture uses a `/lib64/` library directory, then make sure that + the `BaseFilesystem` table in `src/shared/base-filesystem.c` has an entry + for it so that it can be set up automatically if missing. This is useful to + support booting into OS trees that have an empty root directory with only + `/usr/` mounted in. + +7. If your architecture has a CPU opcode similar to x86' RDRAND consider adding + native support for it to `src/basic/random-util.c`'s `rdrand()` function. + +8. If your architecture supports VM virtualization and provides CPU opcodes + similar to x86' CPUID consider adding native support for detecting VMs this + way to `src/basic/virt.c`. diff --git a/src/basic/architecture.c b/src/basic/architecture.c index e5dafb9814..4f5c5b86a6 100644 --- a/src/basic/architecture.c +++ b/src/basic/architecture.c @@ -106,8 +106,7 @@ int uname_architecture(void) { { "crisv32", ARCHITECTURE_CRIS }, #elif defined(__nios2__) { "nios2", ARCHITECTURE_NIOS2 }, -#elif defined(__riscv__) || defined(__riscv) - /* __riscv__ is obsolete, remove in 2018 */ +#elif defined(__riscv) { "riscv32", ARCHITECTURE_RISCV32 }, { "riscv64", ARCHITECTURE_RISCV64 }, # if __SIZEOF_POINTER__ == 4 diff --git a/src/basic/architecture.h b/src/basic/architecture.h index 9abc1831da..2126c79898 100644 --- a/src/basic/architecture.h +++ b/src/basic/architecture.h @@ -210,8 +210,7 @@ int uname_architecture(void); #elif defined(__nios2__) # define native_architecture() ARCHITECTURE_NIOS2 # define LIB_ARCH_TUPLE "nios2-linux-gnu" -#elif defined(__riscv__) || defined(__riscv) - /* __riscv__ is obsolete, remove in 2018 */ +#elif defined(__riscv) # if __SIZEOF_POINTER__ == 4 # define native_architecture() ARCHITECTURE_RISCV32 # define LIB_ARCH_TUPLE "riscv32-linux-gnu" diff --git a/src/shared/base-filesystem.c b/src/shared/base-filesystem.c index 016eb7b82a..47c1ea2802 100644 --- a/src/shared/base-filesystem.c +++ b/src/shared/base-filesystem.c @@ -20,10 +20,10 @@ #include "user-util.h" typedef struct BaseFilesystem { - const char *dir; + const char *dir; /* directory or symlink to create */ mode_t mode; - const char *target; - const char *exists; + const char *target; /* if non-NULL create as symlink to this target */ + const char *exists; /* conditionalize this entry on existance of this file */ bool ignore_failure; } BaseFilesystem; @@ -39,11 +39,26 @@ static const BaseFilesystem table[] = { { "sys", 0755, NULL, NULL, true }, { "dev", 0755, NULL, NULL, true }, #if defined(__i386__) || defined(__x86_64__) + /* Various architecture ABIs define the path to the dynamic loader via the /lib64/ subdirectory of + * the root directory. When booting from an otherwise empty root file system (where only /usr/ has + * been mounted into) it is thus necessary to create a symlink pointing to the right subdirectory of + * /usr/ first — otherwise we couldn't invoke any dynamic binary. Let's detect this case here, and + * create the symlink as needed should it be missing. We prefer doing this consistently with Debian's + * multiarch logic, but support Fedora-style multilib too.*/ { "lib64", 0, "usr/lib/x86_64-linux-gnu\0" "usr/lib64\0", "ld-linux-x86-64.so.2" }, +#else + /* gcc doesn't allow pragma to be used within constructs, hence log about this separately below */ +# define WARN_LIB64 1 #endif }; +#ifdef WARN_LIB64 +#pragma message "If your architecture knows a /lib64/ or /lib32/ directory, please add an entry creating it here." + /* And if your architecture doesn't know these directories, make sure to add ifdeffery here to + * suppress this pragma message. */ +#endif + int base_filesystem_create(const char *root, uid_t uid, gid_t gid) { _cleanup_close_ int fd = -1; int r; diff --git a/src/shared/gpt.c b/src/shared/gpt.c index a2e39dc1a1..0459ce5bf1 100644 --- a/src/shared/gpt.c +++ b/src/shared/gpt.c @@ -4,6 +4,16 @@ #include "string-util.h" #include "utf8.h" +/* Gently push people towards defining GPT type UUIDs for all architectures we know */ +#if !defined(GPT_ROOT_NATIVE) || \ + !defined(GPT_ROOT_NATIVE_VERITY) || \ + !defined(GPT_ROOT_NATIVE_VERITY_SIG) || \ + !defined(GPT_USR_NATIVE) || \ + !defined(GPT_USR_NATIVE_VERITY) || \ + !defined(GPT_USR_NATIVE_VERITY_SIG) +#pragma message "Please define GPT partition types for your architecture." +#endif + const GptPartitionType gpt_partition_type_table[] = { { GPT_ROOT_X86, "root-x86" }, { GPT_ROOT_X86_VERITY, "root-x86-verity" },