Skip to content

Commit 7850005

Browse files
committed
Implemented file seeking sliding window.
1 parent c911ae5 commit 7850005

1 file changed

Lines changed: 12 additions & 57 deletions

File tree

arch/INFLATE.LUA

Lines changed: 12 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -7,22 +7,17 @@ if not LIB then print("Please run unzip instead") os.exit(1) end
77
---@param z boolean Is this deflate64
88
function inflate(r, w, f, z)
99

10-
-- TODO: Pass the file handle to inflate to allow file seeking backwards sliding window instead of using RAM
11-
1210
-- Z = size of sliding window
1311
-- b = buffer
1412
-- p = position
1513
-- bb = bit buffer
1614
-- bc = bit count
1715
-- op = output position
1816
-- kg = keep going (in a loop)
19-
-- o = list of 4096-byte strings that make up the output and sliding window
20-
-- oc = current string being built
21-
-- os = total size of all strings in 'o'
2217
-- lex = length base & extra bits (pairs of bytes)
2318
-- dix = distance extra bits (1 byte per entry)
2419
-- dib = distance base (packed 32-bit LE)
25-
local Z, b, p, bb, bc, op, kg, o, oc, os, lex, dix, dib = z and 65536 or 32768, "", 1, 0, 0, 0, 1, {}, "", 0,
20+
local Z, b, p, bb, bc, op, kg, lex, dix, dib = z and 65536 or 32768, "", 1, 0, 0, 0, 1,
2621
-- lex, dix, dib packed strings
2722

2823
"\3\0\4\0\5\0\6\0\7\0\8\0\9\0\10\0\11\1\13\1\15\1\17\1\19\2\23\2\27\2\31\2\35\3\43\3\51\3\59\3\67\4\83\4\99\4\115\4\131\5\163\5\195\5\227\5\2\0",
@@ -70,24 +65,7 @@ function inflate(r, w, f, z)
7065
---@param by number The byte value (0-255) to append.
7166
function ab(by)
7267
op = op + 1
73-
oc = oc .. string.char(by)
74-
75-
-- TODO: Once file seeking sliding window is implemented: remove oc and o buffers and append directly to output file.
76-
77-
if #oc >= 4096 then
78-
o[#o + 1] = oc
79-
os = os + #oc
80-
oc = ""
81-
82-
-- If window exceeds limit, write and discard the oldest chunk
83-
if os > Z then
84-
85-
-- ot = old table of 4096 bytes that have shifted out of the sliding window
86-
local ot = table.remove(o, 1)
87-
os = os - #ot
88-
w(ot)
89-
end
90-
end
68+
w(string.char(by))
9169
end
9270

9371
---Constructs a canonical Huffman decoding table from a list of code lengths.
@@ -282,34 +260,16 @@ function inflate(r, w, f, z)
282260
print("!Distance", dv, Z, op) os.exit(1)
283261
end
284262

285-
-- Read from output history
286-
for _ = 1, l do
287-
288-
-- TODO: Replace this loop with file seeking sliding window logic.
289-
290-
-- c = character
291-
local c
292-
293-
if dv <= #oc then -- Target is in the currently building chunk
294-
c = oc:sub(#oc - dv + 1, #oc - dv + 1)
295-
else -- Target is in one of the completed chunks
296-
297-
-- of = offset
298-
-- co = coff
299-
local of, co = os - (dv - #oc), 0
300-
for i = 1, #o do
301-
if of < co + #o[i] then
302-
303-
-- n = position
304-
local n = of - co + 1
305-
c = o[i]:sub(n, n)
306-
break
307-
end
308-
co = co + #o[i]
309-
end
310-
end
311-
ab(c:byte())
312-
end
263+
-- Read from output history using the file-backed sliding window
264+
f:seek("end", -dv)
265+
266+
-- n = pattern
267+
local n = f:read(math.min(dv, l))
268+
269+
n = n:rep(l // dv) .. n:sub(1, l % dv)
270+
f:seek("end")
271+
w(n)
272+
op = op + l
313273
end
314274
end
315275
end
@@ -319,9 +279,4 @@ function inflate(r, w, f, z)
319279

320280
if a == 1 then kg = 0 end
321281
end
322-
323-
-- Flush remaining data
324-
-- TODO: Once file seeking sliding window is implemented, remove flushing logic as it's redundant
325-
for i = 1, #o do w(o[i]) end
326-
if #oc > 0 then w(oc) end
327282
end

0 commit comments

Comments
 (0)