Guest User

Falcom Compress v1

a guest
May 22nd, 2016
201
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. import struct
  2. import io
  3.  
  4. outfilename = 'test.cmp'
  5. infilename = 'skill.unc'
  6. def _updateflags(out):
  7. ###"Writes" a flag
  8. ###Writes data if the flag buffer is full, then flushes
  9.     global comp_buffer
  10.     global flag_pos     #Other functions need read access so it has to be global (or passed back and forth)
  11.     flags = 0
  12.     flag_write = 0x8000
  13.     flag_pos = 8
  14.     b = (yield)         #At this point ready to pass in first flag bit
  15.     while True:
  16.         if b:   #Write a "1" (otherwise write 0)
  17.             flags |= flag_write     #Writes a "1"
  18.         flag_pos -= 1
  19.         if flag_pos == 0:
  20.             out.write(struct.pack('<H', flags))
  21.             out.write(comp_buffer)
  22.             comp_buffer = bytearray(0)
  23.             flag_pos = 16
  24.             flags = 0
  25.         else:
  26.             flags >>= 1
  27.         b = (yield)
  28.  
  29. def compress_FALCOM3(filedata):
  30.     out = io.BytesIO()
  31.     data = compress_FALCOM2(filedata)
  32.     #Format is compressed size + 11, decompressed size, chunks, 1st chunk size
  33.     out.write(struct.pack('<IIIH',  len(data) + 11,     #Extra IIHB
  34.                                     len(filedata),
  35.                                     1, len(data)))
  36.     out.write(data)
  37.     out.write(b'\x00')                                  #Stop flag
  38.     out.seek(0)
  39.     return out.read()
  40.  
  41. def compress_FALCOM2(filedata):
  42.     global comp_buffer                  #Other functions need write access
  43.     global out
  44.     file_size = len(filedata)
  45.     file_pos = 0
  46.     comp_buffer = bytearray(0)
  47.     out = io.BytesIO()
  48.     updateflags = _updateflags(out) #Initalize generator
  49.     next(updateflags)               #More initialize generator
  50.     while file_pos < file_size:
  51. ##        print(hex(file_pos))
  52.         match_size = 0
  53.         match_pos = 0
  54.         if file_pos < 0xFF:
  55.             buffer_start = 0
  56.         else:
  57.             buffer_start = file_pos - 255
  58.         for i, byte in enumerate(filedata[buffer_start:file_pos]):
  59.             i += buffer_start
  60.             if byte == filedata[file_pos]:
  61.                 j = 1
  62.                 while True:
  63.                     if i + j == file_pos:
  64.                         break
  65.                     if file_pos + j == file_size:
  66.                         break
  67.                     if filedata[i+j] != filedata[file_pos+j]:
  68.                         break
  69.                     j += 1
  70.                 if j >= match_size:
  71.                     match_size = j
  72.                     match_pos = file_pos - i
  73.         if match_size > 2:
  74. ##            print(match_size)
  75.             if match_size <= 0xFF and match_pos <= 0xFF:
  76.                 updateflags.send(True)
  77.                 comp_buffer.append(match_pos)
  78.                 updateflags.send(False)
  79.                 file_pos += match_size
  80.                 for i in range(2, 5):
  81.                     if i >= match_size:
  82.                         break
  83.                     updateflags.send(False)
  84.                 if match_size >= 6:
  85.                     updateflags.send(False)
  86.                     if match_size >= 0xE:
  87.                         match_size -= 0xE
  88.                         comp_buffer.append(match_size)
  89.                         updateflags.send(False)
  90.                     else:
  91.                         updateflags.send(True)
  92.                         match_size -= 0x6
  93.                         for i in reversed(range(3)):
  94.                             updateflags.send((match_size >> i) & 1)
  95.                 else:
  96.                     updateflags.send(True)
  97.             else:
  98.                 comp_buffer.append(filedata[file_pos])
  99.                 file_pos += 1
  100.                 updateflags.send(False)
  101.         else:
  102.             comp_buffer.append(filedata[file_pos])
  103.             file_pos += 1
  104.             updateflags.send(False)
  105.     for x in range(2):
  106.         updateflags.send(True)
  107.     for x in range(5):
  108.         updateflags.send(False)
  109.     for x in range(0x10 - flag_pos):
  110.         updateflags.send(False)
  111.     out.write(b'\x00')
  112.     out.seek(0)
  113.     return out.read()
  114. if __name__ == '__main__':
  115.     pass
  116.     ##with open('skill.unc', 'rb') as f:
  117.     ##    with open('test.cmp', 'wb') as g:
  118.     ##        g.write(compress_FALCOM3(f.read()))
RAW Paste Data

Adblocker detected! Please consider disabling it...

We've detected AdBlock Plus or some other adblocking software preventing Pastebin.com from fully loading.

We don't have any obnoxious sound, or popup ads, we actively block these annoying types of ads!

Please add Pastebin.com to your ad blocker whitelist or disable your adblocking software.

×