treewide: implement basic aarch64 support

This adds aarch64 platforms, and some fixes for aarch64 support. This is
not yet complete; e.g. toolchains for aarch64 targets are still missing.

I renamed the amd64 platforms to x86_64 and efi to uefi for consistency
with @platforms.

syscall.Dup2 does not exist on arm64, but unix.Dup2 does.

Change-Id: I3ab081b2b852945b723ec83768f79000b8c4def4
Reviewed-on: https://review.monogon.dev/c/monogon/+/4173
Reviewed-by: Lorenz Brun <lorenz@monogon.tech>
Tested-by: Jenkins CI
diff --git a/.bazelrc b/.bazelrc
index d4e676e..b72e72f 100644
--- a/.bazelrc
+++ b/.bazelrc
@@ -34,7 +34,7 @@
 build:remote --noremote_upload_local_results
 
 # Set the execution platform which adds constraints for the scheduler.
-build:remote --extra_execution_platforms=//build/platforms:remote_amd64
+build:remote --extra_execution_platforms=//build/platforms:remote_x86_64
 
 # Enable pure by default. Specific go_binary targets which need cgo should set
 # `pure = "off"`.
@@ -94,13 +94,13 @@
 # In our monorepo, we mostly ignore the host platform since we bring our own
 # execution environment. However, we still need to run a small number of tools
 # such as gazelle.
-build --host_platform=//build/platforms:linux_amd64
+build --host_platform=//build/platforms:linux_x86_64
 
 # Target platform for the monorepo is currently the same as the host platform,
 # but we'll support cross-compilation at some point. Do not rely on it.
-build --platforms=//build/platforms:linux_amd64
+build --platforms=//build/platforms:linux_x86_64
 # Make sure our platform is picked instead of the --host_platform.
-build --extra_execution_platforms=//build/platforms:linux_amd64
+build --extra_execution_platforms=//build/platforms:linux_x86_64
 
 # Build resources
 startup --batch_cpu_scheduling --io_nice_level 7
diff --git a/build/platforms/BUILD.bazel b/build/platforms/BUILD.bazel
index 293af9b..028bb9a 100644
--- a/build/platforms/BUILD.bazel
+++ b/build/platforms/BUILD.bazel
@@ -1,6 +1,6 @@
-# Generic platform for Linux x86_64 targets.
+# Generic platform for Linux targets.
 platform(
-    name = "linux_amd64",
+    name = "linux_x86_64",
     constraint_values = [
         "@platforms//os:linux",
         "@platforms//cpu:x86_64",
@@ -8,9 +8,18 @@
     visibility = ["//visibility:public"],
 )
 
-# EFI preboot environment for x86_64 machines.
 platform(
-    name = "efi_amd64",
+    name = "linux_aarch64",
+    constraint_values = [
+        "@platforms//os:linux",
+        "@platforms//cpu:aarch64",
+    ],
+    visibility = ["//visibility:public"],
+)
+
+# EFI preboot environment.
+platform(
+    name = "uefi_x86_64",
     constraint_values = [
         "@platforms//os:uefi",
         "@platforms//cpu:x86_64",
@@ -19,10 +28,20 @@
 )
 
 platform(
-    name = "remote_amd64",
+    name = "uefi_aarch64",
     constraint_values = [
-        "@platforms//cpu:x86_64",
+        "@platforms//os:uefi",
+        "@platforms//cpu:aarch64",
+    ],
+    visibility = ["//visibility:public"],
+)
+
+# Remote execution platform.
+platform(
+    name = "remote_x86_64",
+    constraint_values = [
         "@platforms//os:linux",
+        "@platforms//cpu:x86_64",
     ],
     exec_properties = {
         "container-image": "docker://gcr.io/monogon-infra/sandbox",
diff --git a/build/toolchain/llvm-efi/transition.bzl b/build/toolchain/llvm-efi/transition.bzl
deleted file mode 100644
index 9c222e6..0000000
--- a/build/toolchain/llvm-efi/transition.bzl
+++ /dev/null
@@ -1,15 +0,0 @@
-def _build_efi_transition_impl(_settings, _attr):
-    """
-    Transition that enables building for an EFI environment. Currently only supports C code.
-    """
-    return {
-        "//command_line_option:platforms": "//build/platforms:efi_amd64",
-    }
-
-build_efi_transition = transition(
-    implementation = _build_efi_transition_impl,
-    inputs = [],
-    outputs = [
-        "//command_line_option:platforms",
-    ],
-)
diff --git a/metropolis/node/core/abloader/BUILD.bazel b/metropolis/node/core/abloader/BUILD.bazel
index b59d035..1210368 100644
--- a/metropolis/node/core/abloader/BUILD.bazel
+++ b/metropolis/node/core/abloader/BUILD.bazel
@@ -5,7 +5,10 @@
     name = "abloader_bin",
     srcs = ["main.rs"],
     edition = "2021",
-    platform = "//build/platforms:efi_amd64",
+    platform = select({
+        "@platforms//cpu:x86_64": "//build/platforms:uefi_x86_64",
+        "@platforms//cpu:aarch64": "//build/platforms:uefi_aarch64",
+    }),
     # rust_binary depends on the status files by default, even if no stamp
     # variables are used, which causes unnecessary rebuilds when the stable
     # status file changes.
diff --git a/metropolis/node/kubernetes/pause/BUILD.bazel b/metropolis/node/kubernetes/pause/BUILD.bazel
index 24a4b54..69529b1 100644
--- a/metropolis/node/kubernetes/pause/BUILD.bazel
+++ b/metropolis/node/kubernetes/pause/BUILD.bazel
@@ -20,7 +20,10 @@
 
 oci_image(
     name = "pause_image",
-    architecture = "amd64",
+    architecture = select({
+        "@platforms//cpu:x86_64": "amd64",
+        "@platforms//cpu:aarch64": "arm64",
+    }),
     entrypoint = ["/app/metropolis/node/kubernetes/pause/pause"],
     os = "linux",
     tars = [":pause_layer"],
diff --git a/osbase/bringup/bringup.go b/osbase/bringup/bringup.go
index 6373b64..8fcb8fe 100644
--- a/osbase/bringup/bringup.go
+++ b/osbase/bringup/bringup.go
@@ -18,7 +18,6 @@
 	"runtime/debug"
 	"strings"
 	"sync/atomic"
-	"syscall"
 	"time"
 
 	"github.com/opencontainers/runc/libcontainer/cgroups"
@@ -190,7 +189,7 @@
 	var wErr, fErr error
 	wErr = wConn.Control(func(wFd uintptr) {
 		fErr = fConn.Control(func(fFd uintptr) {
-			err = syscall.Dup2(int(wFd), int(fFd))
+			err = unix.Dup2(int(wFd), int(fFd))
 		})
 	})
 
diff --git a/osbase/build/mkpayload/def.bzl b/osbase/build/mkpayload/def.bzl
index fe7cf74..fa10e83 100644
--- a/osbase/build/mkpayload/def.bzl
+++ b/osbase/build/mkpayload/def.bzl
@@ -3,7 +3,6 @@
 See https://systemd.io/BOOT_LOADER_SPECIFICATION/#type-2-efi-unified-kernel-images for more information.
 """
 
-load("//build/toolchain/llvm-efi:transition.bzl", "build_efi_transition")
 load("//osbase/build/mkverity:def.bzl", "VerityInfo")
 
 def _efi_unified_kernel_image_impl(ctx):
@@ -113,8 +112,6 @@
             doc = "The stub executable itself as a PE/COFF executable.",
             default = "@efistub//:efistub",
             allow_single_file = True,
-            executable = True,
-            cfg = build_efi_transition,
         ),
         "verity": attr.label(
             doc = "The DeviceMapper Verity rootfs target table.",
diff --git a/third_party/efistub/efistub.bzl b/third_party/efistub/efistub.bzl
index 80c8e40..d0e2a2f 100644
--- a/third_party/efistub/efistub.bzl
+++ b/third_party/efistub/efistub.bzl
@@ -1,7 +1,8 @@
+load("@aspect_bazel_lib//lib:transitions.bzl", "platform_transition_filegroup")
 load("@rules_cc//cc:defs.bzl", "cc_binary")
 
 cc_binary(
-    name = "efistub",
+    name = "efistub_bin",
     srcs = [("src/boot/efi/%s" % v) for v in [
         "assert.c",
         "cpio.c",
@@ -18,5 +19,18 @@
     includes = ["src/fundamental"],
     copts = ["-std=gnu99", "-DSD_BOOT", "-DGIT_VERSION=\\\"0.0.0-mngn\\\""],
     deps = ["@gnuefi//:gnuefi"],
+    target_compatible_with = [
+        "@platforms//os:uefi",
+    ],
+    visibility = ["//visibility:private"],
+)
+
+platform_transition_filegroup(
+    name = "efistub",
+    srcs = [":efistub_bin"],
+    target_platform = select({
+        "@platforms//cpu:x86_64": "@//build/platforms:uefi_x86_64",
+        "@platforms//cpu:aarch64": "@//build/platforms:uefi_aarch64",
+    }),
     visibility = ["//visibility:public"],
 )