Skip to content

Commit 007b5dd

Browse files
pccrocallahan
authored andcommitted
Simplify logic for setting __aarch64_have_lse_atomics
When using a non-glibc loader (e.g. musl), __aarch64_ldadd4_relax will not necessarily be present, but the loader could still be using other outlined atomic functions, so the search for __aarch64_ldadd4_relax would not necessarily succeed. Therefore, remove the logic for disassembling __aarch64_ldadd4_relax, and replace it with code that sets __aarch64_have_lse_atomics directly. This logic was considered necessary because __aarch64_have_lse_atomics isn't exported. However, __aarch64_ldadd4_relax isn't exported either. So either way, the symbol should be findable via .symtab if it is present. It's possible that this wouldn't have worked before because of the bug fixed by #4035.
1 parent 035e5e8 commit 007b5dd

1 file changed

Lines changed: 7 additions & 76 deletions

File tree

src/Monkeypatcher.cc

Lines changed: 7 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -1625,79 +1625,6 @@ void Monkeypatcher::unpatch_dl_runtime_resolves(RecordTask* t) {
16251625
saved_dl_runtime_resolve_code.clear();
16261626
}
16271627

1628-
// https://documentation-service.arm.com/static/67581b3355451e3c38d97c22
1629-
static bool is_aarch64_bti(uint32_t instruction) {
1630-
if ((instruction >> 12) == 0b11010101000000110010 && (instruction & 0x1f) == 0b11111) {
1631-
// Hint instruction.
1632-
uint32_t crm = (instruction >> 8) & ((1 << 4) - 1);
1633-
uint32_t op2 = (instruction >> 5) & ((1 << 3) - 1);
1634-
return crm == 0b0100 && (op2 & 1) == 0;
1635-
}
1636-
return false;
1637-
}
1638-
1639-
static bool is_aarch64_adrp(uint32_t instruction, remote_ptr<void> pc, remote_ptr<void>* address) {
1640-
if ((instruction >> 31) == 1 && ((instruction >> 24) & 0x1f) == 0b10000) {
1641-
uint64_t base = (pc.as_int() >> 12) << 12;
1642-
uint64_t imm = ((instruction >> 29) & 0x3) +
1643-
(((instruction >> 5) & ((1 << 19) - 1)) << 2);
1644-
*address = remote_ptr<void>(base + (imm << 12));
1645-
return true;
1646-
}
1647-
return false;
1648-
}
1649-
1650-
static bool is_aarch64_ldrb(uint32_t instruction, uint32_t* offset) {
1651-
if ((instruction >> 22) == 0b0011100101) {
1652-
*offset = (instruction >> 10) & ((1 << 12) - 1);
1653-
return true;
1654-
}
1655-
return false;
1656-
}
1657-
1658-
/**
1659-
* Patch the __aarch64_have_lse_atomics variable to ensure that LSE atomics are
1660-
* always used even if init_lse_atomics
1661-
*/
1662-
void Monkeypatcher::patch_aarch64_have_lse_atomics(
1663-
RecordTask* t, ElfReader& reader, uintptr_t ldadd4_addr,
1664-
remote_ptr<void> map_start, size_t map_size, size_t map_offset,
1665-
uint64_t prot) {
1666-
ASSERT(t, t->arch() == aarch64);
1667-
remote_ptr<void> addr =
1668-
resolve_address(reader, ldadd4_addr, map_start, map_size, map_offset, prot);
1669-
if (!addr) {
1670-
return;
1671-
}
1672-
1673-
bool ok = true;
1674-
uint8_t instruction_bytes[12];
1675-
t->read_bytes_helper(addr, sizeof(instruction_bytes), instruction_bytes, &ok);
1676-
if (!ok) {
1677-
LOG(warn) << "Can't read ldadd4 instruction bytes at " << addr;
1678-
return;
1679-
}
1680-
uint32_t instructions[3];
1681-
memcpy(instructions, instruction_bytes, sizeof(instructions));
1682-
int index = 0;
1683-
if (is_aarch64_bti(instructions[0])) {
1684-
++index;
1685-
}
1686-
remote_ptr<void> adrp_address;
1687-
if (!is_aarch64_adrp(instructions[index], addr + index*4, &adrp_address)) {
1688-
LOG(warn) << "Instruction 0x" << HEX(instructions[index]) << " is not ADRP";
1689-
return;
1690-
}
1691-
uint32_t ldrb_offset;
1692-
if (!is_aarch64_ldrb(instructions[index + 1], &ldrb_offset)) {
1693-
LOG(warn) << "Instruction 0x" << HEX(instructions[index + 1]) << " is not LDRB";
1694-
return;
1695-
}
1696-
remote_ptr<void> have_lse_atomics_addr = adrp_address + ldrb_offset;
1697-
uint8_t enable = 1;
1698-
write_and_record_mem(t, have_lse_atomics_addr.cast<uint8_t>(), &enable, 1);
1699-
}
1700-
17011628
static bool file_may_need_instrumentation(const AddressSpace::Mapping& map) {
17021629
size_t file_part = map.map.fsname().rfind('/');
17031630
if (file_part == string::npos) {
@@ -1791,9 +1718,13 @@ void Monkeypatcher::patch_after_mmap(RecordTask* t, remote_ptr<void> start,
17911718
break;
17921719
case aarch64:
17931720
for (size_t i = 0; i < syms.size(); ++i) {
1794-
if (syms.is_name(i, "__aarch64_ldadd4_relax")) {
1795-
patch_aarch64_have_lse_atomics(t, reader, syms.addr(i), start, size,
1796-
offset_bytes, prot);
1721+
if (syms.is_name(i, "__aarch64_have_lse_atomics")) {
1722+
// Patch the __aarch64_have_lse_atomics variable to ensure that LSE
1723+
// atomics are always used even if init_lse_atomics hasn't been called
1724+
// yet (or at all).
1725+
static const char one = 1;
1726+
set_and_record_bytes(t, reader, syms.addr(i), &one, sizeof(one),
1727+
start, size, offset_bytes, prot);
17971728
}
17981729
}
17991730
break;

0 commit comments

Comments
 (0)