mirror of
https://github.com/rui314/mold.git
synced 2024-09-21 01:47:11 +03:00
[Mach-O] Fix references to dyld_stub_binder
This commit is contained in:
parent
7ce2c7edb5
commit
2c5582b9e9
@ -54,7 +54,7 @@ void StubHelperSection<ARM64>::copy_buf(Context<ARM64> &ctx) {
|
||||
buf[0] |= encode_page(page(dyld_private) - page(this->hdr.addr));
|
||||
buf[1] |= bits(dyld_private, 11, 0) << 10;
|
||||
|
||||
u64 stub_binder = get_symbol(ctx, "dyld_stub_binder")->get_addr(ctx);
|
||||
u64 stub_binder = get_symbol(ctx, "dyld_stub_binder")->get_got_addr(ctx);
|
||||
buf[3] |= encode_page(page(stub_binder) - page(this->hdr.addr - 12));
|
||||
buf[4] |= bits(stub_binder, 11, 0) << 10;
|
||||
|
||||
@ -151,7 +151,8 @@ void Subsection<ARM64>::scan_relocations(Context<ARM64> &ctx) {
|
||||
break;
|
||||
case ARM64_RELOC_TLVP_LOAD_PAGE21:
|
||||
case ARM64_RELOC_TLVP_LOAD_PAGEOFF12:
|
||||
sym->flags |= NEEDS_THREAD_PTR;
|
||||
if (sym->is_imported)
|
||||
sym->flags |= NEEDS_THREAD_PTR;
|
||||
break;
|
||||
}
|
||||
|
||||
|
@ -533,8 +533,9 @@ static int do_main(int argc, char **argv) {
|
||||
for (ObjectFile<E> *file : ctx.objs)
|
||||
file->check_duplicate_symbols(ctx);
|
||||
|
||||
bool has_pagezero_seg = ctx.arg.pagezero_size;
|
||||
for (i64 i = 0; i < ctx.segments.size(); i++)
|
||||
ctx.segments[i]->seg_idx = i + 1;
|
||||
ctx.segments[i]->seg_idx = (has_pagezero_seg ? i + 1 : i);
|
||||
|
||||
for (ObjectFile<E> *file : ctx.objs)
|
||||
for (std::unique_ptr<Subsection<E> > &subsec : file->subsections)
|
||||
|
@ -913,8 +913,13 @@ u64 Symbol<E>::get_got_addr(Context<E> &ctx) const {
|
||||
|
||||
template <typename E>
|
||||
u64 Symbol<E>::get_tlv_addr(Context<E> &ctx) const {
|
||||
assert(tlv_idx != -1);
|
||||
return ctx.thread_ptrs.hdr.addr + tlv_idx * E::word_size;
|
||||
if (is_imported) {
|
||||
assert(tlv_idx != -1);
|
||||
return ctx.thread_ptrs.hdr.addr + tlv_idx * E::word_size;
|
||||
}
|
||||
|
||||
assert(subsec);
|
||||
return subsec->get_addr(ctx) + value;
|
||||
}
|
||||
|
||||
template <typename E>
|
||||
|
@ -209,7 +209,8 @@ static std::vector<u8> create_data_in_code_cmd(Context<E> &ctx) {
|
||||
|
||||
template <typename E>
|
||||
static std::vector<u8> create_id_dylib_cmd(Context<E> &ctx) {
|
||||
std::vector<u8> buf(sizeof(DylibCommand) + ctx.arg.final_output.size() + 1);
|
||||
std::vector<u8> buf(sizeof(DylibCommand) +
|
||||
align_to(ctx.arg.final_output.size() + 1, 8));
|
||||
DylibCommand &cmd = *(DylibCommand *)buf.data();
|
||||
|
||||
cmd.cmd = LC_ID_DYLIB;
|
||||
@ -664,11 +665,12 @@ void BindSection<E>::compute_size(Context<E> &ctx) {
|
||||
ctx.data_const_seg->seg_idx,
|
||||
sym->get_got_addr(ctx) - ctx.data_const_seg->cmd.vmaddr);
|
||||
|
||||
for (Symbol<E> *sym : ctx.thread_ptrs.syms)
|
||||
if (sym->is_imported)
|
||||
enc.add(((DylibFile<E> *)sym->file)->dylib_idx, sym->name, 0,
|
||||
ctx.data_seg->seg_idx,
|
||||
sym->get_tlv_addr(ctx) - ctx.data_seg->cmd.vmaddr);
|
||||
for (Symbol<E> *sym : ctx.thread_ptrs.syms) {
|
||||
assert(sym->is_imported);
|
||||
enc.add(((DylibFile<E> *)sym->file)->dylib_idx, sym->name, 0,
|
||||
ctx.data_seg->seg_idx,
|
||||
sym->get_tlv_addr(ctx) - ctx.data_seg->cmd.vmaddr);
|
||||
}
|
||||
|
||||
enc.finish();
|
||||
|
||||
@ -1307,9 +1309,7 @@ void ThreadPtrsSection<E>::add(Context<E> &ctx, Symbol<E> *sym) {
|
||||
template <typename E>
|
||||
void ThreadPtrsSection<E>::copy_buf(Context<E> &ctx) {
|
||||
u64 *buf = (u64 *)(ctx.buf + this->hdr.offset);
|
||||
for (i64 i = 0; i < syms.size(); i++)
|
||||
if (!syms[i]->is_imported)
|
||||
buf[i] = syms[i]->get_addr(ctx);
|
||||
memset(buf, 0, this->hdr.size);
|
||||
}
|
||||
|
||||
#define INSTANTIATE(E) \
|
||||
|
37
test/macho/data-reloc.sh
Executable file
37
test/macho/data-reloc.sh
Executable file
@ -0,0 +1,37 @@
|
||||
#!/bin/bash
|
||||
export LC_ALL=C
|
||||
set -e
|
||||
CC="${TEST_CC:-cc}"
|
||||
CXX="${TEST_CXX:-c++}"
|
||||
GCC="${TEST_GCC:-gcc}"
|
||||
GXX="${TEST_GXX:-g++}"
|
||||
OBJDUMP="${OBJDUMP:-objdump}"
|
||||
MACHINE="${MACHINE:-$(uname -m)}"
|
||||
testname=$(basename "$0" .sh)
|
||||
echo -n "Testing $testname ... "
|
||||
cd "$(dirname "$0")"/../..
|
||||
t=out/test/macho/$testname
|
||||
mkdir -p $t
|
||||
|
||||
cat <<EOF | $CC -o $t/a.o -c -xc - -fPIC
|
||||
#include <stdio.h>
|
||||
|
||||
int a = 5;
|
||||
int *b = &a;
|
||||
|
||||
void print() {
|
||||
printf("%d %d\n", a, *b);
|
||||
}
|
||||
EOF
|
||||
|
||||
clang --ld-path=./ld64 -shared -o $t/b.dylib $t/a.o
|
||||
|
||||
cat <<EOF | $CC -o $t/c.o -c -xc - -fPIC
|
||||
void print();
|
||||
int main() { print(); }
|
||||
EOF
|
||||
|
||||
clang --ld-path=./ld64 -o $t/exe $t/b.dylib $t/c.o
|
||||
$t/exe | grep -q '^5 5$'
|
||||
|
||||
echo OK
|
Loading…
Reference in New Issue
Block a user