From e6e1c19badac420e86797c3bc351a6b1c59c7107 Mon Sep 17 00:00:00 2001 From: Přemysl Janouch Date: Sun, 21 May 2017 21:08:33 +0200 Subject: Add a partial decoder for RFC 1950: ZLIB --- plugins/zlib.lua | 57 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 57 insertions(+) create mode 100644 plugins/zlib.lua (limited to 'plugins') diff --git a/plugins/zlib.lua b/plugins/zlib.lua new file mode 100644 index 0000000..0290194 --- /dev/null +++ b/plugins/zlib.lua @@ -0,0 +1,57 @@ +-- +-- zlib.lua: ZLIB Compressed Data Format +-- +-- Copyright (c) 2017, Přemysl Janouch +-- +-- Permission to use, copy, modify, and/or distribute this software for any +-- purpose with or without fee is hereby granted, provided that the above +-- copyright notice and this permission notice appear in all copies. +-- +-- THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +-- WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +-- MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY +-- SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +-- WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION +-- OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN +-- CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. +-- + +-- Based on RFC 1950, this format isn't very widely used +local decode = function (c) + c.endianity = 'be' + + local deflate_levels = { "fastest", "fast", "default", "slowest" } + local deflate + local cmf = c:u8 ("compression method and flags: %s", function (u8) + local cm, cm_name = u8 & 0xf, "unknown" + local cinfo, cinfo_name = u8 >> 4, "unknown" + if cm == 8 then + deflate = true + cm_name = "deflate" + cinfo_name = ("window size = %d"):format (2 ^ (cinfo + 8)) + end + return "%s (%d), %s (%d)", cm_name, cm, cinfo_name, cinfo + end) + local have_dict + local flags = c:u8 ("flags: %s", function (u8) + local check = (cmf * 256 + u8) % 31 == 0 + if check then check = "ok" else check = "failed" end + + local level, level_name = (u8 >> 6) & 3, "unknown" + if deflate then level_name = deflate_levels[level + 1] end + have_dict = (u8 >> 5) & 1 == 1 + + local info = "preset dictionary" + if not have_dict then info = "no " .. info end + return "level %s (%d), check %s, %s", level_name, level, check, info + end) + if have_dict then + c:u16 ("dictionary Adler-32 checksum: %04x") + end + + -- Compressed data follows immediately + -- Not going to decompress it, so we don't know where the final checksum is +end + +hex.register { type="zlib", detect=nil, decode=decode } + -- cgit v1.2.3-70-g09d2