Skip to content

Instantly share code, notes, and snippets.

@x56
Created March 19, 2016 04:58
Show Gist options
  • Save x56/8a16c8e30c954aec014d to your computer and use it in GitHub Desktop.
Save x56/8a16c8e30c954aec014d to your computer and use it in GitHub Desktop.
IDAPython script to name and create structs for all CFLString objects
import idaapi
import idc
#import idautils
import sys
#NOTE: may have to run this a few times to get to the end of the IDB, haven't bothered fixing this
def add_struct_to_idb(name):
idc.Til2Idb(-1, name)
def find_or_create_struct(name):
sid = idc.GetStrucIdByName(name)
if sid == idc.BADADDR:
sid = idc.AddStrucEx(-1, name, 0)
print "added struct \"{0}\", id: {1}".format(name, sid)
else:
print "struct \"{0}\" already exists, id: ".format(name, sid)
add_struct_to_idb(name)
return sid
def create_CFLString_struct():
sid = find_or_create_struct("CFLString")
print idc.AddStrucMember(sid, "magic", -1, idc.FF_DWRD, -1, 4)
print idc.AddStrucMember(sid, "unk4", -1, idc.FF_DWRD, -1, 4)
print idc.AddStrucMember(sid, "cstr", -1, idc.FF_BYTE, -1, 0)
return sid
def apply_struct(ea, sid, size):
if size == -1:
size = idc.GetStrucSize(sid)
idc.MakeUnknown(ea, size, idc.DOUNK_DELNAMES)
idaapi.doStruct(ea, size, sid)
return size
def main():
CFLString_sid = create_CFLString_struct()
# limit search to .rodata
seg_sel = idc.SegByName(".rodata")
ea = idc.SegByBase(seg_sel)
end_ea = idc.SegEnd(ea)
while ea < end_ea:
#find all instances of magic==0x756 and unk4==0x7FFFFFFF
if (idc.Dword(ea), idc.Dword(ea + 4)) == (0x756, 0x7FFFFFFF):
# read bytes until NULL is found
index = 0
cstr = ""
while True:
char = chr(idc.Byte(ea + 8 + index))
if char == "\x00":
break
index += 1
cstr += char
name_str = cstr
for bad_char in ["-", ":", ";", "=", "(", ")", " ", "/", "\\", "<", ">"]:
name_str = name_str.replace(bad_char, "_")
#XXX: lazy/unreliable way to deal with name collisions
suffix = 0
while not idc.MakeNameEx(ea, "cflstr_{0}__{1}".format(name_str, suffix), idc.SN_CHECK | idc.SN_NOWARN):
suffix += 1
# something probably went horribly wrong
if suffix > 100:
print "error creating name at address {0}".format(hex(ea))
sys.exit(1)
# size = magic + unk4 + string_length + NULL_byte
print "applying at {0}".format(hex(ea))
struct_size = apply_struct(ea, CFLString_sid, 8 + len(cstr) + 1)
# preserve alignment
ea += (struct_size & ~3)
else:
ea += 4
if __name__ == "__main__":
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment