Improve binbase_find.py
Signed-off-by: Markus Birth <markus@birth-online.de>
This commit is contained in:
+20
-2
@@ -10,6 +10,7 @@ import sys
|
|||||||
from operator import itemgetter
|
from operator import itemgetter
|
||||||
|
|
||||||
chars = "A-Za-z0-9/\\-:.,_$%'\"()[\]<> "
|
chars = "A-Za-z0-9/\\-:.,_$%'\"()[\]<> "
|
||||||
|
known_strings = [b"POSIX", b"ASCII", b"Foretrex", b" V3.50", b"0:/Garmin", b"Garmin International", b"<?xml version"]
|
||||||
min_length = 10
|
min_length = 10
|
||||||
scores = []
|
scores = []
|
||||||
top_score = 0
|
top_score = 0
|
||||||
@@ -31,20 +32,33 @@ def get_strings(filename, size):
|
|||||||
data = f.read(10)
|
data = f.read(10)
|
||||||
except:
|
except:
|
||||||
break
|
break
|
||||||
|
for ks in known_strings:
|
||||||
|
i = data.find(ks)
|
||||||
|
if i >= 0:
|
||||||
|
print("matched known string: {}".format(ks))
|
||||||
|
table.add(offset + i)
|
||||||
|
offset += i + len(ks)
|
||||||
|
continue
|
||||||
|
|
||||||
match = pattern.match(data)
|
match = pattern.match(data)
|
||||||
if match:
|
if match:
|
||||||
|
print(repr(match))
|
||||||
f.seek(offset - 1)
|
f.seek(offset - 1)
|
||||||
try:
|
try:
|
||||||
char = f.read(1)
|
char = f.read(1)
|
||||||
except:
|
except:
|
||||||
continue
|
continue
|
||||||
if not patternc.match(char):
|
if not patternc.match(char):
|
||||||
table.add(offset)
|
#table.add(offset)
|
||||||
offset += len(match.group(0))
|
offset += len(match.group(0))
|
||||||
offset += 1
|
offset += 1
|
||||||
|
table.add(0xbb0e4)
|
||||||
return table
|
return table
|
||||||
|
|
||||||
def get_pointers(filename):
|
def get_pointers(filename):
|
||||||
|
"""
|
||||||
|
Read file in DWORD chunks and assume everything is a pointer.
|
||||||
|
"""
|
||||||
table = {}
|
table = {}
|
||||||
with open(filename, "rb") as f:
|
with open(filename, "rb") as f:
|
||||||
while True:
|
while True:
|
||||||
@@ -90,19 +104,23 @@ if __name__ == "__main__":
|
|||||||
|
|
||||||
for base in range(args.min_addr, args.max_addr, args.page_size):
|
for base in range(args.min_addr, args.max_addr, args.page_size):
|
||||||
if base % ( args.page_size * 1000 ) == 0:
|
if base % ( args.page_size * 1000 ) == 0:
|
||||||
print("Trying base address 0x{:x}".format(base))
|
print("Trying base address 0x{:x}/0x{:x}".format(base, args.max_addr))
|
||||||
print("\u001b[F\u001b[K", end="")
|
print("\u001b[F\u001b[K", end="")
|
||||||
score = 0
|
score = 0
|
||||||
ptrs = list(ptr_table.keys())
|
ptrs = list(ptr_table.keys())
|
||||||
for ptr in ptrs:
|
for ptr in ptrs:
|
||||||
if ptr < base:
|
if ptr < base:
|
||||||
|
# Pointer points to before base address --> invalid and remove from future queries
|
||||||
#print("Removing pointer 0x{:x} from table".format(ptr))
|
#print("Removing pointer 0x{:x} from table".format(ptr))
|
||||||
del ptr_table[ptr]
|
del ptr_table[ptr]
|
||||||
continue
|
continue
|
||||||
if ptr >= (base + size):
|
if ptr >= (base + size):
|
||||||
|
# Pointer points to after firmware area --> invalid, but might become valid when checking higher base addrs
|
||||||
continue
|
continue
|
||||||
|
# Pointer points somewhere inside firmware, calculate offset
|
||||||
offset = ptr - base
|
offset = ptr - base
|
||||||
if offset in str_table:
|
if offset in str_table:
|
||||||
|
# Wow, pointer points directly to one of the found strings --> we have a winner
|
||||||
score += ptr_table[ptr]
|
score += ptr_table[ptr]
|
||||||
if score:
|
if score:
|
||||||
scores.append((base, score))
|
scores.append((base, score))
|
||||||
|
|||||||
Reference in New Issue
Block a user