Follow-up from epic #40 / PR #58. The Mach-O parser handles thin
64-bit Mach-O only. Release artifacts are per-architecture thin
(`arm64-osx`, `x64-osx` triplets), so the gap is acceptable today,
but anyone consuming a universal binary (e.g. a Homebrew formula
that bundles both architectures) would fail to pack.
Scope
Extend `LocateFlapiSectionInBuffer` and `LocateFlapiSection` to
handle:
- `FAT_MAGIC` / `FAT_MAGIC_64` wrappers (`0xcafebabe` /
`0xcafebabf`) — parse `fat_header` + `fat_arch[]` (or
`fat_arch_64[]`), pick a slice (current architecture preferred,
else the first slice), recurse into the inner Mach-O.
- 32-bit Mach-O (`MH_MAGIC` 0xfeedface). The parser already
has `LC_SEGMENT` skeleton code but isn't exercised. If we don't
ship 32-bit artifacts, we can also just reject these explicitly.
`OverwriteFlapiSection` needs the same handling — it has to write
into the correct slice's section. Locating the section is no longer
enough; we need the slice's byte offset within the fat file so the
write goes to the right place.
Acceptance
- 3 new test cases in `test/cpp/macho_bundle_test.cpp`:
- Fat binary with one arm64 slice containing `__FLAPI/__bundle` —
section located at the correct absolute file offset (slice
offset + section offset within slice).
- Fat binary with two slices (arm64 + x86_64), both with the
section — locator picks the matching arch, or the first if
`uname -m` doesn't match either.
- `OverwriteFlapiSection` writes to the located absolute offset
and a subsequent `LocateBundle` round-trips.
References
Follow-up from epic #40 / PR #58. The Mach-O parser handles thin
64-bit Mach-O only. Release artifacts are per-architecture thin
(`arm64-osx`, `x64-osx` triplets), so the gap is acceptable today,
but anyone consuming a universal binary (e.g. a Homebrew formula
that bundles both architectures) would fail to pack.
Scope
Extend `LocateFlapiSectionInBuffer` and `LocateFlapiSection` to
handle:
`0xcafebabf`) — parse `fat_header` + `fat_arch[]` (or
`fat_arch_64[]`), pick a slice (current architecture preferred,
else the first slice), recurse into the inner Mach-O.
has `LC_SEGMENT` skeleton code but isn't exercised. If we don't
ship 32-bit artifacts, we can also just reject these explicitly.
`OverwriteFlapiSection` needs the same handling — it has to write
into the correct slice's section. Locating the section is no longer
enough; we need the slice's byte offset within the fat file so the
write goes to the right place.
Acceptance
section located at the correct absolute file offset (slice
offset + section offset within slice).
section — locator picks the matching arch, or the first if
`uname -m` doesn't match either.
and a subsequent `LocateBundle` round-trips.
References