diff --git a/lzsip/OpenOS/usr/bin/lzsip.lua b/lzsip/OpenOS/usr/bin/lzsip.lua new file mode 100644 index 0000000..5b3d6b2 --- /dev/null +++ b/lzsip/OpenOS/usr/bin/lzsip.lua @@ -0,0 +1,89 @@ +local lz = require "lzss" +local shell = pcall(require,shell) + +local tA, tO = {}, {} +if shell then + tA, tO = shell.parse(...) +else + tA, tO = {...}, {} +end +tO.bsize = tO.bsize or 16384 + +local function cint(n,l) + local t={} + for i = 0, 7 do + t[i+1] = (n >> (i * 8)) & 0xFF + end + return string.reverse(string.char(table.unpack(t)):sub(1,l)) +end +local function toint(s) + s=s or "" + local n = 0 + local i = 1 + while true do + local p = s:sub(i,i) + if p == "" then break end + local b = string.byte(p) + n = n << 8 + n = n | b + i=i+1 + end + return n +end + +local function cfile(fn) + local fi = io.open(fn,"rb") + if not fi then return false end + local fo = io.open(fn..".lss","wb") + if not fo then fi:close() return false end + fo:write("lz16") -- write header + while true do + local rblock = fi:read(tO.bsize) + if rblock == "" or not rblock then break end + local cblock = lz.compress(rblock) + fo:write(cint(cblock:len(),2)..cblock) + end + fi:close() + fo:close() + return true +end +local function xfile(fn) + local fi = io.open(fn,"rb") + if not fi then return false, "unable to open input file" end + if fi:read(4) ~= "lz16" and not tO.f then + return false, "not an lz16 archive" + end + local fo = io.open(fn:sub(1,-5),"wb") + if not fo then fi:close() return false, "unable to open output file" end + while true do + local len = toint(fi:read(2) or "\0\0") + if len < 1 then + break + end + fo:write(lz.decompress(fi:read(len))) + end + fi:close() + fo:close() + return true +end + +if tO.x then -- extract + for k,v in pairs(tA) do + io.write(v.."...") + local s,r = xfile(v) + if s then + print(" done") + else + print(" failed: "..r) + end + end +else -- create + for k,v in pairs(tA) do + io.write(v.."...") + if cfile(v) then + print(" done.") + else + print(" failed.") + end + end +end diff --git a/lzsip/OpenOS/usr/lib/lzss.lua b/lzsip/OpenOS/usr/lib/lzss.lua new file mode 100644 index 0000000..501d0ec --- /dev/null +++ b/lzsip/OpenOS/usr/lib/lzss.lua @@ -0,0 +1,123 @@ +--[[---------------------------------------------------------------------------- + + LZSS - encoder / decoder + + This is free and unencumbered software released into the public domain. + + Anyone is free to copy, modify, publish, use, compile, sell, or + distribute this software, either in source code form or as a compiled + binary, for any purpose, commercial or non-commercial, and by any + means. + + In jurisdictions that recognize copyright laws, the author or authors + of this software dedicate any and all copyright interest in the + software to the public domain. We make this dedication for the benefit + of the public at large and to the detriment of our heirs and + successors. We intend this dedication to be an overt act of + relinquishment in perpetuity of all present and future rights to this + software under copyright law. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, + EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR + OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + OTHER DEALINGS IN THE SOFTWARE. + + For more information, please refer to + +--]]---------------------------------------------------------------------------- +-------------------------------------------------------------------------------- +local M = {} +local string, table = string, table + +-------------------------------------------------------------------------------- +local POS_BITS = 12 +local LEN_BITS = 16 - POS_BITS +local POS_SIZE = 1 << POS_BITS +local LEN_SIZE = 1 << LEN_BITS +local LEN_MIN = 3 + +-------------------------------------------------------------------------------- +function M.compress(input) + local offset, output = 1, {} + local window = '' + + local function search() + for i = LEN_SIZE + LEN_MIN - 1, LEN_MIN, -1 do + local str = string.sub(input, offset, offset + i - 1) + local pos = string.find(window, str, 1, true) + if pos then + return pos, str + end + end + end + + while offset <= #input do + local flags, buffer = 0, {} + + for i = 0, 7 do + if offset <= #input then + local pos, str = search() + if pos and #str >= LEN_MIN then + local tmp = ((pos - 1) << LEN_BITS) | (#str - LEN_MIN) + buffer[#buffer + 1] = string.pack('>I2', tmp) + else + flags = flags | (1 << i) + str = string.sub(input, offset, offset) + buffer[#buffer + 1] = str + end + window = string.sub(window .. str, -POS_SIZE) + offset = offset + #str + else + break + end + end + + if #buffer > 0 then + output[#output + 1] = string.char(flags) + output[#output + 1] = table.concat(buffer) + end + end + + return table.concat(output) +end + +-------------------------------------------------------------------------------- +function M.decompress(input) + local offset, output = 1, {} + local window = '' + + while offset <= #input do + local flags = string.byte(input, offset) + offset = offset + 1 + + for i = 1, 8 do + local str = nil + if (flags & 1) ~= 0 then + if offset <= #input then + str = string.sub(input, offset, offset) + offset = offset + 1 + end + else + if offset + 1 <= #input then + local tmp = string.unpack('>I2', input, offset) + offset = offset + 2 + local pos = (tmp >> LEN_BITS) + 1 + local len = (tmp & (LEN_SIZE - 1)) + LEN_MIN + str = string.sub(window, pos, pos + len - 1) + end + end + flags = flags >> 1 + if str then + output[#output + 1] = str + window = string.sub(window .. str, -POS_SIZE) + end + end + end + + return table.concat(output) +end + +return M