contrib: add macho branch protection check

This commit is contained in:
fanquake 2024-01-03 17:16:16 +00:00
parent 65c05db660
commit 5335e454c0
No known key found for this signature in database
GPG key ID: 2EEB9F5CC09526C1
2 changed files with 15 additions and 5 deletions

View file

@ -192,6 +192,16 @@ def check_MACHO_control_flow(binary) -> bool:
return True return True
return False return False
def check_MACHO_branch_protection(binary) -> bool:
'''
Check for branch protection instrumentation
'''
content = binary.get_content_from_virtual_address(binary.entrypoint, 4, lief.Binary.VA_TYPES.AUTO)
if content.tolist() == [95, 36, 3, 213]: # bti
return True
return False
BASE_ELF = [ BASE_ELF = [
('PIE', check_PIE), ('PIE', check_PIE),
('NX', check_NX), ('NX', check_NX),
@ -231,7 +241,7 @@ CHECKS = {
lief.ARCHITECTURES.X86: BASE_MACHO + [('PIE', check_PIE), lief.ARCHITECTURES.X86: BASE_MACHO + [('PIE', check_PIE),
('NX', check_NX), ('NX', check_NX),
('CONTROL_FLOW', check_MACHO_control_flow)], ('CONTROL_FLOW', check_MACHO_control_flow)],
lief.ARCHITECTURES.ARM64: BASE_MACHO, lief.ARCHITECTURES.ARM64: BASE_MACHO + [('BRANCH_PROTECTION', check_MACHO_branch_protection)],
} }
} }

View file

@ -137,12 +137,12 @@ class TestSecurityChecks(unittest.TestCase):
else: else:
# arm64 darwin doesn't support non-PIE binaries, control flow or executable stacks # arm64 darwin doesn't support non-PIE binaries, control flow or executable stacks
self.assertEqual(call_security_check(cc, source, executable, ['-Wl,-flat_namespace','-fno-stack-protector', '-Wl,-no_fixup_chains']), self.assertEqual(call_security_check(cc, source, executable, ['-Wl,-flat_namespace','-fno-stack-protector', '-Wl,-no_fixup_chains']),
(1, executable+': failed NOUNDEFS Canary FIXUP_CHAINS')) (1, executable+': failed NOUNDEFS Canary FIXUP_CHAINS BRANCH_PROTECTION'))
self.assertEqual(call_security_check(cc, source, executable, ['-Wl,-flat_namespace','-fno-stack-protector', '-Wl,-fixup_chains']), self.assertEqual(call_security_check(cc, source, executable, ['-Wl,-flat_namespace','-fno-stack-protector', '-Wl,-fixup_chains', '-mbranch-protection=bti']),
(1, executable+': failed NOUNDEFS Canary')) (1, executable+': failed NOUNDEFS Canary'))
self.assertEqual(call_security_check(cc, source, executable, ['-Wl,-flat_namespace','-fstack-protector-all', '-Wl,-fixup_chains']), self.assertEqual(call_security_check(cc, source, executable, ['-Wl,-flat_namespace','-fstack-protector-all', '-Wl,-fixup_chains', '-mbranch-protection=bti']),
(1, executable+': failed NOUNDEFS')) (1, executable+': failed NOUNDEFS'))
self.assertEqual(call_security_check(cc, source, executable, ['-fstack-protector-all', '-Wl,-fixup_chains']), self.assertEqual(call_security_check(cc, source, executable, ['-fstack-protector-all', '-Wl,-fixup_chains', '-mbranch-protection=bti']),
(0, '')) (0, ''))