如何在Wireshark Lua解析器中仅解析Zigbee Cluster Library帧的单个属性
问题:为Wireshark编写Lua解析器修改Zigbee属性显示
这是我第一次提问,我是Lua新手,若有错误请指正。
通用需求
想要为Wireshark编写一个Lua解析器,仅解析Zigbee Cluster Library帧中的指定属性(如将Attribute: 0x0400显示为Attribute: Temperature (0x0400)),同时让官方解析器处理其余内容。
遇到的问题
问题1:解析器的正确挂载方式
测试时将解析器添加到wpan.panid解析器表,指定PANID为0x9dbd时能生效,但仅适用于该特定PANID,且挂载层级过低,只想针对zbee_zcl.attr.id这个属性做修改。
- 疑问:如何让解析器不受PANID限制被调用?如何仅锚定到
zbee_zcl.attr.id属性?
问题2:调用官方解析器无效果
尝试先调用官方的zbee_nwk、zbee_aps、zbee_zcl解析器,再修改目标属性,但调用后解析树无变化。
测试代码:
alreadyCalled = false networkDissector = Dissector.get("zbee_nwk") applicationSupportDissector = Dissector.get("zbee_aps") clusterLibraryDissector = Dissector.get("zbee_zcl") local myProtoField = ProtoField.new("zbee_zcl.attr.id", "zzbee_zcl.attr.id", ftypes.UINT16) function myFunction(treeViewBuffer, packetInfo, tree) if(alreadyCalled == false) then print(tostring(treeViewBuffer) .. " / " .. tostring(packetInfo) .. " / " .. tostring(tree)) print("Nr. of changed stuff: " .. networkDissector:call(treeViewBuffer, packetInfo, tree)) print(tostring(treeViewBuffer) .. " / " .. tostring(packetInfo) .. " / " .. tostring(tree)) alreadyCalled = true end end myProtocol = Proto("MYZIGBEE", "myZigbee") myProtocol.dissector = myFunction DissectorTable.get("wpan.panid"):add(0x9dbd, myProtocol)
- 疑问:为什么调用官方解析器后解析树没变化?是不是调用方式错误?会不会是载荷加密(已在Wireshark中添加密钥)导致的?
TLDR
有经验的开发者会如何实现:让官方解析器处理大部分内容,仅修改指定Zigbee属性的显示?
解决方案
针对你的需求,最适合的方式是使用后解析器(Post-dissector),它能在官方解析器完成解析后,对已生成的解析树进行修改或补充,完美匹配你“只改指定属性,其余交给官方”的需求。
优化后的实现代码
-- 定义后解析器 local zbee_postDissector = Proto("zbee_post", "Zigbee Attribute Display Enhancement") -- 定义要替换显示的属性映射(可根据需求扩展) local attr_map = { [0x0400] = "Temperature", -- 可添加更多属性,比如 [0x0401] = "Humidity" } -- 注册后解析器 register_postdissector(zbee_postDissector) -- 后解析器逻辑 function zbee_postDissector.dissector(tvbuf, pinfo, tree) -- 遍历所有已解析的zbee_zcl.attr.id节点 local attr_ids = {attr_id()} for _, attr in ipairs(attr_ids) do if attr and attr.value then -- 获取属性ID对应的名称 local attr_name = attr_map[attr.value] if attr_name then -- 修改原节点的显示文本 attr:set_text(string.format("%s (0x%04X)", attr_name, attr.value)) end end end return true end
关键说明
- 后解析器的优势:无需挂载到特定解析器表,会自动在所有官方解析器执行后运行,不受PANID限制,直接针对已解析的
zbee_zcl.attr.id节点操作。 - 原代码问题分析:
- 你之前挂载到
wpan.panid的方式属于替换式解析器,会覆盖官方解析逻辑,且仅针对特定PANID生效。 - 直接调用官方解析器无效果,是因为
wpan.panid对应的缓冲区是整个WPAN帧,而zbee_nwk需要的是NWK层的子缓冲区,直接传入整个帧缓冲区会导致解析失败。
- 你之前挂载到
- 加密问题排查:如果已在Wireshark中添加正确的解密密钥,官方解析器能正常解析出
zbee_zcl.attr.id,后解析器就能正常工作;如果解析树中看不到该属性,先确认解密是否成功。
内容的提问来源于stack exchange,提问作者Ducksenz
相关产品推荐
相关产品推荐

