File size: 3,453 Bytes
ce847d4
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
"""Analyze exact chunk boundary structure in the .onemodel file."""
import struct, json

with open("ocr_data/oneocr.onemodel", "rb") as f:
    fdata = f.read()
log = json.load(open("temp/crypto_log.json"))

sha256s = [op for op in log if op["op"] == "sha256"]
sha_map = {s["output"]: s["input"] for s in sha256s}
decrypts = [op for op in log if op["op"] == "decrypt"]

# Get info for first few payload chunks
def get_chunk_info(dec_idx):
    d = decrypts[dec_idx]
    sha_inp = bytes.fromhex(sha_map[d["aes_key"]])
    s1, s2 = struct.unpack_from("<QQ", sha_inp, 0)
    chk = sha_inp[16:32]
    chk_pos = fdata.find(chk)
    return {
        "dec_idx": dec_idx,
        "enc_size": d["input_size"],
        "size1": s1,
        "size2": s2,
        "chk": chk,
        "chk_pos": chk_pos,
    }

# Focus on first few consecutive large chunks
# From the sorted output, the order in file is: dec#02, dec#03, dec#06, dec#11, dec#16, dec#23, ...
chunks_in_order = [2, 3, 6, 11, 16, 23, 28, 33]
infos = [get_chunk_info(i) for i in chunks_in_order]

print("=== Chunk boundary analysis ===\n")
for i, info in enumerate(infos):
    print(f"dec#{info['dec_idx']:02d}: chk_pos={info['chk_pos']}, size1={info['size1']}, enc_size={info['enc_size']}")
    
    if i > 0:
        prev = infos[i-1]
        # Hypothesis: on-disk encrypted data = size1 + 8 (data_size + container_header)
        prev_data_start = prev['chk_pos'] + 32
        prev_on_disk = prev['size1'] + 8
        expected_next_chk = prev_data_start + prev_on_disk
        actual_next_chk = info['chk_pos']
        delta = actual_next_chk - expected_next_chk
        print(f"  Expected chk_pos: {expected_next_chk}, actual: {actual_next_chk}, delta: {delta}")

# Now figure out the EXACT header structure
print("\n=== Bytes around first few chunk boundaries ===\n")

# Between DX and first chunk
dx_end = 24 + 22624  # = 22648
print(f"--- DX end ({dx_end}) to first chunk ---")
for off in range(dx_end, infos[0]['chk_pos'] + 48, 8):
    raw = fdata[off:off+8]
    val = struct.unpack_from("<Q", raw)[0] if len(raw) == 8 else 0
    print(f"  {off:>8}: {raw.hex()}  (uint64={val})")

# Between chunk 0 and chunk 1
c0 = infos[0]
c1 = infos[1]
# data starts at chk_pos + 32, on-disk size is approximately size1+8 or enc_size
# Let's look at bytes around where the boundary should be
c0_data_start = c0['chk_pos'] + 32
c0_approx_end = c0_data_start + c0['size1'] + 8
print(f"\n--- End of dec#{c0['dec_idx']:02d} / Start of dec#{c1['dec_idx']:02d} ---")
print(f"  c0 data_start: {c0_data_start}")
print(f"  c0 size1+8: {c0['size1']+8}")
print(f"  c0 approx end: {c0_approx_end}")
print(f"  c1 chk_pos: {c1['chk_pos']}")

for off in range(c0_approx_end - 16, c1['chk_pos'] + 48, 8):
    raw = fdata[off:off+8]
    val = struct.unpack_from("<Q", raw)[0] if len(raw) == 8 else 0
    ascii_s = ''.join(chr(b) if 32 <= b < 127 else '.' for b in raw)
    print(f"  {off:>8}: {raw.hex()}  val={val:<15d}  {ascii_s}")

# Check file header
header_size = struct.unpack_from("<Q", fdata, 0)[0]
print(f"\nFile header uint64: {header_size}")
print(f"  = file[0:8] as uint64 LE")

# What if it's NOT a uint64 but two uint32?
h1, h2 = struct.unpack_from("<II", fdata, 0)
print(f"  As two uint32: ({h1}, {h2})")

# file[0:24] detailed view
print("\nFile header [0:24]:")
for off in range(0, 24, 8):
    raw = fdata[off:off+8]
    val = struct.unpack_from("<Q", raw)[0]
    print(f"  {off:>3}: {raw.hex()}  uint64={val}")