forked from osmocom/wireshark
From Rolf Fiedler (bug 2408):
This extends the EyeSDN wiretap module to be able to support: - DSS1/Q.931 - PPP - LAPB/X.25 - ATM raw cells - SS7 MTP2 svn path=/trunk/; revision=25123
This commit is contained in:
parent
da44c1d084
commit
7925fd5f2a
|
@ -513,6 +513,7 @@ CLEAN_DISSECTOR_SRC = \
|
||||||
packet-lapbether.c \
|
packet-lapbether.c \
|
||||||
packet-lapd.c \
|
packet-lapd.c \
|
||||||
packet-laplink.c \
|
packet-laplink.c \
|
||||||
|
packet-l1-events.c \
|
||||||
packet-ldp.c \
|
packet-ldp.c \
|
||||||
packet-lge_monitor.c \
|
packet-lge_monitor.c \
|
||||||
packet-linx.c \
|
packet-linx.c \
|
||||||
|
|
|
@ -0,0 +1,152 @@
|
||||||
|
/* packet-l1-events.c
|
||||||
|
* Routines for text-based layer 1 message
|
||||||
|
*
|
||||||
|
* (C) Rolf Fiedler 2008, based on packet-text-media.c by Olivier Biot, 2004.
|
||||||
|
*
|
||||||
|
* $Id$
|
||||||
|
*
|
||||||
|
* Refer to the AUTHORS file or the AUTHORS section in the man page
|
||||||
|
* for contacting the author(s) of this file.
|
||||||
|
*
|
||||||
|
* Wireshark - Network traffic analyzer
|
||||||
|
* By Gerald Combs <gerald@wireshark.org>
|
||||||
|
* Copyright 1998 Gerald Combs
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU General Public License
|
||||||
|
* as published by the Free Software Foundation; either version 2
|
||||||
|
* of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Edit this file with 4-space tabs */
|
||||||
|
|
||||||
|
#ifdef HAVE_CONFIG_H
|
||||||
|
#include "config.h"
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include <string.h>
|
||||||
|
#include <ctype.h>
|
||||||
|
|
||||||
|
#include <glib.h>
|
||||||
|
#include <epan/packet.h>
|
||||||
|
#include <epan/strutil.h>
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* dissector for line-based text messages from layer 1
|
||||||
|
*/
|
||||||
|
|
||||||
|
/* Filterable header fields */
|
||||||
|
static gint proto_l1_events = -1;
|
||||||
|
|
||||||
|
/* Subtrees */
|
||||||
|
static gint ett_l1_events = -1;
|
||||||
|
|
||||||
|
/* Dissector handles */
|
||||||
|
static dissector_handle_t l1_events_handle;
|
||||||
|
|
||||||
|
static void
|
||||||
|
dissect_l1_events(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
|
||||||
|
{
|
||||||
|
proto_tree *subtree;
|
||||||
|
proto_item *ti;
|
||||||
|
gint offset = 0, next_offset;
|
||||||
|
gint len;
|
||||||
|
const char *data_name;
|
||||||
|
|
||||||
|
data_name = pinfo->match_string;
|
||||||
|
if (! (data_name && data_name[0])) {
|
||||||
|
/*
|
||||||
|
* No information from "match_string"
|
||||||
|
*/
|
||||||
|
data_name = (char *)(pinfo->private_data);
|
||||||
|
if (! (data_name && data_name[0])) {
|
||||||
|
/*
|
||||||
|
* No information from "private_data"
|
||||||
|
*/
|
||||||
|
data_name = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (check_col(pinfo->cinfo, COL_PROTOCOL))
|
||||||
|
col_set_str(pinfo->cinfo, COL_PROTOCOL, "Layer1");
|
||||||
|
if (check_col(pinfo->cinfo, COL_DEF_SRC))
|
||||||
|
col_set_str(pinfo->cinfo, COL_DEF_SRC,
|
||||||
|
pinfo->pseudo_header->l1event.uton? "TE" : "NT");
|
||||||
|
if (check_col(pinfo->cinfo, COL_INFO)) {
|
||||||
|
len = tvb_find_line_end(tvb, 0,
|
||||||
|
tvb_ensure_length_remaining(tvb, 0),
|
||||||
|
&next_offset, FALSE);
|
||||||
|
if(len>0)
|
||||||
|
col_set_str(pinfo->cinfo, COL_INFO,
|
||||||
|
tvb_format_text(tvb, 0, len));
|
||||||
|
}
|
||||||
|
if (tree) {
|
||||||
|
ti = proto_tree_add_item(tree, proto_l1_events,
|
||||||
|
tvb, 0, -1, FALSE);
|
||||||
|
if (data_name)
|
||||||
|
proto_item_append_text(ti, ": %s", data_name);
|
||||||
|
subtree = proto_item_add_subtree(ti, ett_l1_events);
|
||||||
|
/* Read the media line by line */
|
||||||
|
while (tvb_reported_length_remaining(tvb, offset) != 0) {
|
||||||
|
/*
|
||||||
|
* XXX - we need to be passed the parameters
|
||||||
|
* of the content type via "pinfo->private_data",
|
||||||
|
* so that we know the character set. We'd
|
||||||
|
* have to handle that character set, which
|
||||||
|
* might be a multibyte character set such
|
||||||
|
* as "iso-10646-ucs-2", or might require other
|
||||||
|
* special processing.
|
||||||
|
*/
|
||||||
|
len = tvb_find_line_end(tvb, offset,
|
||||||
|
tvb_ensure_length_remaining(tvb, offset),
|
||||||
|
&next_offset, FALSE);
|
||||||
|
if (len == -1)
|
||||||
|
break;
|
||||||
|
|
||||||
|
/* We use next_offset - offset instead of len in the
|
||||||
|
* call to tvb_format_text() so it will include the
|
||||||
|
* line terminator(s) (\r and/or \n) in the display.
|
||||||
|
*/
|
||||||
|
proto_tree_add_text(subtree, tvb, offset, next_offset - offset,
|
||||||
|
"%s", tvb_format_text(tvb, offset,
|
||||||
|
next_offset - offset));
|
||||||
|
offset = next_offset;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
proto_register_l1_events(void)
|
||||||
|
{
|
||||||
|
static gint *ett[] = {
|
||||||
|
&ett_l1_events,
|
||||||
|
};
|
||||||
|
|
||||||
|
proto_register_subtree_array(ett, array_length(ett));
|
||||||
|
|
||||||
|
proto_l1_events = proto_register_protocol(
|
||||||
|
"Layer 1 Event Messages", /* Long name */
|
||||||
|
"Layer 1 Events", /* Short name */
|
||||||
|
"data-l1-events"); /* Filter name */
|
||||||
|
register_dissector("data-l1-events", dissect_l1_events,
|
||||||
|
proto_l1_events);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
proto_reg_handoff_l1_events(void)
|
||||||
|
{
|
||||||
|
l1_events_handle = create_dissector_handle(
|
||||||
|
dissect_l1_events, proto_l1_events);
|
||||||
|
|
||||||
|
dissector_add("wtap_encap", WTAP_ENCAP_LAYER1_EVENT, l1_events_handle); /* for text msgs from trace files */
|
||||||
|
}
|
|
@ -43,9 +43,8 @@
|
||||||
* Each Frame starts with the 0xff Flag byte
|
* Each Frame starts with the 0xff Flag byte
|
||||||
* - Bytes 0-2: timestamp (long usec in network byte order)
|
* - Bytes 0-2: timestamp (long usec in network byte order)
|
||||||
* - Bytes 3-7: timestamp (40bits sec since 1970 in network byte order)
|
* - Bytes 3-7: timestamp (40bits sec since 1970 in network byte order)
|
||||||
* - Byte 8: channel (0 for D channel, 1-30 for B1-B30,
|
* - Byte 8: channel (0 for D channel, 1-30 for B1-B30)
|
||||||
* 128 ATM cells, 129 ATM layer indications)
|
* - Byte 9: Sender Bit 0(0 NT, 1 TE), Protocol in Bits 7:1, see enum
|
||||||
* - Byte 9: Sender (0 NT, 1 TE)
|
|
||||||
* - Byte 10-11: frame size in bytes
|
* - Byte 10-11: frame size in bytes
|
||||||
* - Byte 12-n: Frame Payload
|
* - Byte 12-n: Frame Payload
|
||||||
*
|
*
|
||||||
|
@ -58,10 +57,15 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
static int esc_read(guint8 *buf, int len, FILE_T fh)
|
static int esc_read(guint8 *buf, int len, FILE_T fh, int seekback)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
int value;
|
int value;
|
||||||
|
gint64 cur_off;
|
||||||
|
int err;
|
||||||
|
|
||||||
|
if(seekback) cur_off = file_tell(fh);
|
||||||
|
else cur_off=0; // suppress uninitialized warning
|
||||||
|
|
||||||
for(i=0; i<len; i++) {
|
for(i=0; i<len; i++) {
|
||||||
value=file_getc(fh);
|
value=file_getc(fh);
|
||||||
|
@ -78,6 +82,11 @@ static int esc_read(guint8 *buf, int len, FILE_T fh)
|
||||||
}
|
}
|
||||||
buf[i]=value;
|
buf[i]=value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(seekback) {
|
||||||
|
if (file_seek(fh, cur_off, SEEK_SET, &err) == -1)
|
||||||
|
return err<0?err:-err;
|
||||||
|
}
|
||||||
return i;
|
return i;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -151,7 +160,7 @@ int eyesdn_open(wtap *wth, int *err, gchar **err_info _U_)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
wth->data_offset = 0;
|
wth->data_offset = 0;
|
||||||
wth->file_encap = WTAP_ENCAP_ISDN;
|
wth->file_encap = WTAP_ENCAP_PER_PACKET;
|
||||||
wth->file_type = WTAP_FILE_EYESDN;
|
wth->file_type = WTAP_FILE_EYESDN;
|
||||||
wth->snapshot_length = 0; /* not known */
|
wth->snapshot_length = 0; /* not known */
|
||||||
wth->subtype_read = eyesdn_read;
|
wth->subtype_read = eyesdn_read;
|
||||||
|
@ -234,7 +243,7 @@ parse_eyesdn_rec_hdr(wtap *wth, FILE_T fh,
|
||||||
* for a packet. Read in that header and extract the useful
|
* for a packet. Read in that header and extract the useful
|
||||||
* information.
|
* information.
|
||||||
*/
|
*/
|
||||||
if (esc_read(hdr, EYESDN_HDR_LENGTH, fh) != EYESDN_HDR_LENGTH) {
|
if (esc_read(hdr, EYESDN_HDR_LENGTH, fh, 0) != EYESDN_HDR_LENGTH) {
|
||||||
*err = file_error(fh);
|
*err = file_error(fh);
|
||||||
if (*err == 0)
|
if (*err == 0)
|
||||||
*err = WTAP_ERR_SHORT_READ;
|
*err = WTAP_ERR_SHORT_READ;
|
||||||
|
@ -260,20 +269,73 @@ parse_eyesdn_rec_hdr(wtap *wth, FILE_T fh,
|
||||||
pkt_len = ((unsigned long) hdr[10]);
|
pkt_len = ((unsigned long) hdr[10]);
|
||||||
pkt_len = (pkt_len << 8) | ((unsigned long) hdr[11]);
|
pkt_len = (pkt_len << 8) | ((unsigned long) hdr[11]);
|
||||||
|
|
||||||
/* sanity checks */
|
switch(direction >> 1) {
|
||||||
if((channel>30)&&(channel<128)) {
|
default:
|
||||||
|
case EYESDN_ENCAP_ISDN: // ISDN
|
||||||
|
pseudo_header->isdn.uton = direction & 1;
|
||||||
|
pseudo_header->isdn.channel = channel;
|
||||||
|
if(channel) { // bearer channels
|
||||||
|
if(wth) {
|
||||||
|
wth->phdr.pkt_encap = WTAP_ENCAP_ISDN; // recognises PPP
|
||||||
|
pseudo_header->isdn.uton=!pseudo_header->isdn.uton; // bug
|
||||||
|
}
|
||||||
|
} else { // D channel
|
||||||
|
if(wth) {
|
||||||
|
wth->phdr.pkt_encap = WTAP_ENCAP_ISDN;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case EYESDN_ENCAP_MSG: // Layer 1 message
|
||||||
|
if(wth) {
|
||||||
|
wth->phdr.pkt_encap = WTAP_ENCAP_LAYER1_EVENT;
|
||||||
|
}
|
||||||
|
pseudo_header->l1event.uton = (direction & 1);
|
||||||
|
break;
|
||||||
|
case EYESDN_ENCAP_LAPB: // X.25 via LAPB
|
||||||
|
if(wth) {
|
||||||
|
wth->phdr.pkt_encap = WTAP_ENCAP_LAPB;
|
||||||
|
}
|
||||||
|
pseudo_header->x25.flags = (direction & 1) ? 0 : 0x80;
|
||||||
|
break;
|
||||||
|
case EYESDN_ENCAP_ATM: { // ATM cells
|
||||||
|
#define CELL_LEN 53
|
||||||
|
unsigned char cell[CELL_LEN];
|
||||||
|
if(pkt_len != CELL_LEN) {
|
||||||
*err = WTAP_ERR_BAD_RECORD;
|
*err = WTAP_ERR_BAD_RECORD;
|
||||||
*err_info = g_strdup_printf("eyesdn: bad channel number %u",
|
*err_info = g_strdup_printf("eyesdn: ATM cell has a length "
|
||||||
channel);
|
"!= 53 (%u)", pkt_len);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if(direction>1) {
|
if (esc_read(cell, CELL_LEN, fh, 1) != CELL_LEN) {
|
||||||
*err = WTAP_ERR_BAD_RECORD;
|
*err = file_error(fh);
|
||||||
*err_info = g_strdup_printf("eyesdn: bad direction value %u",
|
if (*err == 0)
|
||||||
direction);
|
*err = WTAP_ERR_SHORT_READ;
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(wth) {
|
||||||
|
wth->phdr.pkt_encap = WTAP_ENCAP_ATM_PDUS_UNTRUNCATED;
|
||||||
|
}
|
||||||
|
pseudo_header->atm.flags=ATM_RAW_CELL;
|
||||||
|
pseudo_header->atm.aal=AAL_UNKNOWN;
|
||||||
|
pseudo_header->atm.type=TRAF_UMTS_FP;
|
||||||
|
pseudo_header->atm.subtype=TRAF_ST_UNKNOWN;
|
||||||
|
pseudo_header->atm.vpi=((cell[0]&0xf)<<4) + (cell[0]&0xf);
|
||||||
|
pseudo_header->atm.vci=((cell[0]&0xf)<<4) + cell[0]; // from cell
|
||||||
|
pseudo_header->atm.channel=direction & 1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case EYESDN_ENCAP_MTP2: // SS7 frames
|
||||||
|
pseudo_header->mtp2.sent = direction & 1;
|
||||||
|
pseudo_header->mtp2.annex_a_used = MTP2_ANNEX_A_USED_UNKNOWN;
|
||||||
|
pseudo_header->mtp2.link_number = channel;
|
||||||
|
if(wth) {
|
||||||
|
wth->phdr.pkt_encap = WTAP_ENCAP_MTP2;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
if(pkt_len > EYESDN_MAX_PACKET_LEN) {
|
if(pkt_len > EYESDN_MAX_PACKET_LEN) {
|
||||||
*err = WTAP_ERR_BAD_RECORD;
|
*err = WTAP_ERR_BAD_RECORD;
|
||||||
*err_info = g_strdup_printf("eyesdn: File has %u-byte packet, bigger than maximum of %u",
|
*err_info = g_strdup_printf("eyesdn: File has %u-byte packet, bigger than maximum of %u",
|
||||||
|
@ -287,8 +349,6 @@ parse_eyesdn_rec_hdr(wtap *wth, FILE_T fh,
|
||||||
wth->phdr.caplen = pkt_len;
|
wth->phdr.caplen = pkt_len;
|
||||||
wth->phdr.len = pkt_len;
|
wth->phdr.len = pkt_len;
|
||||||
}
|
}
|
||||||
pseudo_header->isdn.uton = direction;
|
|
||||||
pseudo_header->isdn.channel = channel;
|
|
||||||
|
|
||||||
return pkt_len;
|
return pkt_len;
|
||||||
}
|
}
|
||||||
|
@ -301,7 +361,7 @@ parse_eyesdn_packet_data(FILE_T fh, int pkt_len, guint8* buf, int *err,
|
||||||
int bytes_read;
|
int bytes_read;
|
||||||
|
|
||||||
errno = WTAP_ERR_CANT_READ;
|
errno = WTAP_ERR_CANT_READ;
|
||||||
bytes_read = esc_read(buf, pkt_len, fh);
|
bytes_read = esc_read(buf, pkt_len, fh, 0);
|
||||||
if (bytes_read != pkt_len) {
|
if (bytes_read != pkt_len) {
|
||||||
if (bytes_read == -2) {
|
if (bytes_read == -2) {
|
||||||
*err = file_error(fh);
|
*err = file_error(fh);
|
||||||
|
|
|
@ -26,4 +26,12 @@
|
||||||
|
|
||||||
int eyesdn_open(wtap *wth, int *err, gchar **err_info);
|
int eyesdn_open(wtap *wth, int *err, gchar **err_info);
|
||||||
|
|
||||||
|
enum EyeSDN_TYPES {
|
||||||
|
EYESDN_ENCAP_ISDN=0,
|
||||||
|
EYESDN_ENCAP_MSG,
|
||||||
|
EYESDN_ENCAP_LAPB,
|
||||||
|
EYESDN_ENCAP_ATM,
|
||||||
|
EYESDN_ENCAP_MTP2
|
||||||
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -204,6 +204,7 @@ extern "C" {
|
||||||
#define WTAP_ENCAP_LIN 107
|
#define WTAP_ENCAP_LIN 107
|
||||||
#define WTAP_ENCAP_MOST 108
|
#define WTAP_ENCAP_MOST 108
|
||||||
#define WTAP_ENCAP_CAN20B 109
|
#define WTAP_ENCAP_CAN20B 109
|
||||||
|
#define WTAP_ENCAP_LAYER1_EVENT 110
|
||||||
|
|
||||||
#define WTAP_NUM_ENCAP_TYPES wtap_get_num_encap_types()
|
#define WTAP_NUM_ENCAP_TYPES wtap_get_num_encap_types()
|
||||||
|
|
||||||
|
@ -730,6 +731,11 @@ struct bthci_phdr {
|
||||||
#define BTHCI_CHANNEL_SCO 3
|
#define BTHCI_CHANNEL_SCO 3
|
||||||
#define BTHCI_CHANNEL_EVENT 4
|
#define BTHCI_CHANNEL_EVENT 4
|
||||||
|
|
||||||
|
/* pseudo header for WTAP_ENCAP_LAYER1_EVENT */
|
||||||
|
struct l1event_phdr {
|
||||||
|
gboolean uton;
|
||||||
|
};
|
||||||
|
|
||||||
union wtap_pseudo_header {
|
union wtap_pseudo_header {
|
||||||
struct eth_phdr eth;
|
struct eth_phdr eth;
|
||||||
struct x25_phdr x25;
|
struct x25_phdr x25;
|
||||||
|
@ -749,6 +755,7 @@ union wtap_pseudo_header {
|
||||||
struct erf_mc_phdr erf;
|
struct erf_mc_phdr erf;
|
||||||
struct sita_phdr sita;
|
struct sita_phdr sita;
|
||||||
struct bthci_phdr bthci;
|
struct bthci_phdr bthci;
|
||||||
|
struct l1event_phdr l1event;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct wtap_nstime {
|
struct wtap_nstime {
|
||||||
|
|
Loading…
Reference in New Issue