2022年2月18日 星期五

Wireshark Dissector WSGD 2022

https://wintermade.it/blog/posts/how-to-write-generic-dissectors-in-wireshark.html

2022-02-16


OS

Ubuntu 20 using apt-get install wireshark with version 3.2

Windows 10 with Wireshark 3.6.2 64 bit

C:\Program Files\Wireshark\plugins\3.6\epan\

Or Linux

sudo cp generic.so /usr/lib/x86_64-linux-gnu/wireshark/plugins/3.2/epan

sudo cp custom.wsgd /usr/lib/x86_64-linux-gnu/wireshark/plugins/3.2/epan

sudo cp custom.fdesc /usr/lib/x86_64-linux-gnu/wireshark/plugins/3.2/epan


# udp_server.py

import socketserver

class CustomHandler(socketserver.DatagramRequestHandler):
def handle(self):
data = self.request[0].strip()
print(data)

if __name__ == "__main__":
print("server starting")
serv = socketserver.UDPServer(("127.0.0.1", 8756), CustomHandler)
serv.serve_forever()


udp_client.py

import socket
import struct
import random
import string
import time

HOST, PORT = "localhost", 8756

# SOCK_DGRAM is the socket type to use for UDP sockets
sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)

# refer to `pydoc struct`
HEADER_STRUCT = "".join([
">", # network byte order
"L", # counter
"B", # message size
"B", # message type (0: word, 1: number)
])

PAYLOAD_WORD_TYPE = HEADER_STRUCT + "".join([
"B", # word length
"100s", # string (at most 100 characters)
])
word_struct = struct.Struct(PAYLOAD_WORD_TYPE)

PAYLOAD_NUMBER_TYPE = HEADER_STRUCT + "".join([
"B", # number
"B", # 0: even, 1: odd
"B", # unsigned char
"H", # unsigned short
"I", # unsigned int
"Q", # unsigned long long
])
number_struct = struct.Struct(PAYLOAD_NUMBER_TYPE)

msg_counter = 0
for _ in range(3):
msg_counter += 1

# prepare data to send
if random.random() < 0.99:
num = random.choice(range(256))
is_even = num & 1
ui8 = pow(2,8)-1 # 255
ui16 = pow(2,16)-1 # 65535
ui32 = pow(2,32)-1 # 4294967295
i64 = pow(2,63)-1 # 9223372036854775807 ok
i64 = pow(2,63) # 9223372036854775808 become -9223372036854775808:int64
data = number_struct.pack(msg_counter, 2, 1, num, is_even, ui8, ui16, ui32, i64)
#data = number_struct.pack(msg_counter, 2, 1, num, is_even)
else:
string_len = random.choice(range(100))
the_string = bytes("".join(random.choice(string.ascii_letters+" ") for i in range(string_len)), "ascii")
data = word_struct.pack(msg_counter, 101, 0, string_len, the_string)

# send the message
sock.sendto(data, (HOST, PORT))

# wait 200ms
time.sleep(0.2)

# file custom.wsgd

# protocol metadata

PROTONAME Custom Protocol over UDP

PROTOSHORTNAME Custom

PROTOABBREV custom


# conditions on which the dissector is applied:

# the protocol will be applied on all UDP messages with port = 8756

PARENT_SUBFIELD udp.port

PARENT_SUBFIELD_VALUES 8756


# the name of the header structure

MSG_HEADER_TYPE                    T_custom_header

# field which permits to identify the message type.

MSG_ID_FIELD_NAME                  msg_id

# the main message type - usually it is a fake message, built of one

#    of the possible messages

MSG_MAIN_TYPE                      T_custom_switch(msg_id)


# this token marks the end of the protocol description

PROTO_TYPE_DEFINITIONS


# refer to the description of the data format

include custom.fdesc;



# file custom.fdesc

# here, we define an enumerated type to list the type of messages

#   defined in our protocol

enum8 T_custom_msg_type

{

    word_message   0

    number_message 1

}


# here, we define the structure of the header.

# The header (the same for each message type) must...

struct T_custom_header

{

    # ... define the order of the data

    byte_order big_endian;

    uint32 counter;

    uint8  size_after_header;

    # ... contain the field defined as MSG_ID_FIELD_NAME

    T_custom_msg_type msg_id;

}


struct T_word_message

{

    T_custom_header header;

    uint8           word_len;

    # array of characters

    char[word_len]  word;

    # "word" messages will always have some unused trailing bytes:

    #   they can be marked as raw(*) - the size is calculated at runtime

    raw(*)          spare;

}


struct T_number_message

{

    T_custom_header header;

    uint8           number;

    bool8           is_even;

uint8           uint8;

uint16           uint16;

uint32           uint32;

int64{min=0:max=9223372036854775807}           int64;

}


# T_custom_switch is the main message (as defined in the protocol description)

# according to the parameter msg_id (of type T_custom_msg_type), we define

# the main message to be defined by a single message: either T_word_message or T_number_message.

switch T_custom_switch T_custom_msg_type

{

case T_custom_msg_type::word_message :   T_word_message "";

case T_custom_msg_type::number_message : T_number_message "";

}

Result














more

Multicast

Ubuntu
# route add -net 224.0.0.0 netmask 240.0.0.0 dev lo
# ifconfig lo multicast

# multicast_server.py

import socket
import struct

MCAST_GRP = '224.1.1.1'
MCAST_PORT = 8756
IS_ALL_GROUPS = True

sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.IPPROTO_UDP)
sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
if IS_ALL_GROUPS:
# on this port, receives ALL multicast groups
sock.bind(('', MCAST_PORT))
else:
# on this port, listen ONLY to MCAST_GRP
sock.bind((MCAST_GRP, MCAST_PORT))
mreq = struct.pack("4sl", socket.inet_aton(MCAST_GRP), socket.INADDR_ANY)

sock.setsockopt(socket.IPPROTO_IP, socket.IP_ADD_MEMBERSHIP, mreq)

while True:
# For Python 3, change next line to "print(sock.recv(10240))"
print(sock.recv(10240))

# multicast_client.py

import socket
import struct
import random
import string
import time

# Ubuntu: add a new route
# route add -net 224.0.0.0 netmask 240.0.0.0 dev lo
# ifconfig lo multicast

MCAST_GRP = '224.1.1.1'
MCAST_PORT = 8756
# regarding socket.IP_MULTICAST_TTL
# ---------------------------------
# for all packets sent, after two hops on the network the packet will not
# be re-sent/broadcast (see https://www.tldp.org/HOWTO/Multicast-HOWTO-6.html)
MULTICAST_TTL = 2

# refer to `pydoc struct`
HEADER_STRUCT = "".join([
">", # network byte order
"L", # counter
"B", # message size
"B", # message type (0: word, 1: number)
])

PAYLOAD_WORD_TYPE = HEADER_STRUCT + "".join([
"B", # word length
"100s", # string (at most 100 characters)
])
word_struct = struct.Struct(PAYLOAD_WORD_TYPE)

PAYLOAD_NUMBER_TYPE = HEADER_STRUCT + "".join([
"B", # number
"B", # 0: even, 1: odd
"B", # unsigned char
"H", # unsigned short
"I", # unsigned int
"Q", # unsigned long long
])
number_struct = struct.Struct(PAYLOAD_NUMBER_TYPE)

sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM, socket.IPPROTO_UDP)
sock.setsockopt(socket.IPPROTO_IP, socket.IP_MULTICAST_TTL, MULTICAST_TTL)

msg_counter = 0
for _ in range(3):
msg_counter += 1

# prepare data to send
if random.random() < 0.99:
num = random.choice(range(256))
is_even = num & 1
ui8 = pow(2,8)-1 # 255
ui16 = pow(2,16)-1 # 65535
ui32 = pow(2,32)-1 # 4294967295
i64 = pow(2,63)-1 # 9223372036854775807 ok
i64 = pow(2,63) # 9223372036854775808 become -9223372036854775808:int64
data = number_struct.pack(msg_counter, 2, 1, num, is_even, ui8, ui16, ui32, i64)
#data = number_struct.pack(msg_counter, 2, 1, num, is_even)
else:
string_len = random.choice(range(100))
the_string = bytes("".join(random.choice(string.ascii_letters+" ") for i in range(string_len)), "ascii")
data = word_struct.pack(msg_counter, 101, 0, string_len, the_string)

# send the message
sock.sendto(data, (MCAST_GRP, MCAST_PORT))

# wait 200ms
time.sleep(0.2)

Wireshark (multicast)





















more







沒有留言:

張貼留言

2007 to 2023 HP and Dell Servers Comparison

  HP Gen5 to Gen11  using ChatGPT HP ProLiant Gen Active Years CPU Socket Popular HP CPUs Cores Base Clock Max RAM Capacity Comparable Dell ...