Wireshark-dev: Re: [Wireshark-dev] Start Dissection from an upper layer?

From: Eloy Paris <peloy@xxxxxxxxxx>
Date: Tue, 10 Jun 2008 13:15:32 -0400
On Tue, Jun 10, 2008 at 04:21:52PM +0200, Guillaume Bienkowski wrote:

> Argh, I just poorly explained myself: I was just confused with Ethernet 
> and IP.
> 
> So I confirm, I get only "data" from the 3rd layer (IP)
> Actually, it will always be IP datagrams, so I don't have to bother with 
> IPX or other fancy 3rd layer protocols).
> 
> What I'd like to do now to start the dissection from the 3rd layer, so 
> that I only have one modification to do (the "ip" dissector).

You need to use the DLT_RAW encapsulation type. Read pcap(3) to see what
DLT_RAW is.

I don't see why you'd have to modify any dissectors or anything in the
wireshark source code for this task.

Give something like this a try (this code snippet assumes all the
libwireshark initializations have been done already):

----------------------------------------------------------------------
static void
fill_in_framedata(frame_data *fdata, size_t len, int ll_type)
{
    struct timeval ts;

    gettimeofday(&ts, NULL);

    fdata->next = NULL;
    fdata->prev = NULL;
    fdata->pfd = NULL;
    fdata->num = 0;
    fdata->pkt_len = len;
    fdata->cum_bytes  = 0;
    fdata->cap_len = len;
    fdata->file_off = 0;
    fdata->lnk_t = wtap_pcap_encap_to_wtap_encap(ll_type);
    fdata->abs_ts.secs = ts.tv_sec;
    fdata->abs_ts.nsecs = ts.tv_usec*1000;
    fdata->flags.passed_dfilter = 0;
    fdata->flags.encoding = CHAR_ASCII;
    fdata->flags.visited = 0;
    fdata->flags.marked = 0;
    fdata->flags.ref_time = 0;
    fdata->color_filter = NULL;

    nstime_set_unset(&fdata->rel_ts);
    nstime_set_unset(&fdata->del_cap_ts);
    nstime_set_unset(&fdata->del_dis_ts);
}

/* Free up all data attached to a "frame_data" structure. */
static void
clear_fdata(frame_data *fdata)
{
    if (fdata->pfd)
        g_slist_free(fdata->pfd);
}

/* Dissects IP packet with no layer 2 information. */
epan_dissect_t *
pkt_dissect(char *pkt, size_t len)
{
    epan_dissect_t *edt;
    frame_data fdata;
    union wtap_pseudo_header pseudo_header;

    memset(&pseudo_header, 0, sizeof(pseudo_header) );

    fill_in_framedata(&fdata, len, DLT_RAW);

    edt = epan_dissect_new(1 /* create_proto_tree */,
                           1 /* proto_tree_visible */);

    epan_dissect_run(edt, &pseudo_header, pkt, &fdata, NULL);

    clear_fdata(&fdata);

    return edt;
}

int
main(void)
{
    epan_dissect_t *edt;
    size_t len;

    /* Initialize libwireshark */
    ...

    /* Get a packet */
    pkt = pkt_read(..., &len);

    /* Dissect packet. Only IP packets without L2 information.
       pkt points to the IP header. len is the length of the
       packet (size of IP header + size of payload.) */
    edt = pkt_dissect(pkt, len);

    handle_dissection_results(edt);

    epan_dissect_free(edt);

    return 0;
}
----------------------------------------------------------------------

Let us know how it goes.

Cheers,

Eloy Paris.-
netexpect.org

> 
> What I don't understand is how to make the IP protocol register itself 
> as a "1st layer" protocol (meaning: the dissection should start by 
> seeking IP headers).
> 
> The packet-ip.c has this:
> 
> 
> void
> proto_reg_handoff_ip(void)
> {
>     dissector_handle_t ip_handle;
> 
>         data_handle = find_dissector("data");
>         ip_handle = find_dissector("ip");
>     tapa_handle = find_dissector("tapa");
>     dissector_add("ethertype", ETHERTYPE_IP, ip_handle);
>     dissector_add("ppp.protocol", PPP_IP, ip_handle);
>     dissector_add("ppp.protocol", ETHERTYPE_IP, ip_handle);
>     dissector_add("gre.proto", ETHERTYPE_IP, ip_handle);
>     dissector_add("gre.proto", GRE_WCCP, ip_handle);
>     dissector_add("llc.dsap", SAP_IP, ip_handle);
>     dissector_add("ip.proto", IP_PROTO_IPIP, ip_handle);
>     dissector_add("null.type", BSD_AF_INET, ip_handle);
>     dissector_add("chdlctype", ETHERTYPE_IP, ip_handle);
>     dissector_add("osinl.excl", NLPID_IP, ip_handle);
>     dissector_add("fr.ietf", NLPID_IP, ip_handle);
>     dissector_add("x.25.spi", NLPID_IP, ip_handle);
>         dissector_add("arcnet.protocol_id", ARCNET_PROTO_IP_1051, 
> ip_handle);
>         dissector_add("arcnet.protocol_id", ARCNET_PROTO_IP_1201, 
> ip_handle);
>     dissector_add_handle("udp.port", ip_handle);
> }
> 
> What should I change in there?
> 
> 
> 
> Gilbert Ramirez a �crit :
> >
> > On Tue, Jun 10, 2008 at 7:27 PM, Guillaume Bienkowski
> > <guillaume.bienkowski@xxxxxxxxxxxx> wrote:
> >
> > >
> > > What I know is that my packet data will always contain ONLY the 2nd
> > > layer data (Ethernet) and the encapsulated data (TCP, UDP, ...).
> > >
> >
> > I think I misunderstood you. I thought your packets started at IP or
> > IPX.  Is that not the case?
> >
> > --gilbert
> > _______________________________________________
> > Wireshark-dev mailing list
> > Wireshark-dev@xxxxxxxxxxxxx
> > https://wireshark.org/mailman/listinfo/wireshark-dev
> >
> 
> _______________________________________________
> Wireshark-dev mailing list
> Wireshark-dev@xxxxxxxxxxxxx
> https://wireshark.org/mailman/listinfo/wireshark-dev