Ethereal-dev: Re: [ethereal-dev] tvbuffs for TV Buffs

Note: This archive is from the project's previous web site, ethereal.com. This list is no longer active.

From: Gilbert Ramirez <gram@xxxxxxxxxx>
Date: Wed, 7 Jun 2000 10:26:55 -0500
On Wed, Jun 07, 2000 at 08:07:59AM -0500, Frank Singleton wrote:
> 
> 
> Hi,
> 
> Have written some dissectors and sub dissectors
> and got the handle on handoffs and sub-dissector's
> etc.. ok
> 
> Anyway, I have 2 questions.
> 
> 1. What is a good programming example of using tvbuffs
>    as I want to stay abreast of good ethereal programming
>    practices.
> 
> 2. How hard/difficult/easy is it to convert to tvbuffs ?

I'm glad you asked.

The ease of converting to tvbuffs depends on the dissector itself. There
are two aspects to the conversion. One aspect is changing the code
to use the tvbuff accessor methods to retrieve data. This is an easy change. The
only major thought that goes into it is about optimizing retrievals. In some code,
you might find lots of accesses that are the same:

	var1 = pd[index] & 0xf0;
	var2 = pd[index] & 0x08;
	var3 = pd[index] & 0x04;
	var4 = pd[index] & 0x03;

Instead of repeating the accesses, since you know that tvbuff-lookups add
a bit of overhead, it's better to do this:

	value = tvb_get_guint(tvb, index);
	var1 = value & 0xf0;
	var2 = value & 0x08;
	var3 = value & 0x04;
	var4 = value & 0x03;

For the simplest case of accessing some values and calling the next dissector,
look at packet-raw.c.

The other aspect to conversion takes more thought to deal with. Each dissector
gets handed a tvbuff of type TVBUFF_SUBSET, which is a "virtual" tvbuff. That is,
the dissector access that tvbuff as if the dissector's data started at byte 0 of
the byte array that the tvbuff contains.  Some dissectors don't make heavy use
of their 'offset' variable; they only use it to add to their array index. In that
case, the conversion is simple because you can remove all 'offset's because
the dissector gets to treat 'offset' as 0. See packet-llc.c for an example.

However, other dissectors have functions that take an 'offset' as an argument, and
really do use the 'offset' in a variable way. That is, the helper functions can't
assume that 'offset' is 0. packet-ppp.c is an example of this. It took a bit of
concentration on my part to understand how the various functions in packet-ppp.c
were interacting.

I can't stress enough the importance of regression testing. I wrote the dang
tvbuff.c module, and it took me multiple passes to get my first dissector converted
correctly. The file doc/README.regression is a Makefile that you can use to
perform regression tests via tethereal.

--gilbert