3 * Testy, Virtual(-izable) Buffer of guint8*'s
5 * "Testy" -- the buffer gets mad when an attempt to access data
6 * beyond the bounds of the buffer. An exception is thrown.
8 * "Virtual" -- the buffer can have its own data, can use a subset of
9 * the data of a backing tvbuff, or can be a composite of
14 * Copyright (c) 2000 by Gilbert Ramirez <gram@alumni.rice.edu>
16 * Code to convert IEEE floating point formats to native floating point
17 * derived from code Copyright (c) Ashok Narayanan, 2000
19 * Wireshark - Network traffic analyzer
20 * By Gerald Combs <gerald@wireshark.org>
21 * Copyright 1998 Gerald Combs
23 * This program is free software; you can redistribute it and/or
24 * modify it under the terms of the GNU General Public License
25 * as published by the Free Software Foundation; either version 2
26 * of the License, or (at your option) any later version.
28 * This program is distributed in the hope that it will be useful,
29 * but WITHOUT ANY WARRANTY; without even the implied warranty of
30 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
31 * GNU General Public License for more details.
33 * You should have received a copy of the GNU General Public License
34 * along with this program; if not, write to the Free Software
35 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
52 #include "proto.h" /* XXX - only used for DISSECTOR_ASSERT, probably a new header file? */
55 ensure_contiguous_no_exception(tvbuff_t *tvb, gint offset, gint length,
59 ensure_contiguous(tvbuff_t *tvb, gint offset, gint length);
61 #if GLIB_CHECK_VERSION(2,10,0)
63 /* We dole out tvbuff's from this memchunk. */
64 static GMemChunk *tvbuff_mem_chunk = NULL;
70 #if GLIB_CHECK_VERSION(2,10,0)
72 if (!tvbuff_mem_chunk)
73 tvbuff_mem_chunk = g_mem_chunk_create(tvbuff_t, 20, G_ALLOC_AND_FREE);
80 #if GLIB_CHECK_VERSION(2,10,0)
83 g_mem_chunk_destroy(tvbuff_mem_chunk);
85 tvbuff_mem_chunk = NULL;
90 tvb_init(tvbuff_t *tvb, tvbuff_type type)
92 tvb_backing_t *backing;
93 tvb_comp_t *composite;
96 tvb->initialized = FALSE;
99 tvb->reported_length = 0;
101 tvb->real_data = NULL;
102 tvb->raw_offset = -1;
107 case TVBUFF_REAL_DATA:
112 backing = &tvb->tvbuffs.subset;
118 case TVBUFF_COMPOSITE:
119 composite = &tvb->tvbuffs.composite;
120 composite->tvbs = NULL;
121 composite->start_offsets = NULL;
122 composite->end_offsets = NULL;
126 DISSECTOR_ASSERT_NOT_REACHED();
133 tvb_new(tvbuff_type type)
137 #if GLIB_CHECK_VERSION(2,10,0)
138 tvb = g_slice_new(tvbuff_t);
140 tvb = g_chunk_new(tvbuff_t, tvbuff_mem_chunk);
149 tvb_new_with_subset(guint subset_tvb_offset, guint subset_tvb_length)
151 tvbuff_t *tvb = tvb_new(TVBUFF_SUBSET);
152 tvb->tvbuffs.subset.offset = subset_tvb_offset;
153 tvb->tvbuffs.subset.length = subset_tvb_length;
159 tvb_free(tvbuff_t* tvb)
161 tvbuff_t *member_tvb;
162 tvb_comp_t *composite;
167 if (tvb->usage_count == 0) {
169 case TVBUFF_REAL_DATA:
172 * XXX - do this with a union?
174 tvb->free_cb((gpointer)tvb->real_data);
179 /* This will be NULL if tvb_new_subset() fails because
180 * reported_length < -1 */
181 if (tvb->tvbuffs.subset.tvb) {
182 tvb_decrement_usage_count(tvb->tvbuffs.subset.tvb, 1);
186 case TVBUFF_COMPOSITE:
187 composite = &tvb->tvbuffs.composite;
188 for (slist = composite->tvbs; slist != NULL ; slist = slist->next) {
189 member_tvb = slist->data;
190 tvb_decrement_usage_count(member_tvb, 1);
193 g_slist_free(composite->tvbs);
195 g_free(composite->start_offsets);
196 g_free(composite->end_offsets);
197 if (tvb->real_data) {
199 * XXX - do this with a union?
201 g_free((gpointer)tvb->real_data);
208 g_slist_free(tvb->used_in);
211 #if GLIB_CHECK_VERSION(2,10,0)
212 g_slice_free(tvbuff_t, tvb);
214 g_chunk_free(tvb, tvbuff_mem_chunk);
220 tvb_increment_usage_count(tvbuff_t* tvb, guint count)
222 tvb->usage_count += count;
224 return tvb->usage_count;
228 tvb_decrement_usage_count(tvbuff_t* tvb, guint count)
230 if (tvb->usage_count <= count) {
231 tvb->usage_count = 1;
236 tvb->usage_count -= count;
237 return tvb->usage_count;
243 tvb_free_chain(tvbuff_t* tvb)
247 /* Recursively call tvb_free_chain() */
248 for (slist = tvb->used_in; slist != NULL ; slist = slist->next) {
249 tvb_free_chain( (tvbuff_t*)slist->data );
252 /* Stop the recursion */
259 tvb_set_free_cb(tvbuff_t* tvb, tvbuff_free_cb_t func)
261 DISSECTOR_ASSERT(tvb);
262 DISSECTOR_ASSERT(tvb->type == TVBUFF_REAL_DATA);
267 add_to_used_in_list(tvbuff_t *tvb, tvbuff_t *used_in)
269 tvb->used_in = g_slist_prepend(tvb->used_in, used_in);
270 tvb_increment_usage_count(tvb, 1);
274 tvb_set_child_real_data_tvbuff(tvbuff_t* parent, tvbuff_t* child)
276 DISSECTOR_ASSERT(parent && child);
277 DISSECTOR_ASSERT(parent->initialized);
278 DISSECTOR_ASSERT(child->initialized);
279 DISSECTOR_ASSERT(child->type == TVBUFF_REAL_DATA);
280 add_to_used_in_list(parent, child);
284 tvb_set_real_data_no_exceptions(tvbuff_t* tvb, const guint8* data, guint length, gint reported_length)
286 tvb->real_data = data;
287 tvb->length = length;
288 tvb->reported_length = reported_length;
289 tvb->initialized = TRUE;
293 tvb_set_real_data(tvbuff_t* tvb, const guint8* data, guint length, gint reported_length)
295 DISSECTOR_ASSERT(tvb);
296 DISSECTOR_ASSERT(tvb->type == TVBUFF_REAL_DATA);
297 DISSECTOR_ASSERT(!tvb->initialized);
299 THROW_ON(reported_length < -1, ReportedBoundsError);
301 tvb_set_real_data_no_exceptions(tvb, data, length, reported_length);
305 tvb_new_real_data(const guint8* data, guint length, gint reported_length)
309 THROW_ON(reported_length < -1, ReportedBoundsError);
311 tvb = tvb_new(TVBUFF_REAL_DATA);
313 tvb_set_real_data_no_exceptions(tvb, data, length, reported_length);
316 * This is the top-level real tvbuff for this data source,
317 * so its data source tvbuff is itself.
325 tvb_new_child_real_data(tvbuff_t *parent, const guint8* data, guint length, gint reported_length)
327 tvbuff_t *tvb = tvb_new_real_data(data, length, reported_length);
329 tvb_set_child_real_data_tvbuff (parent, tvb);
335 /* Computes the absolute offset and length based on a possibly-negative offset
336 * and a length that is possible -1 (which means "to the end of the data").
337 * Returns TRUE/FALSE indicating whether the offset is in bounds or
338 * not. The integer ptrs are modified with the new offset and length.
339 * No exception is thrown.
341 * XXX - we return TRUE, not FALSE, if the offset is positive and right
342 * after the end of the tvbuff (i.e., equal to the length). We do this
343 * so that a dissector constructing a subset tvbuff for the next protocol
344 * will get a zero-length tvbuff, not an exception, if there's no data
345 * left for the next protocol - we want the next protocol to be the one
346 * that gets an exception, so the error is reported as an error in that
347 * protocol rather than the containing protocol. */
349 compute_offset_length(guint tvb_length, guint tvb_reported_length, gint offset, gint length,
350 guint *offset_ptr, guint *length_ptr, int *exception)
352 DISSECTOR_ASSERT(offset_ptr);
353 DISSECTOR_ASSERT(length_ptr);
355 /* Compute the offset */
357 /* Positive offset - relative to the beginning of the packet. */
358 if ((guint) offset > tvb_reported_length) {
360 *exception = ReportedBoundsError;
364 else if ((guint) offset > tvb_length) {
366 *exception = BoundsError;
371 *offset_ptr = offset;
375 /* Negative offset - relative to the end of the packet. */
376 if ((guint) -offset > tvb_reported_length) {
378 *exception = ReportedBoundsError;
382 else if ((guint) -offset > tvb_length) {
384 *exception = BoundsError;
389 *offset_ptr = tvb_length + offset;
393 /* Compute the length */
396 /* XXX - ReportedBoundsError? */
397 *exception = BoundsError;
401 else if (length == -1) {
402 *length_ptr = tvb_length - *offset_ptr;
405 *length_ptr = length;
413 check_offset_length_no_exception(guint tvb_length, guint tvb_reported_length, gint offset, gint length,
414 guint *offset_ptr, guint *length_ptr, int *exception)
418 if (!compute_offset_length(tvb_length, tvb_reported_length, offset, length, offset_ptr, length_ptr, exception)) {
423 * Compute the offset of the first byte past the length.
425 end_offset = *offset_ptr + *length_ptr;
428 * Check for an overflow, and clamp "end_offset" at the maximum
429 * if we got an overflow - that should force us to indicate that
430 * we're past the end of the tvbuff.
432 if (end_offset < *offset_ptr)
433 end_offset = UINT_MAX;
436 * Check whether that offset goes more than one byte past the
439 * If not, return TRUE; otherwise, return FALSE and, if "exception"
440 * is non-null, return the appropriate exception through it.
442 if (end_offset <= tvb_length) {
445 else if (end_offset <= tvb_reported_length) {
447 *exception = BoundsError;
452 *exception = ReportedBoundsError;
459 /* Checks (+/-) offset and length and throws an exception if
460 * either is out of bounds. Sets integer ptrs to the new offset
463 check_offset_length(guint tvb_length, guint tvb_reported_length, gint offset, gint length,
464 guint *offset_ptr, guint *length_ptr)
468 if (!check_offset_length_no_exception(tvb_length, tvb_reported_length, offset, length, offset_ptr, length_ptr, &exception)) {
469 DISSECTOR_ASSERT(exception > 0);
475 tvb_set_subset_no_exceptions(tvbuff_t *tvb, tvbuff_t *backing, gint reported_length)
477 tvb->tvbuffs.subset.tvb = backing;
478 tvb->length = tvb->tvbuffs.subset.length;
480 if (reported_length == -1) {
481 tvb->reported_length = backing->reported_length - tvb->tvbuffs.subset.offset;
484 tvb->reported_length = reported_length;
486 tvb->initialized = TRUE;
487 add_to_used_in_list(backing, tvb);
489 /* Optimization. If the backing buffer has a pointer to contiguous, real data,
490 * then we can point directly to our starting offset in that buffer */
491 if (backing->real_data != NULL) {
492 tvb->real_data = backing->real_data + tvb->tvbuffs.subset.offset;
497 tvb_set_subset(tvbuff_t *tvb, tvbuff_t *backing,
498 gint backing_offset, gint backing_length, gint reported_length)
500 DISSECTOR_ASSERT(tvb);
501 DISSECTOR_ASSERT(tvb->type == TVBUFF_SUBSET);
502 DISSECTOR_ASSERT(!tvb->initialized);
504 THROW_ON(reported_length < -1, ReportedBoundsError);
506 check_offset_length(backing->length, backing->reported_length, backing_offset, backing_length,
507 &tvb->tvbuffs.subset.offset,
508 &tvb->tvbuffs.subset.length);
510 tvb_set_subset_no_exceptions(tvb, backing, reported_length);
514 tvb_new_subset(tvbuff_t *backing, gint backing_offset, gint backing_length, gint reported_length)
517 guint subset_tvb_offset;
518 guint subset_tvb_length;
520 DISSECTOR_ASSERT(backing && backing->initialized);
522 THROW_ON(reported_length < -1, ReportedBoundsError);
524 check_offset_length(backing->length, backing->reported_length, backing_offset, backing_length,
528 tvb = tvb_new_with_subset(subset_tvb_offset, subset_tvb_length);
530 tvb_set_subset_no_exceptions(tvb, backing, reported_length);
533 * The top-level data source of this tvbuff is the top-level
534 * data source of its parent.
536 tvb->ds_tvb = backing->ds_tvb;
542 tvb_new_subset_remaining(tvbuff_t *backing, gint backing_offset)
545 guint subset_tvb_offset;
546 guint subset_tvb_length;
548 check_offset_length(backing->length, backing->reported_length, backing_offset, -1 /* backing_length */,
552 tvb = tvb_new_with_subset(subset_tvb_offset, subset_tvb_length);
554 tvb_set_subset_no_exceptions(tvb, backing, -1 /* reported_length */);
557 * The top-level data source of this tvbuff is the top-level
558 * data source of its parent.
560 tvb->ds_tvb = backing->ds_tvb;
566 tvb_composite_append(tvbuff_t* tvb, tvbuff_t* member)
568 tvb_comp_t *composite;
570 DISSECTOR_ASSERT(tvb && !tvb->initialized);
571 DISSECTOR_ASSERT(tvb->type == TVBUFF_COMPOSITE);
572 composite = &tvb->tvbuffs.composite;
573 composite->tvbs = g_slist_append( composite->tvbs, member );
574 add_to_used_in_list(tvb, member);
578 tvb_composite_prepend(tvbuff_t* tvb, tvbuff_t* member)
580 tvb_comp_t *composite;
582 DISSECTOR_ASSERT(tvb && !tvb->initialized);
583 DISSECTOR_ASSERT(tvb->type == TVBUFF_COMPOSITE);
584 composite = &tvb->tvbuffs.composite;
585 composite->tvbs = g_slist_prepend( composite->tvbs, member );
586 add_to_used_in_list(tvb, member);
590 tvb_new_composite(void)
592 return tvb_new(TVBUFF_COMPOSITE);
596 tvb_composite_finalize(tvbuff_t* tvb)
600 tvbuff_t *member_tvb;
601 tvb_comp_t *composite;
604 DISSECTOR_ASSERT(tvb && !tvb->initialized);
605 DISSECTOR_ASSERT(tvb->type == TVBUFF_COMPOSITE);
606 DISSECTOR_ASSERT(tvb->length == 0);
608 composite = &tvb->tvbuffs.composite;
609 num_members = g_slist_length(composite->tvbs);
611 composite->start_offsets = g_new(guint, num_members);
612 composite->end_offsets = g_new(guint, num_members);
614 for (slist = composite->tvbs; slist != NULL; slist = slist->next) {
615 DISSECTOR_ASSERT((guint) i < num_members);
616 member_tvb = slist->data;
617 composite->start_offsets[i] = tvb->length;
618 tvb->length += member_tvb->length;
619 composite->end_offsets[i] = tvb->length - 1;
623 tvb->initialized = TRUE;
629 tvb_length(tvbuff_t* tvb)
631 DISSECTOR_ASSERT(tvb && tvb->initialized);
637 tvb_length_remaining(tvbuff_t *tvb, gint offset)
639 guint abs_offset, abs_length;
641 DISSECTOR_ASSERT(tvb && tvb->initialized);
643 if (compute_offset_length(tvb->length, tvb->reported_length, offset, -1, &abs_offset, &abs_length, NULL)) {
652 tvb_ensure_length_remaining(tvbuff_t *tvb, gint offset)
654 guint abs_offset, abs_length;
657 DISSECTOR_ASSERT(tvb && tvb->initialized);
659 if (!compute_offset_length(tvb->length, tvb->reported_length, offset, -1, &abs_offset, &abs_length, &exception)) {
662 if (abs_length == 0) {
664 * This routine ensures there's at least one byte available.
665 * There aren't any bytes available, so throw the appropriate
668 if (abs_offset >= tvb->reported_length)
669 THROW(ReportedBoundsError);
679 /* Validates that 'length' bytes are available starting from
680 * offset (pos/neg). Does not throw an exception. */
682 tvb_bytes_exist(tvbuff_t *tvb, gint offset, gint length)
684 guint abs_offset, abs_length;
686 DISSECTOR_ASSERT(tvb && tvb->initialized);
688 if (!compute_offset_length(tvb->length, tvb->reported_length, offset, length, &abs_offset, &abs_length, NULL))
691 if (abs_offset + abs_length <= tvb->length) {
699 /* Validates that 'length' bytes are available starting from
700 * offset (pos/neg). Throws an exception if they aren't. */
702 tvb_ensure_bytes_exist(tvbuff_t *tvb, gint offset, gint length)
704 guint abs_offset, abs_length;
706 DISSECTOR_ASSERT(tvb && tvb->initialized);
709 * -1 doesn't mean "until end of buffer", as that's pointless
710 * for this routine. We must treat it as a Really Large Positive
711 * Number, so that we throw an exception; we throw
712 * ReportedBoundsError, as if it were past even the end of a
713 * reassembled packet, and past the end of even the data we
716 * We do the same with other negative lengths.
719 THROW(ReportedBoundsError);
721 check_offset_length(tvb->length, tvb->reported_length, offset, length, &abs_offset, &abs_length);
725 tvb_offset_exists(tvbuff_t *tvb, gint offset)
727 guint abs_offset, abs_length;
729 DISSECTOR_ASSERT(tvb && tvb->initialized);
730 if (!compute_offset_length(tvb->length, tvb->reported_length, offset, -1, &abs_offset, &abs_length, NULL))
733 if (abs_offset < tvb->length) {
742 tvb_reported_length(tvbuff_t* tvb)
744 DISSECTOR_ASSERT(tvb && tvb->initialized);
746 return tvb->reported_length;
750 tvb_reported_length_remaining(tvbuff_t *tvb, gint offset)
752 guint abs_offset, abs_length;
754 DISSECTOR_ASSERT(tvb && tvb->initialized);
756 if (compute_offset_length(tvb->length, tvb->reported_length, offset, -1, &abs_offset, &abs_length, NULL)) {
757 if (tvb->reported_length >= abs_offset)
758 return tvb->reported_length - abs_offset;
767 /* Set the reported length of a tvbuff to a given value; used for protocols
768 whose headers contain an explicit length and where the calling
769 dissector's payload may include padding as well as the packet for
772 Also adjusts the data length. */
774 tvb_set_reported_length(tvbuff_t* tvb, guint reported_length)
776 DISSECTOR_ASSERT(tvb && tvb->initialized);
778 if (reported_length > tvb->reported_length)
779 THROW(ReportedBoundsError);
781 tvb->reported_length = reported_length;
782 if (reported_length < tvb->length)
783 tvb->length = reported_length;
789 first_real_data_ptr(tvbuff_t *tvb)
794 case TVBUFF_REAL_DATA:
795 return tvb->real_data;
797 member = tvb->tvbuffs.subset.tvb;
798 return first_real_data_ptr(member);
799 case TVBUFF_COMPOSITE:
800 member = tvb->tvbuffs.composite.tvbs->data;
801 return first_real_data_ptr(member);
804 DISSECTOR_ASSERT_NOT_REACHED();
810 offset_from_real_beginning(tvbuff_t *tvb, guint counter)
815 case TVBUFF_REAL_DATA:
818 member = tvb->tvbuffs.subset.tvb;
819 return offset_from_real_beginning(member, counter + tvb->tvbuffs.subset.offset);
820 case TVBUFF_COMPOSITE:
821 member = tvb->tvbuffs.composite.tvbs->data;
822 return offset_from_real_beginning(member, counter);
825 DISSECTOR_ASSERT_NOT_REACHED();
830 tvb_offset_from_real_beginning(tvbuff_t *tvb)
832 return offset_from_real_beginning(tvb, 0);
836 composite_ensure_contiguous_no_exception(tvbuff_t *tvb, guint abs_offset,
839 guint i, num_members;
840 tvb_comp_t *composite;
841 tvbuff_t *member_tvb = NULL;
842 guint member_offset, member_length;
845 DISSECTOR_ASSERT(tvb->type == TVBUFF_COMPOSITE);
847 /* Maybe the range specified by offset/length
848 * is contiguous inside one of the member tvbuffs */
849 composite = &tvb->tvbuffs.composite;
850 num_members = g_slist_length(composite->tvbs);
852 for (i = 0; i < num_members; i++) {
853 if (abs_offset <= composite->end_offsets[i]) {
854 slist = g_slist_nth(composite->tvbs, i);
855 member_tvb = slist->data;
859 DISSECTOR_ASSERT(member_tvb);
861 if (check_offset_length_no_exception(member_tvb->length, member_tvb->reported_length, abs_offset - composite->start_offsets[i],
862 abs_length, &member_offset, &member_length, NULL)) {
865 * The range is, in fact, contiguous within member_tvb.
867 DISSECTOR_ASSERT(!tvb->real_data);
868 return ensure_contiguous_no_exception(member_tvb, member_offset, member_length, NULL);
871 tvb->real_data = tvb_memdup(tvb, 0, -1);
872 return tvb->real_data + abs_offset;
875 DISSECTOR_ASSERT_NOT_REACHED();
880 ensure_contiguous_no_exception(tvbuff_t *tvb, gint offset, gint length,
883 guint abs_offset, abs_length;
885 if (!check_offset_length_no_exception(tvb->length, tvb->reported_length, offset, length,
886 &abs_offset, &abs_length, exception)) {
891 * We know that all the data is present in the tvbuff, so
892 * no exceptions should be thrown.
894 if (tvb->real_data) {
895 return tvb->real_data + abs_offset;
899 case TVBUFF_REAL_DATA:
900 DISSECTOR_ASSERT_NOT_REACHED();
902 return ensure_contiguous_no_exception(tvb->tvbuffs.subset.tvb,
903 abs_offset - tvb->tvbuffs.subset.offset,
905 case TVBUFF_COMPOSITE:
906 return composite_ensure_contiguous_no_exception(tvb, abs_offset, abs_length);
910 DISSECTOR_ASSERT_NOT_REACHED();
915 ensure_contiguous(tvbuff_t *tvb, gint offset, gint length)
920 p = ensure_contiguous_no_exception(tvb, offset, length, &exception);
922 DISSECTOR_ASSERT(exception > 0);
929 fast_ensure_contiguous(tvbuff_t *tvb, gint offset, guint length)
934 DISSECTOR_ASSERT(tvb && tvb->initialized);
935 /* We don't check for overflow in this fast path so we only handle simple types */
936 DISSECTOR_ASSERT(length <= 8);
938 if (offset < 0 || !tvb->real_data) {
939 return ensure_contiguous(tvb, offset, length);
943 end_offset = u_offset + length;
945 if (end_offset <= tvb->length) {
946 return tvb->real_data + u_offset;
949 if (end_offset > tvb->reported_length) {
950 THROW(ReportedBoundsError);
958 guint8_find(const guint8* haystack, size_t haystacklen, guint8 needle)
963 for (b = haystack, i = 0; (guint) i < haystacklen; i++, b++) {
973 guint8_pbrk(const guint8* haystack, size_t haystacklen, const guint8 *needles)
978 const guint8 *needlep;
980 for (b = haystack, i = 0; (guint) i < haystacklen; i++, b++) {
983 while ((needle = *needlep) != '\0') {
995 /************** ACCESSORS **************/
998 composite_memcpy(tvbuff_t *tvb, guint8* target, guint abs_offset, size_t abs_length)
1000 guint i, num_members;
1001 tvb_comp_t *composite;
1002 tvbuff_t *member_tvb = NULL;
1003 guint member_offset, member_length;
1007 DISSECTOR_ASSERT(tvb->type == TVBUFF_COMPOSITE);
1009 /* Maybe the range specified by offset/length
1010 * is contiguous inside one of the member tvbuffs */
1011 composite = &tvb->tvbuffs.composite;
1012 num_members = g_slist_length(composite->tvbs);
1014 for (i = 0; i < num_members; i++) {
1015 if (abs_offset <= composite->end_offsets[i]) {
1016 slist = g_slist_nth(composite->tvbs, i);
1017 member_tvb = slist->data;
1021 DISSECTOR_ASSERT(member_tvb);
1023 if (check_offset_length_no_exception(member_tvb->length, member_tvb->reported_length, abs_offset - composite->start_offsets[i],
1024 (gint) abs_length, &member_offset, &member_length, NULL)) {
1026 DISSECTOR_ASSERT(!tvb->real_data);
1027 return tvb_memcpy(member_tvb, target, member_offset, member_length);
1030 /* The requested data is non-contiguous inside
1031 * the member tvb. We have to memcpy() the part that's in the member tvb,
1032 * then iterate across the other member tvb's, copying their portions
1033 * until we have copied all data.
1035 retval = compute_offset_length(member_tvb->length, member_tvb->reported_length, abs_offset - composite->start_offsets[i], -1,
1036 &member_offset, &member_length, NULL);
1037 DISSECTOR_ASSERT(retval);
1039 tvb_memcpy(member_tvb, target, member_offset, member_length);
1040 abs_offset += member_length;
1041 abs_length -= member_length;
1044 if (abs_length > 0) {
1045 composite_memcpy(tvb, target + member_length, abs_offset, abs_length);
1051 DISSECTOR_ASSERT_NOT_REACHED();
1056 tvb_memcpy(tvbuff_t *tvb, void* target, gint offset, size_t length)
1058 guint abs_offset, abs_length;
1060 DISSECTOR_ASSERT(tvb && tvb->initialized);
1063 * XXX - we should eliminate the "length = -1 means 'to the end
1064 * of the tvbuff'" convention, and use other means to achieve
1065 * that; this would let us eliminate a bunch of checks for
1066 * negative lengths in cases where the protocol has a 32-bit
1069 * Allowing -1 but throwing an assertion on other negative
1070 * lengths is a bit more work with the length being a size_t;
1071 * instead, we check for a length <= 2^31-1.
1073 DISSECTOR_ASSERT(length <= 0x7FFFFFFF);
1074 check_offset_length(tvb->length, tvb->reported_length, offset, (gint) length, &abs_offset, &abs_length);
1076 if (tvb->real_data) {
1077 return memcpy(target, tvb->real_data + abs_offset, abs_length);
1081 case TVBUFF_REAL_DATA:
1082 DISSECTOR_ASSERT_NOT_REACHED();
1085 return tvb_memcpy(tvb->tvbuffs.subset.tvb, target,
1086 abs_offset - tvb->tvbuffs.subset.offset,
1089 case TVBUFF_COMPOSITE:
1090 return composite_memcpy(tvb, target, offset, length);
1093 DISSECTOR_ASSERT_NOT_REACHED();
1099 * XXX - this doesn't treat a length of -1 as an error.
1100 * If it did, this could replace some code that calls
1101 * "tvb_ensure_bytes_exist()" and then allocates a buffer and copies
1104 * "composite_ensure_contiguous_no_exception()" depends on -1 not being
1105 * an error; does anything else depend on this routine treating -1 as
1106 * meaning "to the end of the buffer"?
1109 tvb_memdup(tvbuff_t *tvb, gint offset, size_t length)
1111 guint abs_offset, abs_length;
1114 DISSECTOR_ASSERT(tvb && tvb->initialized);
1116 check_offset_length(tvb->length, tvb->reported_length, offset, (gint) length, &abs_offset, &abs_length);
1118 duped = g_malloc(abs_length);
1119 return tvb_memcpy(tvb, duped, abs_offset, abs_length);
1123 * XXX - this doesn't treat a length of -1 as an error.
1124 * If it did, this could replace some code that calls
1125 * "tvb_ensure_bytes_exist()" and then allocates a buffer and copies
1128 * "composite_ensure_contiguous_no_exception()" depends on -1 not being
1129 * an error; does anything else depend on this routine treating -1 as
1130 * meaning "to the end of the buffer"?
1132 * This function allocates memory from a buffer with packet lifetime.
1133 * You do not have to free this buffer, it will be automatically freed
1134 * when wireshark starts decoding the next packet.
1135 * Do not use this function if you want the allocated memory to be persistent
1136 * after the current packet has been dissected.
1139 ep_tvb_memdup(tvbuff_t *tvb, gint offset, size_t length)
1141 guint abs_offset, abs_length;
1144 DISSECTOR_ASSERT(tvb && tvb->initialized);
1146 check_offset_length(tvb->length, tvb->reported_length, offset, (gint) length, &abs_offset, &abs_length);
1148 duped = ep_alloc(abs_length);
1149 return tvb_memcpy(tvb, duped, abs_offset, abs_length);
1155 tvb_get_ptr(tvbuff_t *tvb, gint offset, gint length)
1157 return ensure_contiguous(tvb, offset, length);
1160 /* ---------------- */
1162 tvb_get_guint8(tvbuff_t *tvb, gint offset)
1166 ptr = fast_ensure_contiguous(tvb, offset, sizeof(guint8));
1171 tvb_get_ntohs(tvbuff_t *tvb, gint offset)
1175 ptr = fast_ensure_contiguous(tvb, offset, sizeof(guint16));
1180 tvb_get_ntoh24(tvbuff_t *tvb, gint offset)
1184 ptr = fast_ensure_contiguous(tvb, offset, 3);
1185 return pntoh24(ptr);
1189 tvb_get_ntohl(tvbuff_t *tvb, gint offset)
1193 ptr = fast_ensure_contiguous(tvb, offset, sizeof(guint32));
1198 tvb_get_ntoh64(tvbuff_t *tvb, gint offset)
1202 ptr = fast_ensure_contiguous(tvb, offset, sizeof(guint64));
1203 return pntoh64(ptr);
1207 * Stuff for IEEE float handling on platforms that don't have IEEE
1208 * format as the native floating-point format.
1210 * For now, we treat only the VAX as such a platform.
1212 * XXX - other non-IEEE boxes that can run UNIX include some Crays,
1213 * and possibly other machines.
1215 * It appears that the official Linux port to System/390 and
1216 * zArchitecture uses IEEE format floating point (not a
1219 * I don't know whether there are any other machines that
1220 * could run Wireshark and that don't use IEEE format.
1221 * As far as I know, all of the main commercial microprocessor
1222 * families on which OSes that support Wireshark can run
1223 * use IEEE format (x86, 68k, SPARC, MIPS, PA-RISC, Alpha,
1224 * IA-64, and so on).
1234 #define IEEE_SP_NUMBER_WIDTH 32 /* bits in number */
1235 #define IEEE_SP_EXP_WIDTH 8 /* bits in exponent */
1236 #define IEEE_SP_MANTISSA_WIDTH 23 /* IEEE_SP_NUMBER_WIDTH - 1 - IEEE_SP_EXP_WIDTH */
1238 #define IEEE_SP_SIGN_MASK 0x80000000
1239 #define IEEE_SP_EXPONENT_MASK 0x7F800000
1240 #define IEEE_SP_MANTISSA_MASK 0x007FFFFF
1241 #define IEEE_SP_INFINITY IEEE_SP_EXPONENT_MASK
1243 #define IEEE_SP_IMPLIED_BIT (1 << IEEE_SP_MANTISSA_WIDTH)
1244 #define IEEE_SP_INFINITE ((1 << IEEE_SP_EXP_WIDTH) - 1)
1245 #define IEEE_SP_BIAS ((1 << (IEEE_SP_EXP_WIDTH - 1)) - 1)
1248 ieee_float_is_zero(guint32 w)
1250 return ((w & ~IEEE_SP_SIGN_MASK) == 0);
1254 get_ieee_float(guint32 w)
1260 sign = w & IEEE_SP_SIGN_MASK;
1261 exponent = w & IEEE_SP_EXPONENT_MASK;
1262 mantissa = w & IEEE_SP_MANTISSA_MASK;
1264 if (ieee_float_is_zero(w)) {
1265 /* number is zero, unnormalized, or not-a-number */
1270 * XXX - how to handle this?
1272 if (IEEE_SP_INFINITY == exponent) {
1274 * number is positive or negative infinity, or a special value
1276 return (sign? MINUS_INFINITY: PLUS_INFINITY);
1280 exponent = ((exponent >> IEEE_SP_MANTISSA_WIDTH) - IEEE_SP_BIAS) -
1281 IEEE_SP_MANTISSA_WIDTH;
1282 mantissa |= IEEE_SP_IMPLIED_BIT;
1285 return -mantissa * pow(2, exponent);
1287 return mantissa * pow(2, exponent);
1292 * We assume that if you don't have IEEE floating-point, you have a
1293 * compiler that understands 64-bit integral quantities.
1295 #define IEEE_DP_NUMBER_WIDTH 64 /* bits in number */
1296 #define IEEE_DP_EXP_WIDTH 11 /* bits in exponent */
1297 #define IEEE_DP_MANTISSA_WIDTH 52 /* IEEE_DP_NUMBER_WIDTH - 1 - IEEE_DP_EXP_WIDTH */
1299 #define IEEE_DP_SIGN_MASK 0x8000000000000000LL
1300 #define IEEE_DP_EXPONENT_MASK 0x7FF0000000000000LL
1301 #define IEEE_DP_MANTISSA_MASK 0x000FFFFFFFFFFFFFLL
1302 #define IEEE_DP_INFINITY IEEE_DP_EXPONENT_MASK
1304 #define IEEE_DP_IMPLIED_BIT (1LL << IEEE_DP_MANTISSA_WIDTH)
1305 #define IEEE_DP_INFINITE ((1 << IEEE_DP_EXP_WIDTH) - 1)
1306 #define IEEE_DP_BIAS ((1 << (IEEE_DP_EXP_WIDTH - 1)) - 1)
1309 ieee_double_is_zero(guint64 w)
1311 return ((w & ~IEEE_SP_SIGN_MASK) == 0);
1315 get_ieee_double(guint64 w)
1321 sign = w & IEEE_DP_SIGN_MASK;
1322 exponent = w & IEEE_DP_EXPONENT_MASK;
1323 mantissa = w & IEEE_DP_MANTISSA_MASK;
1325 if (ieee_double_is_zero(w)) {
1326 /* number is zero, unnormalized, or not-a-number */
1331 * XXX - how to handle this?
1333 if (IEEE_DP_INFINITY == exponent) {
1335 * number is positive or negative infinity, or a special value
1337 return (sign? MINUS_INFINITY: PLUS_INFINITY);
1341 exponent = ((exponent >> IEEE_DP_MANTISSA_WIDTH) - IEEE_DP_BIAS) -
1342 IEEE_DP_MANTISSA_WIDTH;
1343 mantissa |= IEEE_DP_IMPLIED_BIT;
1346 return -mantissa * pow(2, exponent);
1348 return mantissa * pow(2, exponent);
1353 * Fetches an IEEE single-precision floating-point number, in
1354 * big-endian form, and returns a "float".
1356 * XXX - should this be "double", in case there are IEEE single-
1357 * precision numbers that won't fit in some platform's native
1361 tvb_get_ntohieee_float(tvbuff_t *tvb, int offset)
1364 return get_ieee_float(tvb_get_ntohl(tvb, offset));
1371 ieee_fp_union.w = tvb_get_ntohl(tvb, offset);
1372 return ieee_fp_union.f;
1377 * Fetches an IEEE double-precision floating-point number, in
1378 * big-endian form, and returns a "double".
1381 tvb_get_ntohieee_double(tvbuff_t *tvb, int offset)
1395 #ifdef WORDS_BIGENDIAN
1396 ieee_fp_union.w[0] = tvb_get_ntohl(tvb, offset);
1397 ieee_fp_union.w[1] = tvb_get_ntohl(tvb, offset+4);
1399 ieee_fp_union.w[0] = tvb_get_ntohl(tvb, offset+4);
1400 ieee_fp_union.w[1] = tvb_get_ntohl(tvb, offset);
1403 return get_ieee_double(ieee_fp_union.dw);
1405 return ieee_fp_union.d;
1410 tvb_get_letohs(tvbuff_t *tvb, gint offset)
1414 ptr = fast_ensure_contiguous(tvb, offset, sizeof(guint16));
1415 return pletohs(ptr);
1419 tvb_get_letoh24(tvbuff_t *tvb, gint offset)
1423 ptr = fast_ensure_contiguous(tvb, offset, 3);
1424 return pletoh24(ptr);
1428 tvb_get_letohl(tvbuff_t *tvb, gint offset)
1432 ptr = fast_ensure_contiguous(tvb, offset, sizeof(guint32));
1433 return pletohl(ptr);
1437 tvb_get_letoh64(tvbuff_t *tvb, gint offset)
1441 ptr = fast_ensure_contiguous(tvb, offset, sizeof(guint64));
1442 return pletoh64(ptr);
1446 * Fetches an IEEE single-precision floating-point number, in
1447 * little-endian form, and returns a "float".
1449 * XXX - should this be "double", in case there are IEEE single-
1450 * precision numbers that won't fit in some platform's native
1454 tvb_get_letohieee_float(tvbuff_t *tvb, int offset)
1457 return get_ieee_float(tvb_get_letohl(tvb, offset));
1464 ieee_fp_union.w = tvb_get_letohl(tvb, offset);
1465 return ieee_fp_union.f;
1470 * Fetches an IEEE double-precision floating-point number, in
1471 * little-endian form, and returns a "double".
1474 tvb_get_letohieee_double(tvbuff_t *tvb, int offset)
1488 #ifdef WORDS_BIGENDIAN
1489 ieee_fp_union.w[0] = tvb_get_letohl(tvb, offset+4);
1490 ieee_fp_union.w[1] = tvb_get_letohl(tvb, offset);
1492 ieee_fp_union.w[0] = tvb_get_letohl(tvb, offset);
1493 ieee_fp_union.w[1] = tvb_get_letohl(tvb, offset+4);
1496 return get_ieee_double(ieee_fp_union.dw);
1498 return ieee_fp_union.d;
1502 /* Fetch an IPv4 address, in network byte order.
1503 * We do *not* convert them to host byte order; we leave them in
1504 * network byte order. */
1506 tvb_get_ipv4(tvbuff_t *tvb, gint offset)
1511 ptr = fast_ensure_contiguous(tvb, offset, sizeof(guint32));
1512 memcpy(&addr, ptr, sizeof addr);
1516 /* Fetch an IPv6 address. */
1518 tvb_get_ipv6(tvbuff_t *tvb, gint offset, struct e_in6_addr *addr)
1522 ptr = ensure_contiguous(tvb, offset, sizeof(*addr));
1523 memcpy(addr, ptr, sizeof *addr);
1528 tvb_get_ntohguid(tvbuff_t *tvb, gint offset, e_guid_t *guid)
1530 ensure_contiguous(tvb, offset, sizeof(*guid));
1531 guid->data1 = tvb_get_ntohl(tvb, offset);
1532 guid->data2 = tvb_get_ntohs(tvb, offset + 4);
1533 guid->data3 = tvb_get_ntohs(tvb, offset + 6);
1534 tvb_memcpy(tvb, guid->data4, offset + 8, sizeof guid->data4);
1538 tvb_get_letohguid(tvbuff_t *tvb, gint offset, e_guid_t *guid)
1540 ensure_contiguous(tvb, offset, sizeof(*guid));
1541 guid->data1 = tvb_get_letohl(tvb, offset);
1542 guid->data2 = tvb_get_letohs(tvb, offset + 4);
1543 guid->data3 = tvb_get_letohs(tvb, offset + 6);
1544 tvb_memcpy(tvb, guid->data4, offset + 8, sizeof guid->data4);
1548 tvb_get_guid(tvbuff_t *tvb, gint offset, e_guid_t *guid, gboolean little_endian)
1550 if (little_endian) {
1551 tvb_get_letohguid(tvb, offset, guid);
1553 tvb_get_ntohguid(tvb, offset, guid);
1557 static const guint8 bit_mask8[] = {
1568 /* Bit offset mask for number of bits = 8 - 16 */
1569 static const guint16 bit_mask16[] = {
1580 /* Get 1 - 8 bits */
1582 tvb_get_bits8(tvbuff_t *tvb, gint bit_offset, gint no_of_bits)
1589 DISSECTOR_ASSERT_NOT_REACHED();
1591 /* Byte align offset */
1592 offset = bit_offset>>3;
1594 /* Find out which mask to use for the most significant octet
1595 * by convering bit_offset into the offset into the first
1598 bit_offset = bit_offset & 0x7;
1599 tot_no_bits = bit_offset+no_of_bits;
1601 /* Read one octet, mask off bit_offset bits and left shift out the unused bits */
1602 value = tvb_get_guint8(tvb,offset) & bit_mask8[bit_offset];
1603 value = value >> (8-tot_no_bits);
1605 /* Read two octets, mask off bit_offset bits and left shift out the unused bits */
1606 value = tvb_get_ntohs(tvb,offset) & bit_mask16[bit_offset];
1607 value = value >> (16 - tot_no_bits);
1610 return (guint8)value;
1613 /* Get 9 - 16 bits */
1614 /* Bit offset mask for number of bits = 16 - 32 */
1615 static const guint32 bit_mask32[] = {
1627 tvb_get_bits16(tvbuff_t *tvb, gint bit_offset, gint no_of_bits,gboolean little_endian)
1631 guint16 tempval = 0;
1634 if ((no_of_bits<=8)||(no_of_bits>16)) {
1635 /* If bits <= 8 use tvb_get_bits8 */
1636 DISSECTOR_ASSERT_NOT_REACHED();
1639 DISSECTOR_ASSERT_NOT_REACHED();
1640 /* This part is not implemented yet */
1643 /* Byte align offset */
1644 offset = bit_offset>>3;
1646 /* Find out which mask to use for the most significant octet
1647 * by convering bit_offset into the offset into the first
1650 bit_offset = bit_offset & 0x7;
1651 tot_no_bits = bit_offset+no_of_bits;
1652 /* Read two octets and mask off bit_offset bits */
1653 value = tvb_get_ntohs(tvb,offset) & bit_mask16[bit_offset];
1654 if(tot_no_bits < 16){
1655 /* Left shift out the unused bits */
1656 value = value >> (16 - tot_no_bits);
1657 }else if(tot_no_bits > 16){
1658 /* Spans three octets, read next octet and shift as needed */
1659 value = value << (tot_no_bits - 16);
1660 tempval = tvb_get_guint8(tvb,offset+2);
1661 tempval = tempval >> (24-tot_no_bits);
1662 value = value | tempval;
1668 /* Bit offset mask for number of bits = 32 - 64 */
1669 static const guint64 bit_mask64[] = {
1670 G_GINT64_CONSTANT(0xffffffffffffffffU),
1671 G_GINT64_CONSTANT(0x7fffffffffffffffU),
1672 G_GINT64_CONSTANT(0x3fffffffffffffffU),
1673 G_GINT64_CONSTANT(0x1fffffffffffffffU),
1674 G_GINT64_CONSTANT(0x0fffffffffffffffU),
1675 G_GINT64_CONSTANT(0x07ffffffffffffffU),
1676 G_GINT64_CONSTANT(0x03ffffffffffffffU),
1677 G_GINT64_CONSTANT(0x01ffffffffffffffU)
1681 tvb_get_bits32(tvbuff_t *tvb, gint bit_offset, gint no_of_bits, gboolean little_endian)
1685 guint32 tempval = 0;
1688 if ((no_of_bits<=16)||(no_of_bits>32)) {
1689 /* If bits <= 16 use tvb_get_bits8 or tvb_get_bits16 */
1690 DISSECTOR_ASSERT_NOT_REACHED();
1693 DISSECTOR_ASSERT_NOT_REACHED();
1694 /* This part is not implemented yet */
1697 /* Byte align offset */
1698 offset = bit_offset>>3;
1700 /* Find out which mask to use for the most significant octet
1701 * by convering bit_offset into the offset into the first
1704 bit_offset = bit_offset & 0x7;
1705 tot_no_bits = bit_offset+no_of_bits;
1706 /* Read four octets and mask off bit_offset bits */
1707 value = tvb_get_ntohl(tvb,offset) & bit_mask32[bit_offset];
1708 if(tot_no_bits < 32){
1709 /* Left shift out the unused bits */
1710 value = value >> (32 - tot_no_bits);
1711 }else if(tot_no_bits > 32){
1712 /* Spans five octets, read next octet and shift as needed */
1713 value = value << (tot_no_bits - 32);
1714 tempval = tvb_get_guint8(tvb,offset+4);
1715 tempval = tempval >> (40-tot_no_bits);
1716 value = value | tempval;
1723 tvb_get_bits64(tvbuff_t *tvb, gint bit_offset, gint no_of_bits, gboolean little_endian)
1727 guint64 tempval = 0;
1730 if ((no_of_bits<=32)||(no_of_bits>64)) {
1731 /* If bits <= 32 use tvb_get_bits8, tvb_get_bits16 or tvb_get_bits32 */
1732 DISSECTOR_ASSERT_NOT_REACHED();
1735 DISSECTOR_ASSERT_NOT_REACHED();
1736 /* This part is not implemented yet */
1739 /* Byte align offset */
1740 offset = bit_offset>>3;
1742 /* Find out which mask to use for the most significant octet
1743 * by convering bit_offset into the offset into the first
1746 bit_offset = bit_offset & 0x7;
1747 tot_no_bits = bit_offset+no_of_bits;
1748 /* Read eight octets and mask off bit_offset bits */
1749 value = tvb_get_ntoh64(tvb,offset) & bit_mask64[bit_offset];
1750 if (tot_no_bits < 64){
1751 /* Left shift out the unused bits */
1752 value = value >> (64 - tot_no_bits);
1753 }else if (tot_no_bits > 64){
1754 /* Spans nine octets, read next octet and shift as needed */
1755 value = value << (tot_no_bits - 64);
1756 tempval = tvb_get_guint8(tvb,offset+8);
1757 tempval = tempval >> (72-tot_no_bits);
1758 value = value | tempval;
1765 tvb_get_bits(tvbuff_t *tvb, gint bit_offset, gint no_of_bits, gboolean little_endian)
1767 /* This function can handle only up to 32 requested bits */
1768 if (no_of_bits > 32)
1769 DISSECTOR_ASSERT_NOT_REACHED();
1771 if (no_of_bits == 0)
1774 /* Number of requested bits is in range [17, 32] */
1775 if (no_of_bits > 16)
1776 return tvb_get_bits32(tvb, bit_offset, no_of_bits, little_endian);
1778 /* Number of requested bits is in range [9, 16] */
1780 return tvb_get_bits16(tvb, bit_offset, no_of_bits, little_endian);
1782 /* Number of requested bits is in range [1, 8] */
1783 return tvb_get_bits8(tvb, bit_offset, no_of_bits);
1786 /* Find first occurence of needle in tvbuff, starting at offset. Searches
1787 * at most maxlength number of bytes; if maxlength is -1, searches to
1789 * Returns the offset of the found needle, or -1 if not found.
1790 * Will not throw an exception, even if maxlength exceeds boundary of tvbuff;
1791 * in that case, -1 will be returned if the boundary is reached before
1792 * finding needle. */
1794 tvb_find_guint8(tvbuff_t *tvb, gint offset, gint maxlength, guint8 needle)
1796 const guint8 *result;
1797 guint abs_offset, junk_length;
1801 DISSECTOR_ASSERT(tvb && tvb->initialized);
1803 check_offset_length(tvb->length, tvb->reported_length, offset, 0, &abs_offset, &junk_length);
1805 /* Only search to end of tvbuff, w/o throwing exception. */
1806 tvbufflen = tvb_length_remaining(tvb, abs_offset);
1807 if (maxlength == -1) {
1808 /* No maximum length specified; search to end of tvbuff. */
1811 else if (tvbufflen < (guint) maxlength) {
1812 /* Maximum length goes past end of tvbuff; search to end
1817 /* Maximum length doesn't go past end of tvbuff; search
1822 /* If we have real data, perform our search now. */
1823 if (tvb->real_data) {
1824 result = guint8_find(tvb->real_data + abs_offset, limit, needle);
1825 if (result == NULL) {
1829 return (gint) (result - tvb->real_data);
1834 case TVBUFF_REAL_DATA:
1835 DISSECTOR_ASSERT_NOT_REACHED();
1838 return tvb_find_guint8(tvb->tvbuffs.subset.tvb,
1839 abs_offset - tvb->tvbuffs.subset.offset,
1842 case TVBUFF_COMPOSITE:
1843 DISSECTOR_ASSERT_NOT_REACHED();
1844 /* XXX - return composite_find_guint8(tvb, offset, limit, needle); */
1847 DISSECTOR_ASSERT_NOT_REACHED();
1851 /* Find first occurence of any of the needles in tvbuff, starting at offset.
1852 * Searches at most maxlength number of bytes; if maxlength is -1, searches
1854 * Returns the offset of the found needle, or -1 if not found.
1855 * Will not throw an exception, even if maxlength exceeds boundary of tvbuff;
1856 * in that case, -1 will be returned if the boundary is reached before
1857 * finding needle. */
1859 tvb_pbrk_guint8(tvbuff_t *tvb, gint offset, gint maxlength, const guint8 *needles)
1861 const guint8 *result;
1862 guint abs_offset, junk_length;
1866 DISSECTOR_ASSERT(tvb && tvb->initialized);
1868 check_offset_length(tvb->length, tvb->reported_length, offset, 0, &abs_offset, &junk_length);
1870 /* Only search to end of tvbuff, w/o throwing exception. */
1871 tvbufflen = tvb_length_remaining(tvb, abs_offset);
1872 if (maxlength == -1) {
1873 /* No maximum length specified; search to end of tvbuff. */
1876 else if (tvbufflen < (guint) maxlength) {
1877 /* Maximum length goes past end of tvbuff; search to end
1882 /* Maximum length doesn't go past end of tvbuff; search
1887 /* If we have real data, perform our search now. */
1888 if (tvb->real_data) {
1889 result = guint8_pbrk(tvb->real_data + abs_offset, limit, needles);
1890 if (result == NULL) {
1894 return (gint) (result - tvb->real_data);
1899 case TVBUFF_REAL_DATA:
1900 DISSECTOR_ASSERT_NOT_REACHED();
1903 return tvb_pbrk_guint8(tvb->tvbuffs.subset.tvb,
1904 abs_offset - tvb->tvbuffs.subset.offset,
1907 case TVBUFF_COMPOSITE:
1908 DISSECTOR_ASSERT_NOT_REACHED();
1909 /* XXX - return composite_pbrk_guint8(tvb, offset, limit, needle); */
1912 DISSECTOR_ASSERT_NOT_REACHED();
1916 /* Find size of stringz (NUL-terminated string) by looking for terminating
1917 * NUL. The size of the string includes the terminating NUL.
1919 * If the NUL isn't found, it throws the appropriate exception.
1922 tvb_strsize(tvbuff_t *tvb, gint offset)
1924 guint abs_offset, junk_length;
1927 DISSECTOR_ASSERT(tvb && tvb->initialized);
1929 check_offset_length(tvb->length, tvb->reported_length, offset, 0, &abs_offset, &junk_length);
1930 nul_offset = tvb_find_guint8(tvb, abs_offset, -1, 0);
1931 if (nul_offset == -1) {
1933 * OK, we hit the end of the tvbuff, so we should throw
1936 * Did we hit the end of the captured data, or the end
1937 * of the actual data? If there's less captured data
1938 * than actual data, we presumably hit the end of the
1939 * captured data, otherwise we hit the end of the actual
1942 if (tvb_length(tvb) < tvb_reported_length(tvb)) {
1945 THROW(ReportedBoundsError);
1948 return (nul_offset - abs_offset) + 1;
1951 /* Find length of string by looking for end of string ('\0'), up to
1952 * 'maxlength' characters'; if 'maxlength' is -1, searches to end
1954 * Returns -1 if 'maxlength' reached before finding EOS. */
1956 tvb_strnlen(tvbuff_t *tvb, gint offset, guint maxlength)
1959 guint abs_offset, junk_length;
1961 DISSECTOR_ASSERT(tvb && tvb->initialized);
1963 check_offset_length(tvb->length, tvb->reported_length, offset, 0, &abs_offset, &junk_length);
1965 result_offset = tvb_find_guint8(tvb, abs_offset, maxlength, 0);
1967 if (result_offset == -1) {
1971 return result_offset - abs_offset;
1976 * Implement strneql etc
1980 * Call strncmp after checking if enough chars left, returning 0 if
1981 * it returns 0 (meaning "equal") and -1 otherwise, otherwise return -1.
1984 tvb_strneql(tvbuff_t *tvb, gint offset, const gchar *str, gint size)
1988 ptr = ensure_contiguous_no_exception(tvb, offset, size, NULL);
1991 int cmp = strncmp((const char *)ptr, str, size);
1994 * Return 0 if equal, -1 otherwise.
1996 return (cmp == 0 ? 0 : -1);
1999 * Not enough characters in the tvbuff to match the
2007 * Call g_ascii_strncasecmp after checking if enough chars left, returning
2008 * 0 if it returns 0 (meaning "equal") and -1 otherwise, otherwise return -1.
2011 tvb_strncaseeql(tvbuff_t *tvb, gint offset, const gchar *str, gint size)
2015 ptr = ensure_contiguous_no_exception(tvb, offset, size, NULL);
2018 int cmp = g_ascii_strncasecmp((const char *)ptr, str, size);
2021 * Return 0 if equal, -1 otherwise.
2023 return (cmp == 0 ? 0 : -1);
2026 * Not enough characters in the tvbuff to match the
2034 * Call memcmp after checking if enough chars left, returning 0 if
2035 * it returns 0 (meaning "equal") and -1 otherwise, otherwise return -1.
2038 tvb_memeql(tvbuff_t *tvb, gint offset, const guint8 *str, size_t size)
2042 ptr = ensure_contiguous_no_exception(tvb, offset, (gint) size, NULL);
2045 int cmp = memcmp(ptr, str, size);
2048 * Return 0 if equal, -1 otherwise.
2050 return (cmp == 0 ? 0 : -1);
2053 * Not enough characters in the tvbuff to match the
2060 /* Convert a string from Unicode to ASCII. At the moment we fake it by
2061 * replacing all non-ASCII characters with a '.' )-: The caller must
2062 * free the result returned. The len parameter is the number of guint16's
2063 * to convert from Unicode. */
2065 tvb_fake_unicode(tvbuff_t *tvb, int offset, int len, gboolean little_endian)
2071 /* Make sure we have enough data before allocating the buffer,
2072 so we don't blow up if the length is huge. */
2073 tvb_ensure_bytes_exist(tvb, offset, 2*len);
2075 /* We know we won't throw an exception, so we don't have to worry
2076 about leaking this buffer. */
2077 buffer = g_malloc(len + 1);
2079 for (i = 0; i < len; i++) {
2080 character = little_endian ? tvb_get_letohs(tvb, offset)
2081 : tvb_get_ntohs(tvb, offset);
2082 buffer[i] = character < 256 ? character : '.';
2091 /* Convert a string from Unicode to ASCII. At the moment we fake it by
2092 * replacing all non-ASCII characters with a '.' )-: The len parameter is
2093 * the number of guint16's to convert from Unicode.
2095 * This function allocates memory from a buffer with packet lifetime.
2096 * You do not have to free this buffer, it will be automatically freed
2097 * when wireshark starts decoding the next packet.
2100 tvb_get_ephemeral_faked_unicode(tvbuff_t *tvb, int offset, int len, gboolean little_endian)
2106 /* Make sure we have enough data before allocating the buffer,
2107 so we don't blow up if the length is huge. */
2108 tvb_ensure_bytes_exist(tvb, offset, 2*len);
2110 /* We know we won't throw an exception, so we don't have to worry
2111 about leaking this buffer. */
2112 buffer = ep_alloc(len + 1);
2114 for (i = 0; i < len; i++) {
2115 character = little_endian ? tvb_get_letohs(tvb, offset)
2116 : tvb_get_ntohs(tvb, offset);
2117 buffer[i] = character < 256 ? character : '.';
2127 * Format the data in the tvb from offset for length ...
2131 tvb_format_text(tvbuff_t *tvb, gint offset, gint size)
2136 if ((ptr = ensure_contiguous(tvb, offset, size)) == NULL) {
2137 len = tvb_length_remaining(tvb, offset);
2138 ptr = ensure_contiguous(tvb, offset, len);
2141 return format_text(ptr, len);
2145 * Format the data in the tvb from offset for length ...
2149 tvb_format_text_wsp(tvbuff_t *tvb, gint offset, gint size)
2154 if ((ptr = ensure_contiguous(tvb, offset, size)) == NULL) {
2156 len = tvb_length_remaining(tvb, offset);
2157 ptr = ensure_contiguous(tvb, offset, len);
2161 return format_text_wsp(ptr, len);
2166 * Like "tvb_format_text()", but for null-padded strings; don't show
2167 * the null padding characters as "\000".
2170 tvb_format_stringzpad(tvbuff_t *tvb, gint offset, gint size)
2172 const guint8 *ptr, *p;
2176 if ((ptr = ensure_contiguous(tvb, offset, size)) == NULL) {
2178 len = tvb_length_remaining(tvb, offset);
2179 ptr = ensure_contiguous(tvb, offset, len);
2183 for (p = ptr, stringlen = 0; stringlen < len && *p != '\0'; p++, stringlen++)
2185 return format_text(ptr, stringlen);
2190 * Like "tvb_format_text_wsp()", but for null-padded strings; don't show
2191 * the null padding characters as "\000".
2194 tvb_format_stringzpad_wsp(tvbuff_t *tvb, gint offset, gint size)
2196 const guint8 *ptr, *p;
2200 if ((ptr = ensure_contiguous(tvb, offset, size)) == NULL) {
2202 len = tvb_length_remaining(tvb, offset);
2203 ptr = ensure_contiguous(tvb, offset, len);
2207 for (p = ptr, stringlen = 0; stringlen < len && *p != '\0'; p++, stringlen++)
2209 return format_text_wsp(ptr, stringlen);
2214 * Given a tvbuff, an offset, and a length, allocate a buffer big enough
2215 * to hold a non-null-terminated string of that length at that offset,
2216 * plus a trailing '\0', copy the string into it, and return a pointer
2219 * Throws an exception if the tvbuff ends before the string does.
2222 tvb_get_string(tvbuff_t *tvb, gint offset, gint length)
2225 guint8 *strbuf = NULL;
2227 tvb_ensure_bytes_exist(tvb, offset, length);
2229 ptr = ensure_contiguous(tvb, offset, length);
2230 strbuf = g_malloc(length + 1);
2232 memcpy(strbuf, ptr, length);
2234 strbuf[length] = '\0';
2238 * Given a tvbuff, an offset, and a length, allocate a buffer big enough
2239 * to hold a non-null-terminated string of that length at that offset,
2240 * plus a trailing '\0', copy the string into it, and return a pointer
2243 * Throws an exception if the tvbuff ends before the string does.
2245 * This function allocates memory from a buffer with packet lifetime.
2246 * You do not have to free this buffer, it will be automatically freed
2247 * when wireshark starts decoding the next packet.
2248 * Do not use this function if you want the allocated memory to be persistent
2249 * after the current packet has been dissected.
2252 tvb_get_ephemeral_string(tvbuff_t *tvb, gint offset, gint length)
2255 guint8 *strbuf = NULL;
2257 tvb_ensure_bytes_exist(tvb, offset, length);
2259 ptr = ensure_contiguous(tvb, offset, length);
2260 strbuf = ep_alloc(length + 1);
2262 memcpy(strbuf, ptr, length);
2264 strbuf[length] = '\0';
2269 * Given a tvbuff, an offset, and a length, allocate a buffer big enough
2270 * to hold a non-null-terminated string of that length at that offset,
2271 * plus a trailing '\0', copy the string into it, and return a pointer
2274 * Throws an exception if the tvbuff ends before the string does.
2276 * This function allocates memory from a buffer with capture session lifetime.
2277 * You do not have to free this buffer, it will be automatically freed
2278 * when wireshark starts or opens a new capture.
2281 tvb_get_seasonal_string(tvbuff_t *tvb, gint offset, gint length)
2284 guint8 *strbuf = NULL;
2286 tvb_ensure_bytes_exist(tvb, offset, length);
2288 ptr = ensure_contiguous(tvb, offset, length);
2289 strbuf = se_alloc(length + 1);
2291 memcpy(strbuf, ptr, length);
2293 strbuf[length] = '\0';
2298 * Given a tvbuff and an offset, with the offset assumed to refer to
2299 * a null-terminated string, find the length of that string (and throw
2300 * an exception if the tvbuff ends before we find the null), allocate
2301 * a buffer big enough to hold the string, copy the string into it,
2302 * and return a pointer to the string. Also return the length of the
2303 * string (including the terminating null) through a pointer.
2306 tvb_get_stringz(tvbuff_t *tvb, gint offset, gint *lengthp)
2311 size = tvb_strsize(tvb, offset);
2312 strptr = g_malloc(size);
2313 tvb_memcpy(tvb, strptr, offset, size);
2319 * Given a tvbuff and an offset, with the offset assumed to refer to
2320 * a null-terminated string, find the length of that string (and throw
2321 * an exception if the tvbuff ends before we find the null), allocate
2322 * a buffer big enough to hold the string, copy the string into it,
2323 * and return a pointer to the string. Also return the length of the
2324 * string (including the terminating null) through a pointer.
2326 * This function allocates memory from a buffer with packet lifetime.
2327 * You do not have to free this buffer, it will be automatically freed
2328 * when wireshark starts decoding the next packet.
2329 * Do not use this function if you want the allocated memory to be persistent
2330 * after the current packet has been dissected.
2333 tvb_get_ephemeral_stringz(tvbuff_t *tvb, gint offset, gint *lengthp)
2338 size = tvb_strsize(tvb, offset);
2339 strptr = ep_alloc(size);
2340 tvb_memcpy(tvb, strptr, offset, size);
2347 * Given a tvbuff and an offset, with the offset assumed to refer to
2348 * a null-terminated string, find the length of that string (and throw
2349 * an exception if the tvbuff ends before we find the null), allocate
2350 * a buffer big enough to hold the string, copy the string into it,
2351 * and return a pointer to the string. Also return the length of the
2352 * string (including the terminating null) through a pointer.
2354 * This function allocates memory from a buffer with capture session lifetime.
2355 * You do not have to free this buffer, it will be automatically freed
2356 * when wireshark starts or opens a new capture.
2359 tvb_get_seasonal_stringz(tvbuff_t *tvb, gint offset, gint *lengthp)
2364 size = tvb_strsize(tvb, offset);
2365 strptr = se_alloc(size);
2366 tvb_memcpy(tvb, strptr, offset, size);
2372 /* Looks for a stringz (NUL-terminated string) in tvbuff and copies
2373 * no more than bufsize number of bytes, including terminating NUL, to buffer.
2374 * Returns length of string (not including terminating NUL), or -1 if the string was
2375 * truncated in the buffer due to not having reached the terminating NUL.
2376 * In this way, it acts like g_snprintf().
2378 * bufsize MUST be greater than 0.
2380 * When processing a packet where the remaining number of bytes is less
2381 * than bufsize, an exception is not thrown if the end of the packet
2382 * is reached before the NUL is found. If no NUL is found before reaching
2383 * the end of the short packet, -1 is still returned, and the string
2384 * is truncated with a NUL, albeit not at buffer[bufsize - 1], but
2385 * at the correct spot, terminating the string.
2387 * *bytes_copied will contain the number of bytes actually copied,
2388 * including the terminating-NUL.
2391 _tvb_get_nstringz(tvbuff_t *tvb, gint offset, guint bufsize, guint8* buffer,
2395 guint abs_offset, junk_length;
2397 gboolean decreased_max = FALSE;
2399 check_offset_length(tvb->length, tvb->reported_length, offset, 0, &abs_offset, &junk_length);
2401 /* There must at least be room for the terminating NUL. */
2402 DISSECTOR_ASSERT(bufsize != 0);
2404 /* If there's no room for anything else, just return the NUL. */
2411 /* Only read to end of tvbuff, w/o throwing exception. */
2412 len = tvb_length_remaining(tvb, abs_offset);
2414 /* check_offset_length() won't throw an exception if we're
2415 * looking at the byte immediately after the end of the tvbuff. */
2417 THROW(ReportedBoundsError);
2420 /* This should not happen because check_offset_length() would
2421 * have already thrown an exception if 'offset' were out-of-bounds.
2423 DISSECTOR_ASSERT(len != -1);
2426 * If we've been passed a negative number, bufsize will
2429 DISSECTOR_ASSERT(bufsize <= G_MAXINT);
2431 if ((guint)len < bufsize) {
2433 decreased_max = TRUE;
2439 stringlen = tvb_strnlen(tvb, abs_offset, limit - 1);
2440 /* If NUL wasn't found, copy the data and return -1 */
2441 if (stringlen == -1) {
2442 tvb_memcpy(tvb, buffer, abs_offset, limit);
2443 if (decreased_max) {
2445 /* Add 1 for the extra NUL that we set at buffer[limit],
2446 * pretending that it was copied as part of the string. */
2447 *bytes_copied = limit + 1;
2450 *bytes_copied = limit;
2455 /* Copy the string to buffer */
2456 tvb_memcpy(tvb, buffer, abs_offset, stringlen + 1);
2457 *bytes_copied = stringlen + 1;
2461 /* Looks for a stringz (NUL-terminated string) in tvbuff and copies
2462 * no more than bufsize number of bytes, including terminating NUL, to buffer.
2463 * Returns length of string (not including terminating NUL), or -1 if the string was
2464 * truncated in the buffer due to not having reached the terminating NUL.
2465 * In this way, it acts like g_snprintf().
2467 * When processing a packet where the remaining number of bytes is less
2468 * than bufsize, an exception is not thrown if the end of the packet
2469 * is reached before the NUL is found. If no NUL is found before reaching
2470 * the end of the short packet, -1 is still returned, and the string
2471 * is truncated with a NUL, albeit not at buffer[bufsize - 1], but
2472 * at the correct spot, terminating the string.
2475 tvb_get_nstringz(tvbuff_t *tvb, gint offset, guint bufsize, guint8* buffer)
2479 DISSECTOR_ASSERT(tvb && tvb->initialized);
2481 return _tvb_get_nstringz(tvb, offset, bufsize, buffer, &bytes_copied);
2484 /* Like tvb_get_nstringz(), but never returns -1. The string is guaranteed to
2485 * have a terminating NUL. If the string was truncated when copied into buffer,
2486 * a NUL is placed at the end of buffer to terminate it.
2489 tvb_get_nstringz0(tvbuff_t *tvb, gint offset, guint bufsize, guint8* buffer)
2491 gint len, bytes_copied;
2493 DISSECTOR_ASSERT(tvb && tvb->initialized);
2495 len = _tvb_get_nstringz(tvb, offset, bufsize, buffer, &bytes_copied);
2498 buffer[bufsize - 1] = 0;
2499 return bytes_copied - 1;
2507 * Given a tvbuff, an offset into the tvbuff, and a length that starts
2508 * at that offset (which may be -1 for "all the way to the end of the
2509 * tvbuff"), find the end of the (putative) line that starts at the
2510 * specified offset in the tvbuff, going no further than the specified
2513 * Return the length of the line (not counting the line terminator at
2514 * the end), or, if we don't find a line terminator:
2516 * if "deseg" is true, return -1;
2518 * if "deseg" is false, return the amount of data remaining in
2521 * Set "*next_offset" to the offset of the character past the line
2522 * terminator, or past the end of the buffer if we don't find a line
2523 * terminator. (It's not set if we return -1.)
2526 tvb_find_line_end(tvbuff_t *tvb, gint offset, int len, gint *next_offset,
2534 len = tvb_length_remaining(tvb, offset);
2536 * XXX - what if "len" is still -1, meaning "offset is past the
2537 * end of the tvbuff"?
2539 eob_offset = offset + len;
2542 * Look either for a CR or an LF.
2544 eol_offset = tvb_pbrk_guint8(tvb, offset, len, (const guint8 *)"\r\n");
2545 if (eol_offset == -1) {
2547 * No CR or LF - line is presumably continued in next packet.
2551 * Tell our caller we saw no EOL, so they can
2552 * try to desegment and get the entire line
2558 * Pretend the line runs to the end of the tvbuff.
2560 linelen = eob_offset - offset;
2562 *next_offset = eob_offset;
2566 * Find the number of bytes between the starting offset
2569 linelen = eol_offset - offset;
2574 if (tvb_get_guint8(tvb, eol_offset) == '\r') {
2576 * Yes - is it followed by an LF?
2578 if (eol_offset + 1 >= eob_offset) {
2580 * Dunno - the next byte isn't in this
2585 * We'll return -1, although that
2586 * runs the risk that if the line
2587 * really *is* terminated with a CR,
2588 * we won't properly dissect this
2591 * It's probably more likely that
2592 * the line ends with CR-LF than
2593 * that it ends with CR by itself.
2599 * Well, we can at least look at the next
2602 if (tvb_get_guint8(tvb, eol_offset + 1) == '\n') {
2604 * It's an LF; skip over the CR.
2612 * Return the offset of the character after the last
2613 * character in the line, skipping over the last character
2614 * in the line terminator.
2617 *next_offset = eol_offset + 1;
2623 * Given a tvbuff, an offset into the tvbuff, and a length that starts
2624 * at that offset (which may be -1 for "all the way to the end of the
2625 * tvbuff"), find the end of the (putative) line that starts at the
2626 * specified offset in the tvbuff, going no further than the specified
2629 * However, treat quoted strings inside the buffer specially - don't
2630 * treat newlines in quoted strings as line terminators.
2632 * Return the length of the line (not counting the line terminator at
2633 * the end), or the amount of data remaining in the buffer if we don't
2634 * find a line terminator.
2636 * Set "*next_offset" to the offset of the character past the line
2637 * terminator, or past the end of the buffer if we don't find a line
2641 tvb_find_line_end_unquoted(tvbuff_t *tvb, gint offset, int len,
2644 gint cur_offset, char_offset;
2651 len = tvb_length_remaining(tvb, offset);
2653 * XXX - what if "len" is still -1, meaning "offset is past the
2654 * end of the tvbuff"?
2656 eob_offset = offset + len;
2658 cur_offset = offset;
2662 * Is this part of the string quoted?
2666 * Yes - look only for the terminating quote.
2668 char_offset = tvb_find_guint8(tvb, cur_offset, len,
2672 * Look either for a CR, an LF, or a '"'.
2674 char_offset = tvb_pbrk_guint8(tvb, cur_offset, len,
2675 (const guint8 *)"\r\n\"");
2677 if (char_offset == -1) {
2679 * Not found - line is presumably continued in
2681 * We pretend the line runs to the end of the tvbuff.
2683 linelen = eob_offset - offset;
2685 *next_offset = eob_offset;
2691 * We're processing a quoted string.
2692 * We only looked for ", so we know it's a ";
2693 * as we're processing a quoted string, it's a
2701 c = tvb_get_guint8(tvb, char_offset);
2704 * Un-quoted "; it begins a quoted
2710 * It's a CR or LF; we've found a line
2713 * Find the number of bytes between the
2714 * starting offset and the CR or LF.
2716 linelen = char_offset - offset;
2723 * Yes; is it followed by an LF?
2725 if (char_offset + 1 < eob_offset &&
2726 tvb_get_guint8(tvb, char_offset + 1)
2729 * Yes; skip over the CR.
2736 * Return the offset of the character after
2737 * the last character in the line, skipping
2738 * over the last character in the line
2739 * terminator, and quit.
2742 *next_offset = char_offset + 1;
2748 * Step past the character we found.
2750 cur_offset = char_offset + 1;
2751 if (cur_offset >= eob_offset) {
2753 * The character we found was the last character
2754 * in the tvbuff - line is presumably continued in
2756 * We pretend the line runs to the end of the tvbuff.
2758 linelen = eob_offset - offset;
2760 *next_offset = eob_offset;
2768 * Copied from the mgcp dissector. (This function should be moved to /epan )
2769 * tvb_skip_wsp - Returns the position in tvb of the first non-whitespace
2770 * character following offset or offset + maxlength -1 whichever
2774 * tvb - The tvbuff in which we are skipping whitespace.
2775 * offset - The offset in tvb from which we begin trying to skip whitespace.
2776 * maxlength - The maximum distance from offset that we may try to skip
2779 * Returns: The position in tvb of the first non-whitespace
2780 * character following offset or offset + maxlength -1 whichever
2783 gint tvb_skip_wsp(tvbuff_t* tvb, gint offset, gint maxlength)
2785 gint counter = offset;
2786 gint end = offset + maxlength,tvb_len;
2789 /* Get the length remaining */
2790 tvb_len = tvb_length(tvb);
2791 end = offset + maxlength;
2797 /* Skip past spaces, tabs, CRs and LFs until run out or meet something else */
2798 for (counter = offset;
2800 ((tempchar = tvb_get_guint8(tvb,counter)) == ' ' ||
2801 tempchar == '\t' || tempchar == '\r' || tempchar == '\n');
2807 gint tvb_skip_wsp_return(tvbuff_t* tvb, gint offset){
2808 gint counter = offset;
2813 for(counter = offset; counter > end &&
2814 ((tempchar = tvb_get_guint8(tvb,counter)) == ' ' ||
2815 tempchar == '\t' || tempchar == '\n' || tempchar == '\r'); counter--);
2822 * Format a bunch of data from a tvbuff as bytes, returning a pointer
2823 * to the string with the formatted data, with "punct" as a byte
2827 tvb_bytes_to_str_punct(tvbuff_t *tvb, gint offset, gint len, gchar punct)
2829 return bytes_to_str_punct(tvb_get_ptr(tvb, offset, len), len, punct);
2833 * Format a bunch of data from a tvbuff as bytes, returning a pointer
2834 * to the string with the formatted data.
2837 tvb_bytes_to_str(tvbuff_t *tvb, gint offset, gint len)
2839 return bytes_to_str(tvb_get_ptr(tvb, offset, len), len);
2842 /* Find a needle tvbuff within a haystack tvbuff. */
2844 tvb_find_tvb(tvbuff_t *haystack_tvb, tvbuff_t *needle_tvb, gint haystack_offset)
2846 guint haystack_abs_offset, haystack_abs_length;
2847 const guint8 *haystack_data;
2848 const guint8 *needle_data;
2849 const guint needle_len = needle_tvb->length;
2850 const guint8 *location;
2852 DISSECTOR_ASSERT(haystack_tvb && haystack_tvb->initialized);
2854 if (haystack_tvb->length < 1 || needle_tvb->length < 1) {
2858 /* Get pointers to the tvbuffs' data. */
2859 haystack_data = tvb_get_ptr(haystack_tvb, 0, -1);
2860 needle_data = tvb_get_ptr(needle_tvb, 0, -1);
2862 check_offset_length(haystack_tvb->length, haystack_tvb->reported_length, haystack_offset, -1,
2863 &haystack_abs_offset, &haystack_abs_length);
2865 location = epan_memmem(haystack_data + haystack_abs_offset, haystack_abs_length,
2866 needle_data, needle_len);
2869 return (gint) (location - haystack_data);
2877 * Uncompresses a zlib compressed packet inside a message of tvb at offset with
2878 * length comprlen. Returns an uncompressed tvbuffer if uncompression
2879 * succeeded or NULL if uncompression failed.
2881 #define TVB_Z_MIN_BUFSIZ 32768
2882 #define TVB_Z_MAX_BUFSIZ 1048576 * 10
2883 /* #define TVB_Z_DEBUG 1 */
2887 tvb_uncompress(tvbuff_t *tvb, int offset, int comprlen)
2890 guint bytes_out = 0;
2891 guint8 *compr = NULL;
2892 guint8 *uncompr = NULL;
2893 tvbuff_t *uncompr_tvb = NULL;
2894 z_streamp strm = NULL;
2895 Bytef *strmbuf = NULL;
2896 guint inits_done = 0;
2897 gint wbits = MAX_WBITS;
2898 guint8 *next = NULL;
2899 guint bufsiz = TVB_Z_MIN_BUFSIZ;
2901 guint inflate_passes = 0;
2902 guint bytes_in = tvb_length_remaining(tvb, offset);
2909 compr = tvb_memdup(tvb, offset, comprlen);
2915 * Assume that the uncompressed data is at least twice as big as
2916 * the compressed size.
2918 bufsiz = tvb_length_remaining(tvb, offset) * 2;
2919 bufsiz = CLAMP(bufsiz, TVB_Z_MIN_BUFSIZ, TVB_Z_MAX_BUFSIZ);
2922 printf("bufsiz: %u bytes\n", bufsiz);
2927 strm = g_new0(z_stream, 1);
2928 strm->next_in = next;
2929 strm->avail_in = comprlen;
2931 strmbuf = g_malloc0(bufsiz);
2932 strm->next_out = strmbuf;
2933 strm->avail_out = bufsiz;
2935 err = inflateInit2(strm, wbits);
2946 memset(strmbuf, '\0', bufsiz);
2947 strm->next_out = strmbuf;
2948 strm->avail_out = bufsiz;
2950 err = inflate(strm, Z_SYNC_FLUSH);
2952 if (err == Z_OK || err == Z_STREAM_END) {
2953 guint bytes_pass = bufsiz - strm->avail_out;
2959 if (uncompr == NULL) {
2960 uncompr = g_memdup(strmbuf, bytes_pass);
2962 guint8 *new_data = g_malloc0(bytes_out + bytes_pass);
2964 g_memmove(new_data, uncompr, bytes_out);
2965 g_memmove((new_data + bytes_out), strmbuf,
2972 bytes_out += bytes_pass;
2974 if ( err == Z_STREAM_END) {
2980 } else if (err == Z_BUF_ERROR) {
2982 * It's possible that not enough frames were captured
2983 * to decompress this fully, so return what we've done
2990 if (uncompr != NULL) {
2997 } else if (err == Z_DATA_ERROR && inits_done == 1
2998 && uncompr == NULL && (*compr == 0x1f) &&
2999 (*(compr + 1) == 0x8b)) {
3001 * inflate() is supposed to handle both gzip and deflate
3002 * streams automatically, but in reality it doesn't
3003 * seem to handle either (at least not within the
3004 * context of an HTTP response.) We have to try
3005 * several tweaks, depending on the type of data and
3006 * version of the library installed.
3010 * Gzip file format. Skip past the header, since the
3011 * fix to make it work (setting windowBits to 31)
3012 * doesn't work with all versions of the library.
3014 Bytef *c = compr + 2;
3017 if (*c == Z_DEFLATED) {
3029 /* Skip past the MTIME, XFL, and OS fields. */
3032 if (flags & (1 << 2)) {
3033 /* An Extra field is present. */
3034 gint xsize = (gint)(*c |
3040 if (flags & (1 << 3)) {
3041 /* A null terminated filename */
3043 while ((c - compr) < comprlen && *c != '\0') {
3050 if (flags & (1 << 4)) {
3051 /* A null terminated comment */
3053 while ((c - compr) < comprlen && *c != '\0') {
3063 strm->next_in = next;
3064 if (c - compr > comprlen) {
3071 comprlen -= (int) (c - compr);
3074 err = inflateInit2(strm, wbits);
3076 } else if (err == Z_DATA_ERROR && uncompr == NULL &&
3080 * Re-init the stream with a negative
3081 * MAX_WBITS. This is necessary due to
3082 * some servers (Apache) not sending
3083 * the deflate header with the
3084 * content-encoded response.
3090 strm->next_in = next;
3091 strm->avail_in = comprlen;
3094 memset(strmbuf, '\0', bufsiz);
3095 strm->next_out = strmbuf;
3096 strm->avail_out = bufsiz;
3098 err = inflateInit2(strm, wbits);
3116 if (uncompr == NULL) {
3125 printf("inflate() total passes: %u\n", inflate_passes);
3126 printf("bytes in: %u\nbytes out: %u\n\n", bytes_in, bytes_out);
3129 if (uncompr != NULL) {
3130 uncompr_tvb = tvb_new_real_data((guint8*) uncompr, bytes_out,
3132 tvb_set_free_cb(uncompr_tvb, g_free);
3139 tvb_uncompress(tvbuff_t *tvb _U_, int offset _U_, int comprlen _U_)
3145 tvbuff_t* tvb_child_uncompress(tvbuff_t *parent _U_, tvbuff_t *tvb, int offset, int comprlen)
3147 tvbuff_t *new_tvb = tvb_uncompress(tvb, offset, comprlen);
3149 tvb_set_child_real_data_tvbuff (parent, new_tvb);