import
keystone
import
ida_bytes
import
ida_ida
import
ida_segment
import
ida_ua
import
idaapi
import
idautils
import
idc
ks
=
keystone.Ks(keystone.KS_ARCH_ARM64, keystone.KS_MODE_LITTLE_ENDIAN)
def
getAddrRange():
start
=
ida_ida.inf_get_min_ea()
size
=
ida_ida.inf_get_max_ea()
-
start
for
seg
in
idautils.Segments():
seg
=
idaapi.getseg(seg)
segName
=
ida_segment.get_segm_name(seg)
if
segName
=
=
".text"
:
start
=
seg.start_ea
size
=
seg.size()
return
start, size
def
binSearch(start, end, pattern):
matches
=
[]
addr
=
start
if
end
=
=
0
:
end
=
idc.BADADDR
if
end !
=
idc.BADADDR:
end
=
end
+
1
while
True
:
addr
=
ida_bytes.bin_search(addr, end, bytes.fromhex(pattern),
None
, idaapi.BIN_SEARCH_FORWARD,
idaapi.BIN_SEARCH_NOCASE)
if
addr
=
=
idc.BADADDR:
break
else
:
matches.append(addr)
addr
=
addr
+
1
return
matches
def
generate(code, addr):
encoding, _
=
ks.asm(code, addr)
return
encoding
full_nop_list
=
[
"FF0301D1E0FB00A90100009480000010FE0300AAFF030191C0035FD6E0FB7CA9"
,
"FFC300D1E07B01A90100009480000010FE0300AAFFC30091C0035FD6E07B7EA9"
,
"FF4301D1E07B02A90100009480000010FE0300AAFF430191C0035FD6E07B7DA9"
,
"FF4301D1E0FB00A90100009480000010FE0300AAFF430191C0035FD6E0FB7BA9"
,
"FF4301D1E0FB01A90100009480000010FE0300AAFF430191C0035FD6E0FB7CA9"
,
"E0FB3EA90100009460000010FE0300AAC0035FD6E0FB7EA9"
,
"E07B3EA90100009460000010FE0300AAC0035FD6E07B7EA9"
,
"E07B3FA90100009460000010FE0300AAC0035FD6E07B7FA9"
]
for
i
in
range
(
len
(full_nop_list)):
matches
=
binSearch(
0
,
0
, full_nop_list[i])
for
matche
in
matches:
print
(
"flower"
+
str
(i)
+
":"
,
hex
(matche))
nopCode
=
generate(
"nop"
,
0
)
ida_bytes.patch_bytes(matche, bytes(nopCode)
*
int
(
len
(full_nop_list[i])
/
8
))
start, size
=
getAddrRange()
insn
=
ida_ua.insn_t()
indirect_jump_addr
=
[]
for
i
in
range
(
0
, size,
4
):
addr
=
start
+
i
if
idaapi.decode_insn(insn, addr):
mnemonic
=
insn.get_canon_mnem()
if
mnemonic
=
=
"BL"
and
insn.Op1.addr
=
=
0x14DFC
:
indirect_jump_addr.append(addr)
for
i
in
range
(
0
, size,
4
):
addr
=
start
+
i
if
idaapi.decode_insn(insn, addr):
mnemonic
=
insn.get_canon_mnem()
local_addr
=
insn.Op1.addr
if
mnemonic
=
=
"B"
and
local_addr
in
indirect_jump_addr:
firstinsn
=
ida_ua.insn_t()
idaapi.decode_insn(firstinsn, addr
-
4
)
if
firstinsn.get_canon_mnem()
=
=
'MOV'
:
value
=
firstinsn.Op2.value
elif
firstinsn.get_canon_mnem()
=
=
'LDR'
:
value
=
ida_bytes.get_dword(firstinsn.Op2.addr)
else
:
print
(
"需要额外处理"
)
offset_addr
=
local_addr
+
4
+
4
*
value
target_addr
=
local_addr
+
4
+
ida_bytes.get_dword(offset_addr)
print
(
"flower_indirect local_addr"
,
hex
(addr),
"target_addr"
,
hex
(target_addr))
code
=
f
"B {hex(target_addr)}"
bCode
=
generate(code, addr)
ida_bytes.patch_bytes(addr, bytes(bCode))