From 4980fdc8aae7c79119b59c731b1164972bfd0936 Mon Sep 17 00:00:00 2001 From: Artyom Tetyukhin <51746822+arttet@users.noreply.github.com> Date: Sun, 3 Sep 2023 06:55:53 +0400 Subject: [PATCH] write/macho: Support the arm64e architecture for macOS/iOS (#574) --- src/elf.rs | 1 + src/write/coff.rs | 2 +- src/write/elf/object.rs | 2 +- src/write/macho.rs | 16 ++++++++++++++-- src/write/mod.rs | 5 +++++ src/write/xcoff.rs | 2 +- 6 files changed, 23 insertions(+), 5 deletions(-) diff --git a/src/elf.rs b/src/elf.rs index da68ec2d..f202c598 100644 --- a/src/elf.rs +++ b/src/elf.rs @@ -1921,6 +1921,7 @@ pub const GNU_PROPERTY_HIUSER: u32 = 0xffffffff; /// AArch64 specific GNU properties. pub const GNU_PROPERTY_AARCH64_FEATURE_1_AND: u32 = 0xc0000000; +pub const GNU_PROPERTY_AARCH64_FEATURE_PAUTH: u32 = 0xc0000001; pub const GNU_PROPERTY_AARCH64_FEATURE_1_BTI: u32 = 1 << 0; pub const GNU_PROPERTY_AARCH64_FEATURE_1_PAC: u32 = 1 << 1; diff --git a/src/write/coff.rs b/src/write/coff.rs index d2f7ccc6..2277a08e 100644 --- a/src/write/coff.rs +++ b/src/write/coff.rs @@ -83,7 +83,7 @@ impl<'a> Object<'a> { name } - pub(crate) fn coff_fixup_relocation(&mut self, mut relocation: &mut Relocation) -> i64 { + pub(crate) fn coff_fixup_relocation(&mut self, relocation: &mut Relocation) -> i64 { if relocation.kind == RelocationKind::GotRelative { // Use a stub symbol for the relocation instead. // This isn't really a GOT, but it's a similar purpose. diff --git a/src/write/elf/object.rs b/src/write/elf/object.rs index acc820c9..421d23a8 100644 --- a/src/write/elf/object.rs +++ b/src/write/elf/object.rs @@ -152,7 +152,7 @@ impl<'a> Object<'a> { }) } - pub(crate) fn elf_fixup_relocation(&mut self, mut relocation: &mut Relocation) -> Result { + pub(crate) fn elf_fixup_relocation(&mut self, relocation: &mut Relocation) -> Result { // Return true if we should use a section symbol to avoid preemption. fn want_section_symbol(relocation: &Relocation, symbol: &Symbol) -> bool { if symbol.scope != SymbolScope::Dynamic { diff --git a/src/write/macho.rs b/src/write/macho.rs index e3ce55bb..05c376cf 100644 --- a/src/write/macho.rs +++ b/src/write/macho.rs @@ -48,6 +48,14 @@ impl MachOBuildVersion { // Public methods. impl<'a> Object<'a> { + /// Specify the Mach-O CPU subtype. + /// + /// Requires `feature = "macho"`. + #[inline] + pub fn set_macho_cpu_subtype(&mut self, cpu_subtype: u32) { + self.macho_cpu_subtype = Some(cpu_subtype); + } + /// Specify information for a Mach-O `LC_BUILD_VERSION` command. /// /// Requires `feature = "macho"`. @@ -243,7 +251,7 @@ impl<'a> Object<'a> { init_symbol_id } - pub(crate) fn macho_fixup_relocation(&mut self, mut relocation: &mut Relocation) -> i64 { + pub(crate) fn macho_fixup_relocation(&mut self, relocation: &mut Relocation) -> i64 { let constant = match relocation.kind { // AArch64Call relocations have special handling for the addend, so don't adjust it RelocationKind::Relative if relocation.encoding == RelocationEncoding::AArch64Call => 0, @@ -385,7 +393,7 @@ impl<'a> Object<'a> { .map_err(|_| Error(String::from("Cannot allocate buffer")))?; // Write file header. - let (cputype, cpusubtype) = match self.architecture { + let (cputype, mut cpusubtype) = match self.architecture { Architecture::Arm => (macho::CPU_TYPE_ARM, macho::CPU_SUBTYPE_ARM_ALL), Architecture::Aarch64 => (macho::CPU_TYPE_ARM64, macho::CPU_SUBTYPE_ARM64_ALL), Architecture::Aarch64_Ilp32 => { @@ -403,6 +411,10 @@ impl<'a> Object<'a> { } }; + if let Some(cpu_subtype) = self.macho_cpu_subtype { + cpusubtype = cpu_subtype; + } + let flags = match self.flags { FileFlags::MachO { flags } => flags, _ => 0, diff --git a/src/write/mod.rs b/src/write/mod.rs index 711ff16d..15ca29d7 100644 --- a/src/write/mod.rs +++ b/src/write/mod.rs @@ -75,6 +75,9 @@ pub struct Object<'a> { pub mangling: Mangling, /// Mach-O "_tlv_bootstrap" symbol. tlv_bootstrap: Option, + /// Mach-O CPU subtype. + #[cfg(feature = "macho")] + macho_cpu_subtype: Option, #[cfg(feature = "macho")] macho_build_version: Option, } @@ -96,6 +99,8 @@ impl<'a> Object<'a> { mangling: Mangling::default(format, architecture), tlv_bootstrap: None, #[cfg(feature = "macho")] + macho_cpu_subtype: None, + #[cfg(feature = "macho")] macho_build_version: None, } } diff --git a/src/write/xcoff.rs b/src/write/xcoff.rs index 6c9a8038..fc58886e 100644 --- a/src/write/xcoff.rs +++ b/src/write/xcoff.rs @@ -66,7 +66,7 @@ impl<'a> Object<'a> { } } - pub(crate) fn xcoff_fixup_relocation(&mut self, mut relocation: &mut Relocation) -> i64 { + pub(crate) fn xcoff_fixup_relocation(&mut self, relocation: &mut Relocation) -> i64 { let constant = match relocation.kind { RelocationKind::Relative => relocation.addend + 4, _ => relocation.addend,