Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import os,sys,struct
- reload(sys)
- sys.setdefaultencoding('sjis')
- op_codes = {
- 0x0:0x0,0x1:0x1,0x2:0x2,0x3:0x2,
- 0x4:0x3,0x5:0x3,0x6:0x3,0x7:0x3,
- 0x8:0x3,0x9:0x4,0xa:0x4,0xb:0x4,
- 0xc:0x4,0xd:0x5,0xe:0x5,0xf:0x5,
- 0x10:0x5,0x11:0x6,0x12:0x6,0x13:0x6,
- 0x14:0x6,0x15:0x7,0x16:0x7,0x17:0x7,
- 0x18:0x7,0x19:0x8,0x1a:0x8,0x1b:0x8,
- 0x1c:0x8,0x1d:0x9,0x1e:0x9,0x1f:0xa,
- 0x20:0xb,0x21:0xc,
- }
- def get_data(filename):
- totalbytes = os.path.getsize(filename)
- infile = open(filename, 'rb')
- totalfiledata = infile.read(totalbytes)
- infile.close()
- return totalfiledata
- def get_dataval(filedata,i,data_type,minus):
- data_type -= minus
- if (data_type < 0 or data_type > 3):
- print 'data_type FUCKED UP WITH A VAL OF 0x%x' % data_type
- sys.exit()
- elif data_type == 0:
- data = struct.unpack('<B',filedata[i:i+1])[0]
- i += 1
- elif data_type == 1:
- data = struct.unpack('<H',filedata[i:i+2])[0]
- i += 2
- elif data_type == 2:
- data = struct.unpack('<B',filedata[i+2:i+3])[0]
- data << 16
- data |= struct.unpack('<H',filedata[i:i+2])[0]
- i += 3
- elif data_type == 3:
- data = struct.unpack('<I',filedata[i:i+4])[0]
- i += 4
- else:
- print 'UNREACHABLE!!!'
- sys.exit()
- return data,i
- if __name__ == '__main__':
- filedata = get_data(sys.argv[1])
- header_len = struct.unpack('<I',filedata[0x8:0xc])[0]
- sec1_len = (struct.unpack('<H',filedata[header_len+1:header_len+3])[0] * 2) + 4
- sec2_len = (struct.unpack('<H',filedata[header_len+sec1_len+1:header_len+sec1_len+3])[0] * 2) + 4
- sec3_len = (struct.unpack('<B',filedata[header_len+sec1_len+sec2_len+1:header_len+sec1_len+sec2_len+2])[0] * 2) + 3
- script_start = header_len+sec1_len+sec2_len+sec3_len
- string_script_pos = struct.unpack('<I',filedata[0x10:0x14])[0]
- string_pos = struct.unpack('<I',filedata[0x14:0x18])[0]
- strings = ''
- i = script_start
- while i < string_script_pos:
- op_start = i
- if struct.unpack('<B',filedata[i:i+1])[0] not in op_codes:
- print 'Unknown op code %x at %x' % (struct.unpack('<B',filedata[i:i+1])[0],i)
- sys.exit()
- real_opcode = struct.unpack('<B',filedata[i:i+1])[0]
- op_code = op_codes[real_opcode]
- i += 1
- if op_code == 0x1: # opcodes 0x1
- continue;
- elif op_code == 0x3: # opcodes 0x4,0x5,0x6,0x7,0x8
- data_type = real_opcode - 4
- if data_type < 0 or data_type > 4:
- print '%x - data type fucked!' % i
- sys.exit()
- elif data_type == 0:
- data = 0
- elif data_type == 1:
- data = struct.unpack('<B',filedata[i:i+1])[0]
- i += 1
- elif data_type == 2:
- data = struct.unpack('<H',filedata[i:i+2])[0]
- i += 2
- elif data_type == 3:
- data = struct.unpack('<B',filedata[i+2:i+3])[0]
- data <<= 16
- data |= struct.unpack('<H',filedata[i:i+2])[0]
- i += 3
- elif data_type == 4:
- data = struct.unpack('<I',filedata[i:i+4])[0]
- i += 4
- elif op_code == 0x4: # opcodes 0x9,0xa,0xb,0xc
- data_type = real_opcode - 0x9
- if data_type < 0 or data_type > 3:
- print 'data_type fucked at %x' % i
- sys.exit()
- elif data_type == 0: #5 bytes
- i += 5
- elif data_type == 1: #6 bytes
- i += 6
- elif data_type == 2:
- i += 7
- elif data_type == 3:
- i += 8
- elif op_code == 0x7: # opcodes 0x15,0x16,0x17,18, strings
- data,i = get_dataval(filedata,i,real_opcode,0x15)
- script_type = struct.unpack('<B',filedata[string_script_pos:string_script_pos+1])[0]
- data2,throwaway = get_dataval(filedata,string_script_pos+1,script_type,0xD)
- script_type -= 0xB
- string_format_step = struct.unpack('<B',filedata[string_script_pos+3:string_script_pos+4])[0] - 0xC
- total_string_len = data2 * string_format_step
- unknown1 = string_format_step + total_string_len + 1 #psbfile+AD1B
- script_type = string_format_step - 1
- data *= string_format_step
- data += string_script_pos + (struct.unpack('<B',filedata[string_script_pos:string_script_pos+1])[0] - 0xC) + 2
- if script_type < 0 or script_type > 3:
- print 'script_type fucked'
- sys.exit()
- elif script_type == 0:
- curr_string_pos = struct.unpack('<B',filedata[data:data+1])[0]
- elif script_type == 1:
- curr_string_pos = struct.unpack('<H',filedata[data:data+2])[0]
- elif script_type == 2:
- curr_string_pos = struct.unpack('<B',filedata[data+2:data+3])[0]
- curr_string_pos <<= 16
- curr_string_pos |= struct.unpack('<H',filedata[data:data+2])[0]
- elif script_type == 3:
- curr_string_pos = struct.unpack('<I',filedata[data:data+4])[0]
- curr_string_pos += string_pos
- string = filedata[curr_string_pos:filedata.find('\x00',curr_string_pos)]
- if strings.find(string) == -1:
- strings += string + '\n'
- elif op_code == 0x9: #opcodes 0x1d,0x1e
- data_type = real_opcode - 0x1D
- if data_type < 0 or data_type > 1:
- print 'opcode 0x9 fucked at %x!' % i
- sys.exit()
- if data_type == 1:
- data = struct.unpack('<I',filedata[i:i+4])[0]
- i += 4
- elif op_code == 0xa: #opcodes 0x1f
- val1 = struct.unpack('<I',filedata[i:i+4])[0]
- val2 = struct.unpack('<I',filedata[i+4:i+8])[0]
- i += 8
- elif op_code == 0xb: # op_code 0x20, jump
- data_type = struct.unpack('<B',filedata[i:i+1])[0]
- i += 1
- data,i = get_dataval(filedata,i,data_type,0xD)
- data_type -= 0xB
- data_type2 = struct.unpack('<B',filedata[i:i+1])[0] - 0xC
- i += 1
- data_len = data * data_type2
- i += data_len
- elif op_code == 0xc: #opcodes 0x21
- for x in range(0,2):
- #print 'i %x' % i
- byte2 = struct.unpack('<B',filedata[i:i+1])[0]
- i += 1
- byte3,i = get_dataval(filedata,i,byte2,0xD)
- byte2 -= 0xB
- byte4 = struct.unpack('<B',filedata[i:i+1])[0] - 0xC
- data_len = byte3 * byte4
- i += 1
- i += data_len
- else:
- print 'Unfinished op code %x at %x! Real opcode %x' % (op_code, i-1, real_opcode)
- sys.exit()
- outfile = open('strings.txt','wb')
- outfile.write(strings)
- outfile.close()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement