Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion api/docs/intro.dox
Original file line number Diff line number Diff line change
Expand Up @@ -470,7 +470,9 @@ preferred client library base in the low 4GB. The \ref op_reachable_client
"-reachable_client runtime option" can be used to remove this guarantee.
The option is automatically turned off when DynamoRIO and clients are
statically linked with the application: for such static usage, 32-bit
reachability to the code cache by clients is not guaranteed.
reachability to the code cache by clients is not guaranteed. It is also
disabled on macOS, where the lack of a private loader means we cannot
control where the client library gets loaded.

The net result is that any static data or code in a client library, or any
data allocated using DynamoRIO's API routines (except dr_raw_mem_alloc() or
Expand Down
4 changes: 3 additions & 1 deletion core/optionsx.h
Original file line number Diff line number Diff line change
Expand Up @@ -1674,7 +1674,9 @@ OPTION_DEFAULT(bool, reachable_heap, false,
"guarantee that all heap memory is 32-bit-displacement "
"reachable from the code cache.")
/* i#3570: For static DR we do not guarantee reachability. */
OPTION_DEFAULT(bool, reachable_client, IF_STATIC_LIBRARY_ELSE(false, true),
/* i#7296: On macOS we have no private loader and cannot realiably alloc near client */
OPTION_DEFAULT(bool, reachable_client,
IF_STATIC_LIBRARY_ELSE(false, IF_MACOS_ELSE(false, true)),
"guarantee that clients are reachable from the code cache.")
#endif
/* XXX i#3566: Support for W^X has some current limitations:
Expand Down
14 changes: 12 additions & 2 deletions core/unix/signal.c
Original file line number Diff line number Diff line change
Expand Up @@ -7696,8 +7696,6 @@ os_forge_exception(app_pc target_pc, dr_exception_type_t type)
sigframe_rt_t *frame = (sigframe_rt_t *)frame_no_xstate;
int sig;
dr_where_am_i_t cur_whereami = dcontext->whereami;
kernel_ucontext_t *uc = get_ucontext_from_rt_frame(frame);
sigcontext_t *sc = SIGCXT_FROM_UCXT(uc);
switch (type) {
case ILLEGAL_INSTRUCTION_EXCEPTION: sig = SIGILL; break;
case UNREADABLE_MEMORY_EXECUTION_EXCEPTION: sig = SIGSEGV; break;
Expand All @@ -7715,6 +7713,18 @@ os_forge_exception(app_pc target_pc, dr_exception_type_t type)
* to a plain frame on delivery.
*/
memset(frame, 0, sizeof(*frame));

kernel_ucontext_t *uc = get_ucontext_from_rt_frame(frame);
#if defined(MACOS)
/* Since SIGCXT_FROM_UCXT just accesses the uc->uc_mcontext ptr field on
* macOS, sc will be NULL below if we do not initialize uc_mcontext first.
* On macOS, the uc_mcontext pointer always just points to the mcontext
* elsewhere in the frame.
*/
uc->IF_X64_ELSE(uc_mcontext64, uc_mcontext) = (void *)&frame->mc;
#endif
sigcontext_t *sc = SIGCXT_FROM_UCXT(uc);

frame->info.si_signo = sig;
/* Set si_code to match what would happen natively. We also need this to
* avoid the !is_sys_kill() check in record_pending_signal() to avoid an
Expand Down
6 changes: 4 additions & 2 deletions suite/tests/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -6173,13 +6173,15 @@ if (NOT ARM) # FIXME i#1551: fix bugs on ARM
endif ()
endif (NOT ARM)

if (X86 OR AARCH64) # FIXME i#1551: port asm to ARM
# FIXME i#1551: port asm to ARM
# FIXME i#5383: selfmod tests fail to build on macOS + ARM64
if (X86 OR AARCH64 AND NOT (APPLE AND AARCH64))
tobuild(security-common.selfmod2 security-common/selfmod2.c)
tochcon(security-common.selfmod2 textrel_shlib_t)

tobuild(security-common.selfmod security-common/selfmod.c)
tochcon(security-common.selfmod textrel_shlib_t)
endif (X86 OR AARCH64)
endif (X86 OR AARCH64 AND NOT (APPLE AND AARCH64))

if (X86) # FIXME i#1551, i#1569: port asm to ARM and AArch64
if (NOT APPLE) # XXX i#58: port test to MacOS
Expand Down
8 changes: 6 additions & 2 deletions suite/tests/client-interface/cbr-retarget.c
Original file line number Diff line number Diff line change
Expand Up @@ -62,9 +62,13 @@ main(void)
}
;
#elif defined(AARCH64)
__asm("cbnz xzr, skip");
__asm("cbnz xzr, 1f");
# ifdef MACOS
__asm("bl _foo");
# else
__asm("bl foo");
__asm("skip:");
# endif
__asm("1:");
#else
__asm("movl $0x0, %ecx");
__asm("cmp $0x0, %ecx");
Expand Down
4 changes: 3 additions & 1 deletion suite/tests/client-interface/strace.dll.c
Original file line number Diff line number Diff line change
Expand Up @@ -349,7 +349,9 @@ event_post_syscall(void *drcontext, int sysnum)
static int
get_write_sysnum(void)
{
#ifdef UNIX
#if defined(MACOS)
return SYS_write_nocancel;
#elif defined(UNIX)
return SYS_write;
#else
byte *entry;
Expand Down
9 changes: 6 additions & 3 deletions suite/tests/linux/mangle_pauth.c
Original file line number Diff line number Diff line change
Expand Up @@ -109,8 +109,10 @@ handle_signal(int signal, siginfo_t *siginfo, ucontext_t *ucxt)
* We need to strip the PAC from from the fault address to canonicalize it and
* compare it to the expected branch target address.
*/
const uintptr_t fault_pc = strip_pac(ucxt->uc_mcontext.pc);
LOG(" ucxt->uc_mcontext.pc = " PFX "\n", ucxt->uc_mcontext.pc);
const uintptr_t pc =
IF_MACOS_ELSE(ucxt->uc_mcontext->__ss.__pc, ucxt->uc_mcontext.pc);
const uintptr_t fault_pc = strip_pac(pc);
LOG(" ucxt->uc_mcontext.pc = " PFX "\n", pc);
LOG(" fault_pc = " PFX "\n", fault_pc);
LOG(" branch_target_addr = " PFX "\n", branch_target_addr);
if (fault_pc == branch_target_addr)
Expand All @@ -123,7 +125,8 @@ handle_signal(int signal, siginfo_t *siginfo, ucontext_t *ucxt)
/* CPU has FEAT_FPACCOMBINE so the branch instruction generated an authentication
* failure exception and the fault PC should match the branch instruction address.
*/
const uintptr_t fault_pc = ucxt->uc_mcontext.pc;
const uintptr_t fault_pc =
IF_MACOS_ELSE(ucxt->uc_mcontext->__ss.__pc, ucxt->uc_mcontext.pc);
LOG(" fault_pc = " PFX "\n", fault_pc);
LOG(" branch_instr_addr = " PFX "\n", branch_instr_addr);
if (fault_pc == branch_instr_addr)
Expand Down
6 changes: 5 additions & 1 deletion suite/tests/tools.c
Original file line number Diff line number Diff line change
Expand Up @@ -526,6 +526,9 @@ set_check_signal_mask(sigset_t *mask, sigset_t *returned_mask)
void
dump_ucontext(ucontext_t *ucxt, bool is_sve, int vl_bytes)
{
# ifdef MACOS
assert(false); /* NYI */
# else
struct _aarch64_ctx *head = (struct _aarch64_ctx *)(ucxt->uc_mcontext.RESERVED);
assert(head->magic == FPSIMD_MAGIC);
assert(head->size == sizeof(struct fpsimd_context));
Expand All @@ -541,7 +544,7 @@ dump_ucontext(ucontext_t *ucxt, bool is_sve, int vl_bytes)
}
print("\n");

# ifndef DR_HOST_NOT_TARGET
# ifndef DR_HOST_NOT_TARGET
if (is_sve) {
size_t offset = sizeof(struct fpsimd_context);
struct _aarch64_ctx *next_head =
Expand Down Expand Up @@ -621,6 +624,7 @@ dump_ucontext(ucontext_t *ucxt, bool is_sve, int vl_bytes)
next_head = (struct _aarch64_ctx *)(ucxt->uc_mcontext.RESERVED + offset);
}
}
# endif
# endif
}
# endif
Expand Down
Loading