2 * Copyright 2004, Irene Ruengeler <i.ruengeler [AT] fh-muenster.de>
6 * Ethereal - Network traffic analyzer
7 * By Gerald Combs <gerald@ethereal.com>
8 * Copyright 1998 Gerald Combs
10 * This program is free software; you can redistribute it and/or
11 * modify it under the terms of the GNU General Public License
12 * as published by the Free Software Foundation; either version 2
13 * of the License, or (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
31 #include "simple_dialog.h" /* Both is used for error handling */
33 #include "epan/packet_info.h" /* Needed for packet_info */
34 #include <epan/tap.h> /* Needed for register_tap_listener */
36 #include "dlg_utils.h"
37 #include "compat_macros.h"
40 #include "sctp_stat.h"
42 #include "epan/address.h"
44 #define SCTP_HEARTBEAT_CHUNK_ID 4
45 #define SCTP_HEARTBEAT_ACK_CHUNK_ID 5
46 #define SCTP_ABORT_CHUNK_ID 6
47 #define SCTP_SHUTDOWN_CHUNK_ID 7
48 #define SCTP_SHUTDOWN_ACK_CHUNK_ID 8
49 #define SCTP_ERROR_CHUNK_ID 9
50 #define SCTP_COOKIE_ECHO_CHUNK_ID 10
51 #define SCTP_COOKIE_ACK_CHUNK_ID 11
52 #define SCTP_ECNE_CHUNK_ID 12
53 #define SCTP_CWR_CHUNK_ID 13
54 #define SCTP_SHUTDOWN_COMPLETE_CHUNK_ID 14
55 #define SCTP_FORWARD_TSN_CHUNK_ID 192
56 #define SCTP_ASCONF_ACK_CHUNK_ID 0x80
57 #define SCTP_PKTDROP_CHUNK_ID 0X81
58 #define SCTP_ASCONF_CHUNK_ID 0XC1
59 #define SCTP_IETF_EXT 255
61 #define SCTP_ABORT_CHUNK_T_BIT 0x01
63 #define PARAMETER_TYPE_LENGTH 2
64 #define PARAMETER_LENGTH_LENGTH 2
65 #define PARAMETER_HEADER_LENGTH (PARAMETER_TYPE_LENGTH + PARAMETER_LENGTH_LENGTH)
67 #define PARAMETER_HEADER_OFFSET 0
68 #define PARAMETER_TYPE_OFFSET PARAMETER_HEADER_OFFSET
69 #define PARAMETER_LENGTH_OFFSET (PARAMETER_TYPE_OFFSET + PARAMETER_TYPE_LENGTH)
70 #define PARAMETER_VALUE_OFFSET (PARAMETER_LENGTH_OFFSET + PARAMETER_LENGTH_LENGTH)
72 #define IPV6_ADDRESS_LENGTH 16
73 #define IPV6_ADDRESS_OFFSET PARAMETER_VALUE_OFFSET
74 #define IPV4_ADDRESS_LENGTH 4
75 #define IPV4_ADDRESS_OFFSET PARAMETER_VALUE_OFFSET
76 #define IPV4ADDRESS_PARAMETER_ID 0x0005
77 #define IPV6ADDRESS_PARAMETER_ID 0x0006
79 #define SACK_CHUNK_CUMULATIVE_TSN_ACK_LENGTH 4
80 #define SACK_CHUNK_CUMULATIVE_TSN_ACK_OFFSET (CHUNK_VALUE_OFFSET + 0)
81 #define SACK_CHUNK_ADV_REC_WINDOW_CREDIT_LENGTH 4
82 #define SACK_CHUNK_ADV_REC_WINDOW_CREDIT_OFFSET (SACK_CHUNK_CUMULATIVE_TSN_ACK_OFFSET + \
83 SACK_CHUNK_CUMULATIVE_TSN_ACK_LENGTH)
85 #define INIT_CHUNK_INITIAL_TSN_LENGTH 4
86 #define INIT_CHUNK_FIXED_PARAMTERS_LENGTH (INIT_CHUNK_INITIATE_TAG_LENGTH + \
87 INIT_CHUNK_ADV_REC_WINDOW_CREDIT_LENGTH + \
88 INIT_CHUNK_NUMBER_OF_OUTBOUND_STREAMS_LENGTH + \
89 INIT_CHUNK_NUMBER_OF_INBOUND_STREAMS_LENGTH + \
90 INIT_CHUNK_INITIAL_TSN_LENGTH)
91 #define CHUNK_HEADER_LENGTH (CHUNK_TYPE_LENGTH + \
92 CHUNK_FLAGS_LENGTH + \
94 #define INIT_CHUNK_VARIABLE_LENGTH_PARAMETER_OFFSET (INIT_CHUNK_INITIAL_TSN_OFFSET + \
95 INIT_CHUNK_INITIAL_TSN_LENGTH )
97 static const value_string chunk_type_values[] = {
98 { SCTP_DATA_CHUNK_ID, "DATA" },
99 { SCTP_INIT_CHUNK_ID, "INIT" },
100 { SCTP_INIT_ACK_CHUNK_ID, "INIT_ACK" },
101 { SCTP_SACK_CHUNK_ID, "SACK" },
102 { SCTP_HEARTBEAT_CHUNK_ID, "HEARTBEAT" },
103 { SCTP_HEARTBEAT_ACK_CHUNK_ID, "HEARTBEAT_ACK" },
104 { SCTP_ABORT_CHUNK_ID, "ABORT" },
105 { SCTP_SHUTDOWN_CHUNK_ID, "SHUTDOWN" },
106 { SCTP_SHUTDOWN_ACK_CHUNK_ID, "SHUTDOWN_ACK" },
107 { SCTP_ERROR_CHUNK_ID, "ERROR" },
108 { SCTP_COOKIE_ECHO_CHUNK_ID, "COOKIE_ECHO" },
109 { SCTP_COOKIE_ACK_CHUNK_ID, "COOKIE_ACK" },
110 { SCTP_ECNE_CHUNK_ID, "ECNE" },
111 { SCTP_CWR_CHUNK_ID, "CWR" },
112 { SCTP_SHUTDOWN_COMPLETE_CHUNK_ID, "SHUTDOWN_COMPLETE" },
113 { SCTP_FORWARD_TSN_CHUNK_ID, "FORWARD TSN" },
114 { SCTP_ASCONF_ACK_CHUNK_ID, "ASCONF_ACK" },
115 { SCTP_PKTDROP_CHUNK_ID, "PKTDROP" },
116 { SCTP_ASCONF_CHUNK_ID, "ASCONF" },
117 { SCTP_IETF_EXT, "IETF_EXTENSION" },
121 #define FORWARD_STREAM 0
122 #define BACKWARD_STREAM 1
123 #define FORWARD_ADD_FORWARD_VTAG 2
124 #define BACKWARD_ADD_FORWARD_VTAG 3
125 #define BACKWARD_ADD_BACKWARD_VTAG 4
126 #define ADDRESS_FORWARD_STREAM 5
127 #define ADDRESS_BACKWARD_STREAM 6
128 #define ADDRESS_FORWARD_ADD_FORWARD_VTAG 7
129 #define ADDRESS_BACKWARD_ADD_FORWARD_VTAG 8
130 #define ADDRESS_BACKWARD_ADD_BACKWARD_VTAG 9
131 #define ASSOC_NOT_FOUND 10
133 static sctp_allassocs_info_t sctp_tapinfo_struct = {0, NULL, FALSE, NULL};
136 void free_first(gpointer data, gpointer user_data _U_)
141 void tsn_free(gpointer data, gpointer user_data _U_)
145 tsn = (tsn_t *) data;
146 if (tsn->tsns != NULL)
148 g_list_foreach(tsn->tsns, free_first, NULL);
149 g_list_free(tsn->tsns);
157 sctp_allassocs_info_t *tapdata = arg;
159 sctp_assoc_info_t * info;
161 list = g_list_first(tapdata->assoc_info_list);
164 info = (sctp_assoc_info_t *) (list->data);
166 if (info->addr1 != NULL)
168 g_list_foreach(info->addr1, free_first, NULL);
169 g_list_free(info->addr1);
173 if (info->addr2 != NULL)
175 g_list_foreach(info->addr2,free_first, NULL);
176 g_list_free(info->addr2);
180 if (info->error_info_list != NULL)
182 g_list_foreach(info->error_info_list, free_first, NULL);
183 g_list_free(info->error_info_list);
184 info->error_info_list = NULL;
187 if (info->frame_numbers != NULL)
189 g_list_free(info->frame_numbers);
190 info->frame_numbers = NULL;
193 if (info->tsn1 != NULL)
195 g_list_foreach(info->tsn1, tsn_free, NULL);
196 g_list_free(info->tsn1);
200 if (info->tsn2 != NULL)
202 g_list_foreach(info->tsn2, tsn_free, NULL);
203 g_list_free(info->tsn2);
207 if (info->sack1 != NULL)
209 g_list_foreach(info->sack1, tsn_free, NULL);
210 g_list_free(info->sack1);
214 if (info->sack2 != NULL)
216 g_list_foreach(info->sack2, tsn_free, NULL);
217 g_list_free(info->sack2);
221 if (info->sort_tsn1 != NULL)
222 g_ptr_array_free(info->sort_tsn1, TRUE);
224 if (info->sort_tsn2 != NULL)
225 g_ptr_array_free(info->sort_tsn2, TRUE);
227 if (info->sort_sack1 != NULL)
228 g_ptr_array_free(info->sort_sack1, TRUE);
230 if (info->sort_sack2 != NULL)
231 g_ptr_array_free(info->sort_sack2, TRUE);
233 if (info->min_max != NULL)
235 g_slist_foreach(info->min_max, free_first, NULL);
236 info->min_max = NULL;
240 list = g_list_next(list);
242 g_list_free(tapdata->assoc_info_list);
243 tapdata->sum_tvbs = 0;
244 tapdata->assoc_info_list = NULL;
248 static sctp_assoc_info_t *calc_checksum(struct _sctp_info *check_data, sctp_assoc_info_t *data)
252 if (check_data->adler32_calculated)
254 data->n_adler32_calculated++;
255 if (check_data->adler32_correct)
256 data->n_adler32_correct++;
258 if (check_data->crc32c_calculated)
260 data->n_crc32c_calculated++;
261 if (check_data->crc32c_correct)
262 data->n_crc32c_correct++;
264 if (data->n_adler32_calculated > 0)
266 if ((float)(data->n_adler32_correct*1.0/data->n_adler32_calculated) > 0.5)
268 strcpy(data->checksum_type,"ADLER32");
269 data->n_checksum_errors=(data->n_adler32_calculated-data->n_adler32_correct);
274 if (data->n_crc32c_calculated>0)
276 if ((float)(data->n_crc32c_correct*1.0/data->n_crc32c_calculated) > 0.5)
278 strcpy(data->checksum_type,"CRC32C");
279 data->n_checksum_errors=data->n_crc32c_calculated-data->n_crc32c_correct;
286 strcpy(data->checksum_type,"UNKNOWN");
287 data->n_checksum_errors=0;
295 gint sctp_assoc_vtag_cmp(gconstpointer aa, gconstpointer bb)
298 const struct _sctp_assoc_info* a = aa;
299 const struct _sctp_assoc_info* b = bb;
304 if (a == NULL || b == NULL)
308 if ((a->port1 == b->port1) &&
309 (a->port2 == b->port2) &&
310 (a->verification_tag1 == b->verification_tag1) &&
311 ((a->verification_tag1 != 0 ||
312 (b->verification_tag2 != 0))))
313 return(FORWARD_STREAM);
315 if ((a->port1 == b->port2) &&
316 (a->port2 == b->port1) &&
317 (a->verification_tag1 == b->verification_tag2))
318 return(BACKWARD_STREAM);
320 if ((a->port1 == b->port2) &&
321 (a->port2 == b->port1) &&
322 (a->verification_tag2 == b->verification_tag1))
323 return(BACKWARD_STREAM);
325 /*forward stream verifivation tag can be added*/
326 if ((a->port1 == b->port1) &&
327 (a->port2 == b->port2) &&
328 (a->verification_tag1 != 0) &&
329 (b->verification_tag1 == 0) &&
330 (b->verification_tag2 !=0))
331 return (FORWARD_ADD_FORWARD_VTAG);
333 if ((a->port1 == b->port2) &&
334 (a->port2 == b->port1) &&
335 (a->verification_tag1 == b->verification_tag2) &&
336 (b->verification_tag1 == 0))
337 return (BACKWARD_ADD_FORWARD_VTAG);
339 /*backward stream verification tag can be added */
340 if ((a->port1 == b->port2) &&
341 (a->port2 == b->port1) &&
342 (a->verification_tag1 !=0) &&
343 (b->verification_tag1 != 0) &&
344 (b->verification_tag2 == 0))
345 return(BACKWARD_ADD_BACKWARD_VTAG);
347 return(ASSOC_NOT_FOUND);
351 gint sctp_assoc_address_cmp(gconstpointer aa, gconstpointer bb)
353 GList *srclist, *dstlist;
354 const struct _sctp_tmp_info* a = aa;
355 const struct _sctp_assoc_info* b = bb;
356 address *srcstore=NULL;
357 address *dststore=NULL;
360 gboolean src_v4=FALSE;
361 gboolean src_v6=FALSE;
362 gboolean dst_v4=FALSE;
363 gboolean dst_v6=FALSE;
366 src = g_malloc(sizeof(address));
367 if (a->src.type == AT_IPv4)
373 else if (a->src.type==AT_IPv6)
379 addr = g_malloc(src->len);
380 memcpy(addr, a->src.data, src->len);
383 dst = g_malloc(sizeof(address));
384 if (a->dst.type == AT_IPv4)
390 else if (a->dst.type==AT_IPv6)
396 addr = g_malloc(dst->len);
397 memcpy(addr, a->dst.data, dst->len);
400 srclist = g_list_first(b->addr1);
403 srcstore = (address *) (srclist->data);
404 if (srcstore->type==AT_IPv4 && src_v4==TRUE)
406 if (*src->data==*srcstore->data && a->port1 == b->port1)
408 dstlist = g_list_first(b->addr2);
411 dststore = (address *) (dstlist->data);
412 if ((dststore->type==AT_IPv4 && dst_v4==TRUE) ||(dststore->type==AT_IPv6 && dst_v6==TRUE) )
414 if (*dst->data==*dststore->data && a->port2 == b->port2)
416 if ((a->verification_tag1 !=0)&& (b->verification_tag1 == 0)&& (b->verification_tag2 !=0))
417 return ADDRESS_FORWARD_ADD_FORWARD_VTAG;
419 return ADDRESS_FORWARD_STREAM;
422 dstlist=g_list_next(dstlist);
425 dstlist=g_list_next(dstlist);
427 srclist=g_list_next(srclist);
430 srclist=g_list_next(srclist);
432 else if (srcstore->type==AT_IPv6 && src_v6==TRUE)
434 if (*src->data == *srcstore->data && a->port1 == b->port1)
436 dstlist = g_list_first(b->addr2);
439 dststore = (address *) (dstlist->data);
440 if ((dststore->type==AT_IPv4 && dst_v4==TRUE) || (dststore->type==AT_IPv6 && dst_v6==TRUE))
442 if (*dst->data==*dststore->data && a->port2 == b->port2)
444 if ((a->verification_tag1 !=0)&& (b->verification_tag1 == 0)&& (b->verification_tag2 !=0))
445 return ADDRESS_FORWARD_ADD_FORWARD_VTAG;
447 return ADDRESS_FORWARD_STREAM;
450 dstlist=g_list_next(dstlist);
453 dstlist=g_list_next(dstlist);
455 srclist=g_list_next(srclist);
458 srclist=g_list_next(srclist);
461 srclist=g_list_next(srclist);
467 src = g_malloc(sizeof(address));
468 if (a->dst.type == AT_IPv4)
474 else if (a->dst.type==AT_IPv6)
480 addr = g_malloc(src->len);
481 memcpy(addr, a->dst.data, src->len);
484 dst = g_malloc(sizeof(address));
485 if (a->src.type == AT_IPv4)
491 else if (a->src.type==AT_IPv6)
497 addr = g_malloc(dst->len);
498 memcpy(addr, a->src.data, dst->len);
501 srclist = g_list_first(b->addr1);
504 srcstore = (address *) (srclist->data);
505 if (srcstore->type==AT_IPv4 && src_v4==TRUE)
507 if (*src->data==*srcstore->data && a->port2 == b->port1)
509 dstlist = g_list_first(b->addr2);
512 dststore = (address *) (dstlist->data);
513 if ((dststore->type==AT_IPv4 && src_v4==TRUE) || (dststore->type==AT_IPv6 && src_v6==TRUE))
515 if (*dst->data==*dststore->data && a->port1 == b->port2)
517 if ((a->verification_tag1 ==b->verification_tag2)&& (b->verification_tag1 == 0))
518 return ADDRESS_BACKWARD_ADD_FORWARD_VTAG;
519 else if ((a->verification_tag1 !=0) && (b->verification_tag1 != 0)&& (b->verification_tag2 == 0))
520 return ADDRESS_BACKWARD_ADD_BACKWARD_VTAG;
522 return ADDRESS_BACKWARD_STREAM;
525 dstlist=g_list_next(dstlist);
528 dstlist=g_list_next(dstlist);
530 srclist=g_list_next(srclist);
533 srclist=g_list_next(srclist);
535 else if (srcstore->type==AT_IPv6 && src_v6==TRUE)
537 if (*src->data == *srcstore->data && a->port2 == b->port1)
539 dstlist = g_list_first(b->addr2);
542 dststore = (address *) (dstlist->data);
543 if ((dststore->type==AT_IPv4 && src_v4==TRUE) || (dststore->type==AT_IPv6 && src_v6==TRUE))
545 if (*dst->data==*dststore->data && a->port1 == b->port2)
547 if ((a->verification_tag1 ==b->verification_tag2)&& (b->verification_tag1 == 0))
548 return ADDRESS_BACKWARD_ADD_FORWARD_VTAG;
549 else if ((a->verification_tag1 !=0) && (b->verification_tag1 != 0)&& (b->verification_tag2 == 0))
550 return ADDRESS_BACKWARD_ADD_BACKWARD_VTAG;
552 return ADDRESS_BACKWARD_STREAM;
555 dstlist=g_list_next(dstlist);
558 dstlist=g_list_next(dstlist);
560 srclist=g_list_next(srclist);
563 srclist=g_list_next(srclist);
566 srclist=g_list_next(srclist);
572 return ASSOC_NOT_FOUND;
580 sctp_assoc_info_t * find_assoc(sctp_tmp_info_t * needle)
582 sctp_allassocs_info_t *assoc_info;
583 sctp_assoc_info_t *info = NULL;
587 assoc_info = &sctp_tapinfo_struct;
588 if ((list = g_list_first(assoc_info->assoc_info_list))!=NULL)
592 cmp=sctp_assoc_vtag_cmp(needle, (sctp_assoc_info_t*)(list->data));
593 /*if (cmp==ASSOC_NOT_FOUND)
595 cmp=sctp_assoc_address_cmp(needle, (sctp_assoc_info_t*)(list->data));
600 info = (sctp_assoc_info_t*)(list->data);
603 case BACKWARD_STREAM:
604 info = (sctp_assoc_info_t*)(list->data);
607 case FORWARD_ADD_FORWARD_VTAG:
608 info = (sctp_assoc_info_t*)(list->data);
609 info->verification_tag1=needle->verification_tag1;
612 case BACKWARD_ADD_FORWARD_VTAG:
613 info = (sctp_assoc_info_t*)(list->data);
614 info->verification_tag1=needle->verification_tag1;
617 case BACKWARD_ADD_BACKWARD_VTAG:
618 info = (sctp_assoc_info_t*)(list->data);
619 info->verification_tag2=needle->verification_tag1;
622 case ADDRESS_FORWARD_STREAM:
623 info = (sctp_assoc_info_t*)(list->data);
625 info->check_address=TRUE;
627 case ADDRESS_BACKWARD_STREAM:
628 info = (sctp_assoc_info_t*)(list->data);
630 info->check_address=TRUE;
632 case ADDRESS_FORWARD_ADD_FORWARD_VTAG:
633 info = (sctp_assoc_info_t*)(list->data);
634 info->verification_tag1=needle->verification_tag1;
636 info->check_address=TRUE;
638 case ADDRESS_BACKWARD_ADD_FORWARD_VTAG:
639 info = (sctp_assoc_info_t*)(list->data);
640 info->verification_tag1=needle->verification_tag1;
642 info->check_address=TRUE;
644 case ADDRESS_BACKWARD_ADD_BACKWARD_VTAG:
645 info = (sctp_assoc_info_t*)(list->data);
646 info->verification_tag2=needle->verification_tag1;
648 info->check_address=TRUE;
652 list = g_list_next(list);
658 sctp_assoc_info_t * add_chunk_count(address * vadd, sctp_assoc_info_t * info, guint32 direction, guint32 type)
662 sctp_addr_chunk *ch=NULL;
666 list = g_list_first(info->addr_chunk_count);
670 ch = (sctp_addr_chunk *)(list->data);
671 if (ch->direction == direction)
673 v = (address *) (ch->addr);
674 if (*(vadd->data)==*(v->data))
676 ch->addr_count[type]++;
681 list = g_list_next(list);
685 list = g_list_next(list);
687 ch = g_malloc(sizeof(sctp_addr_chunk));
688 ch->direction = direction;
689 ch->addr = g_malloc(sizeof(address));
690 ch->addr->type = vadd->type;
691 ch->addr->len = vadd->len;
692 dat = g_malloc(vadd->len);
693 memcpy(dat, vadd->data, vadd->len);
694 ch->addr->data = dat;
696 ch->addr_count[i] = 0;
697 ch->addr_count[type]++;
698 info->addr_chunk_count = g_list_append(info->addr_chunk_count, ch);
703 sctp_assoc_info_t * add_address(address * vadd, sctp_assoc_info_t *info, guint8 direction)
709 list = g_list_first(info->addr1);
711 list = g_list_first(info->addr2);
715 v = (address *) (list->data);
716 if (v->type == AT_IPv4 && vadd->type == AT_IPv4)
718 if (*vadd->data!=*v->data)
720 list = g_list_next(list);
728 else if (v->type == AT_IPv6 && vadd->type == AT_IPv6)
730 if (strcmp(ip6_to_str((const struct e_in6_addr *)(vadd->data)), ip6_to_str((const struct e_in6_addr *)v->data)))
732 list = g_list_next(list);
742 list = g_list_next(list);
747 info->addr1 = g_list_append(info->addr1, vadd);
748 else if (direction==2)
749 info->addr2 = g_list_append(info->addr2, vadd);
755 packet(void *tapdata _U_, packet_info *pinfo , epan_dissect_t *edt _U_ , const void *data)
757 struct _sctp_info *sctp_info;
758 guint32 chunk_number = 0, tsnumber;
759 sctp_tmp_info_t tmp_info;
760 sctp_assoc_info_t *info = NULL;
761 sctp_error_info_t *error = NULL;
763 guint16 type, length;
764 address *store = NULL;
767 guint8 *t_s_n = NULL;
768 gboolean sackchunk = FALSE;
769 gboolean datachunk = FALSE;
771 struct tsn_sort *tsn_s;
775 sctp_allassocs_info_t *assoc_info=NULL;
776 assoc_info = &sctp_tapinfo_struct;
778 sctp_info = (struct _sctp_info *) data;
781 type = sctp_info->ip_src.type;
785 tmp_info.src.type = AT_IPv4;
786 tmp_info.src.len = 4;
788 else if (type == AT_IPv6)
790 tmp_info.src.type = AT_IPv6;
791 tmp_info.src.len = 16;
794 addr = g_malloc(tmp_info.src.len);
795 memcpy(addr, sctp_info->ip_src.data, tmp_info.src.len);
796 tmp_info.src.data = addr;
798 type = sctp_info->ip_dst.type;
802 tmp_info.dst.type = AT_IPv4;
803 tmp_info.dst.len = 4;
805 else if (type == AT_IPv6)
807 tmp_info.dst.type = AT_IPv6;
808 tmp_info.dst.len = 16;
811 addr = g_malloc(tmp_info.dst.len);
812 memcpy(addr, sctp_info->ip_dst.data, tmp_info.dst.len);
813 tmp_info.dst.data = addr;
815 tmp_info.port1 = sctp_info->sport;
816 tmp_info.port2 = sctp_info->dport;
818 if (sctp_info->vtag_reflected)
820 tmp_info.verification_tag2 = sctp_info->verification_tag;
821 tmp_info.verification_tag1 = 0;
825 tmp_info.verification_tag1 = sctp_info->verification_tag;
826 tmp_info.verification_tag2 = 0;
830 info = find_assoc(&tmp_info);
833 tmp_info.n_tvbs = sctp_info->number_of_tvbs;
834 sctp_tapinfo_struct.sum_tvbs+=sctp_info->number_of_tvbs;
836 if (sctp_info->number_of_tvbs > 0)
838 info = g_malloc(sizeof(sctp_assoc_info_t));
839 memset(info, 0, sizeof(sctp_assoc_info_t));
840 info->src.type = tmp_info.src.type;
841 info->src.len = tmp_info.src.len;
842 addr = g_malloc(tmp_info.dst.len);
843 memcpy(addr,(tmp_info.src.data), tmp_info.src.len);
844 info->src.data = addr;
845 info->dst.type = tmp_info.dst.type;
846 info->dst.len = tmp_info.dst.len;
847 addr = g_malloc(tmp_info.dst.len);
848 memcpy(addr, (tmp_info.dst.data), tmp_info.dst.len);
849 info->dst.data = addr;
850 info->port1 = tmp_info.port1;
851 info->port2 = tmp_info.port2;
852 info->verification_tag1 = tmp_info.verification_tag1;
853 info->verification_tag2 = tmp_info.verification_tag2;
854 info->n_tvbs = tmp_info.n_tvbs;
856 info->initack = FALSE;
858 info = calc_checksum(sctp_info, info);
860 info->error_info_list = NULL;
861 info->min_secs = 0xffffffff;
862 info->min_usecs = 0xffffffff;
865 info->min_tsn2 = 0xFFFFFFFF;
866 info->min_tsn1 = 0xffffffff;
869 info->max_bytes1 = 0;
870 info->max_bytes2 = 0;
871 info->n_data_chunks = 0;
872 info->n_data_bytes = 0;
873 info->n_data_chunks_ep1 = 0;
874 info->n_data_bytes_ep1 = 0;
875 info->n_data_chunks_ep2 = 0;
876 info->n_data_bytes_ep2 = 0;
877 info->n_sack_chunks_ep1 = 0;
878 info->n_sack_chunks_ep2 = 0;
879 info->n_array_tsn1 = 0;
880 info->n_array_tsn2 = 0;
881 info->max_window1 = 0;
882 info->max_window2 = 0;
883 info->min_max = NULL;
884 info->sort_tsn1 = g_ptr_array_new();
885 info->sort_tsn2 = g_ptr_array_new();
886 info->sort_sack1 = g_ptr_array_new();
887 info->sort_sack2 = g_ptr_array_new();
888 for (i=0; i < NUM_CHUNKS; i++)
890 info->chunk_count[i] = 0;
891 info->ep1_chunk_count[i] = 0;
892 info->ep2_chunk_count[i] = 0;
894 info->addr_chunk_count = NULL;
896 if (((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_CHUNK_ID) ||
897 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_ACK_CHUNK_ID) ||
898 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_DATA_CHUNK_ID) ||
899 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_SACK_CHUNK_ID))
901 tsn = g_malloc(sizeof(tsn_t));
902 sack = g_malloc(sizeof(tsn_t));
905 sack->src.type=tsn->src.type = tmp_info.src.type;
906 sack->src.len=tsn->src.len = tmp_info.src.len;
907 addr = g_malloc(tmp_info.src.len);
908 memcpy(addr, tmp_info.src.data, tmp_info.src.len);
909 tsn->src.data = addr;
910 addr = g_malloc(tmp_info.src.len);
911 memcpy(addr, tmp_info.src.data, tmp_info.src.len);
912 sack->src.data = addr;
913 sack->dst.type = tsn->dst.type = tmp_info.dst.type;
914 sack->dst.len =tsn->dst.len = tmp_info.dst.len;
915 addr = g_malloc(tmp_info.dst.len);
916 memcpy(addr, tmp_info.dst.data, tmp_info.dst.len);
917 tsn->dst.data = addr;
918 addr = g_malloc(tmp_info.dst.len);
919 memcpy(addr, tmp_info.dst.data, tmp_info.dst.len);
920 sack->dst.data = addr;
921 sack->secs=tsn->secs = (guint32)pinfo->fd->rel_secs;
922 sack->usecs=tsn->usecs = (guint32)pinfo->fd->rel_usecs;
923 if (((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_DATA_CHUNK_ID) ||
924 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_SACK_CHUNK_ID))
926 if (tsn->secs < info->min_secs)
928 info->min_secs = tsn->secs;
929 info->min_usecs = tsn->usecs;
931 else if (tsn->secs == info->min_secs && tsn->usecs < info->min_usecs)
932 info->min_usecs = tsn->usecs;
934 if (tsn->secs > info->max_secs)
936 info->max_secs = tsn->secs;
937 info->max_usecs = tsn->usecs;
939 else if (tsn->secs == info->max_secs && tsn->usecs > info->max_usecs)
940 info->max_usecs = tsn->usecs;
943 sack->frame_number = tsn->frame_number = pinfo->fd->num;
945 if ((tvb_get_guint8(sctp_info->tvb[0],0) == SCTP_INIT_CHUNK_ID) || (tvb_get_guint8(sctp_info->tvb[0],0) == SCTP_INIT_ACK_CHUNK_ID))
947 info->min_tsn1 = tvb_get_ntohl(sctp_info->tvb[0],INIT_CHUNK_INITIAL_TSN_OFFSET);
948 info->verification_tag2 = tvb_get_ntohl(sctp_info->tvb[0], INIT_CHUNK_INITIATE_TAG_OFFSET);
949 info->instream1 = tvb_get_ntohs(sctp_info->tvb[0],INIT_CHUNK_NUMBER_OF_INBOUND_STREAMS_OFFSET);
950 info->outstream1 = tvb_get_ntohs(sctp_info->tvb[0],INIT_CHUNK_NUMBER_OF_OUTBOUND_STREAMS_OFFSET);
951 for (chunk_number = 1; chunk_number < sctp_info->number_of_tvbs; chunk_number++)
953 type = tvb_get_ntohs(sctp_info->tvb[chunk_number],0);
954 if (type == IPV4ADDRESS_PARAMETER_ID)
956 store = g_malloc(sizeof (address));
957 store->type = AT_IPv4;;
959 store->data = g_malloc(4);
960 tvb_memcpy(sctp_info->tvb[chunk_number], (guint8 *)(store->data),IPV4_ADDRESS_OFFSET, 4);
961 info = add_address(store, info, 1);
963 else if (type == IPV6ADDRESS_PARAMETER_ID)
965 store = g_malloc(sizeof (address));
966 store->type = AT_IPv6;;
968 store->data = g_malloc(16);
969 tvb_memcpy(sctp_info->tvb[chunk_number], (guint8 *)(store->data),IPV6_ADDRESS_OFFSET, IPV6_ADDRESS_LENGTH);
970 info = add_address(store, info, 1);
974 if (tvb_get_guint8(sctp_info->tvb[0],0) == SCTP_INIT_CHUNK_ID)
980 info->initack_dir = 1;
981 info->initack = TRUE;
983 info->chunk_count[tvb_get_guint8(sctp_info->tvb[0],0)]++;
984 info->ep1_chunk_count[tvb_get_guint8(sctp_info->tvb[0],0)]++;
985 info = add_chunk_count(&tmp_info.src, info, 1, tvb_get_guint8(sctp_info->tvb[0],0));
989 if (((tvb_get_guint8(sctp_info->tvb[0],0)) != SCTP_INIT_CHUNK_ID) &&
990 ((tvb_get_guint8(sctp_info->tvb[0],0)) != SCTP_INIT_ACK_CHUNK_ID) &&
991 ((tvb_get_guint8(sctp_info->tvb[0],0)) != SCTP_DATA_CHUNK_ID) &&
992 ((tvb_get_guint8(sctp_info->tvb[0],0)) != SCTP_SACK_CHUNK_ID))
994 tsn = g_malloc(sizeof(tsn_t));
995 sack = g_malloc(sizeof(tsn_t));
999 for (chunk_number = 0; chunk_number < sctp_info->number_of_tvbs; chunk_number++)
1001 if ((tvb_get_guint8(sctp_info->tvb[chunk_number],0)) < 12)
1003 info->chunk_count[tvb_get_guint8(sctp_info->tvb[0],0)]++;
1004 info->ep1_chunk_count[tvb_get_guint8(sctp_info->tvb[0],0)]++;
1005 info = add_chunk_count(&tmp_info.src, info, 1, tvb_get_guint8(sctp_info->tvb[0],0));
1009 info->chunk_count[12]++;
1010 info->ep1_chunk_count[12]++;
1011 info = add_chunk_count(&tmp_info.src, info, 1, 12);
1013 if (tvb_get_guint8(sctp_info->tvb[chunk_number],0) == SCTP_DATA_CHUNK_ID)
1015 length = tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET)-DATA_CHUNK_HEADER_LENGTH;
1016 info->n_data_chunks++;
1017 info->n_data_bytes+=length;
1018 info->outstream1 = tvb_get_ntohs((sctp_info->tvb)[chunk_number], DATA_CHUNK_STREAM_ID_OFFSET)+1;
1019 tsnumber = tvb_get_ntohl((sctp_info->tvb)[chunk_number], DATA_CHUNK_TSN_OFFSET);
1020 if (tsnumber < info->min_tsn1)
1021 info->min_tsn1 = tsnumber;
1022 if (tsnumber > info->max_tsn1)
1024 length=tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET)-DATA_CHUNK_HEADER_LENGTH;
1025 info->n_data_chunks_ep1++;
1026 info->n_data_bytes_ep1+=length;
1027 info->max_tsn1 = tsnumber;
1029 t_s_n = g_malloc(16);
1030 tvb_memcpy(sctp_info->tvb[chunk_number], (guint8 *)(t_s_n),0, 16);
1031 tsn->tsns = g_list_append(tsn->tsns, t_s_n);
1033 tsn_s = g_malloc(sizeof(struct tsn_sort));
1034 tsn_s->tsnumber = tsnumber;
1035 tsn_s->secs = tsn->secs;
1036 tsn_s->usecs = tsn->usecs;
1038 tsn_s->length = length-DATA_CHUNK_HEADER_LENGTH;
1039 g_ptr_array_add(info->sort_tsn1, tsn_s);
1040 info->n_array_tsn1++;
1042 if (tvb_get_guint8(sctp_info->tvb[chunk_number],0) == SCTP_SACK_CHUNK_ID)
1044 tsnumber = tvb_get_ntohl((sctp_info->tvb)[chunk_number], SACK_CHUNK_CUMULATIVE_TSN_ACK_OFFSET);
1045 if (tsnumber < info->min_tsn2)
1046 info->min_tsn2 = tsnumber;
1047 if (tsnumber > info->max_tsn2)
1048 info->max_tsn2 = tsnumber;
1049 info->n_sack_chunks_ep2++;
1050 length = tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET);
1051 t_s_n = g_malloc(length);
1052 tvb_memcpy(sctp_info->tvb[chunk_number], (guint8 *)(t_s_n),0, length);
1053 sack->tsns = g_list_append(sack->tsns, t_s_n);
1055 tsn_s = g_malloc(sizeof(struct tsn_sort));
1056 tsn_s->tsnumber = tsnumber;
1057 tsn_s->secs = tsn->secs;
1058 tsn_s->usecs = tsn->usecs;
1060 tsn_s->length = tvb_get_ntohl(sctp_info->tvb[chunk_number], SACK_CHUNK_ADV_REC_WINDOW_CREDIT_OFFSET);
1061 if (tsn_s->length > info->max_window1)
1062 info->max_window1 = tsn_s->length;
1063 g_ptr_array_add(info->sort_sack2, tsn_s);
1064 info->n_sack_chunks_ep2++;
1068 if (info->verification_tag1 != 0 || info->verification_tag2 != 0)
1070 store = g_malloc(sizeof (address));
1071 store->type = tmp_info.src.type;
1072 store->len = tmp_info.src.len;
1073 addr = g_malloc(tmp_info.src.len);
1074 memcpy(addr,(tmp_info.src.data),tmp_info.src.len);
1076 info = add_address(store, info, 1);
1077 store = g_malloc(sizeof (address));
1078 store->type = tmp_info.dst.type;
1079 store->len = tmp_info.dst.len;
1080 addr = g_malloc(tmp_info.dst.len);
1081 memcpy(addr,(tmp_info.dst.data),tmp_info.dst.len);
1083 info = add_address(store, info, 2);
1084 info->frame_numbers=g_list_prepend(info->frame_numbers,&(pinfo->fd->num));
1085 if (datachunk == TRUE)
1086 info->tsn1 = g_list_prepend(info->tsn1, tsn);
1087 if (sackchunk == TRUE)
1088 info->sack2 = g_list_prepend(info->sack2, sack);
1089 sctp_tapinfo_struct.assoc_info_list = g_list_append(sctp_tapinfo_struct.assoc_info_list, info);
1093 error = g_malloc(sizeof(sctp_error_info_t));
1094 error->frame_number = pinfo->fd->num;
1096 strcpy(error->chunk_info,"");
1097 if ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_CHUNK_ID)
1098 strcpy(error->chunk_info, val_to_str(tvb_get_guint8(sctp_info->tvb[0],0),chunk_type_values,"Reserved"));
1100 for (chunk_number = 0; chunk_number < sctp_info->number_of_tvbs; chunk_number++)
1101 strcat(error->chunk_info, val_to_str(tvb_get_guint8(sctp_info->tvb[chunk_number],0),chunk_type_values,"Reserved"));
1102 error->info_text = "INFOS";
1103 info->error_info_list = g_list_append(info->error_info_list, error);
1106 } /* endif (!info) */
1109 if (((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_CHUNK_ID) ||
1110 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_ACK_CHUNK_ID) ||
1111 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_DATA_CHUNK_ID) ||
1112 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_SACK_CHUNK_ID))
1115 tsn = g_malloc(sizeof(tsn_t));
1116 sack = g_malloc(sizeof(tsn_t));
1119 sack->src.type = tsn->src.type = tmp_info.src.type;
1120 sack->src.len = tsn->src.len = tmp_info.src.len;
1121 addr = g_malloc(tmp_info.src.len);
1122 memcpy(addr, tmp_info.src.data, tmp_info.src.len);
1123 tsn->src.data = addr;
1124 addr = g_malloc(tmp_info.src.len);
1125 memcpy(addr, tmp_info.src.data, tmp_info.src.len);
1126 sack->src.data = addr;
1127 sack->dst.type = tsn->dst.type = tmp_info.dst.type;
1128 sack->dst.len = tsn->dst.len = tmp_info.dst.len;
1129 addr = g_malloc(tmp_info.dst.len);
1130 memcpy(addr, tmp_info.dst.data, tmp_info.dst.len);
1131 tsn->dst.data = addr;
1132 addr = g_malloc(tmp_info.dst.len);
1133 memcpy(addr, tmp_info.dst.data, tmp_info.dst.len);
1134 sack->dst.data = addr;
1135 sack->secs=tsn->secs = (guint32)pinfo->fd->rel_secs;
1136 sack->usecs=tsn->usecs = (guint32)pinfo->fd->rel_usecs;
1137 if (((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_DATA_CHUNK_ID) ||
1138 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_SACK_CHUNK_ID))
1140 if (tsn->secs < info->min_secs)
1142 info->min_secs = tsn->secs;
1143 info->min_usecs = tsn->usecs;
1145 else if (tsn->secs == info->min_secs && tsn->usecs < info->min_usecs)
1146 info->min_usecs = tsn->usecs;
1148 if (tsn->secs > info->max_secs)
1150 info->max_secs = tsn->secs;
1151 info->max_usecs = tsn->usecs;
1153 else if (tsn->secs == info->max_secs && tsn->usecs > info->max_usecs)
1154 info->max_usecs = tsn->usecs;
1156 sack->frame_number = tsn->frame_number = pinfo->fd->num;
1158 info->frame_numbers = g_list_prepend(info->frame_numbers,&(pinfo->fd->num));
1160 store = g_malloc(sizeof (address));
1161 store->type = tmp_info.src.type;
1162 store->len = tmp_info.src.len;
1163 addr = g_malloc(tmp_info.src.len);
1164 memcpy(addr,(tmp_info.src.data),tmp_info.src.len);
1167 if (info->direction == 1)
1168 info = add_address(store, info, 1);
1169 else if (info->direction == 2)
1170 info = add_address(store, info, 2);
1172 store = g_malloc(sizeof (address));
1173 store->type = tmp_info.dst.type;
1174 store->len = tmp_info.dst.len;
1175 addr = g_malloc(tmp_info.dst.len);
1176 memcpy(addr,(tmp_info.dst.data),tmp_info.dst.len);
1179 if (info->direction == 1)
1180 info = add_address(store, info, 2);
1181 else if (info->direction == 2)
1182 info = add_address(store, info, 1);
1184 if (((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_ACK_CHUNK_ID) ||
1185 ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_CHUNK_ID))
1187 tsnumber = tvb_get_ntohl((sctp_info->tvb)[chunk_number], INIT_CHUNK_INITIAL_TSN_OFFSET);
1189 if (info->direction == 2)
1191 if (tsnumber < info->min_tsn2)
1192 info->min_tsn2 = tsnumber;
1193 if (tsnumber > info->max_tsn2)
1194 info->max_tsn2 = tsnumber;
1195 info->instream2 = tvb_get_ntohs(sctp_info->tvb[0],INIT_CHUNK_NUMBER_OF_INBOUND_STREAMS_OFFSET);
1196 info->outstream2 = tvb_get_ntohs(sctp_info->tvb[0],INIT_CHUNK_NUMBER_OF_OUTBOUND_STREAMS_OFFSET);
1197 /*info->initack_dir=2;*/
1198 info->tsn2 = g_list_prepend(info->tsn2, tsn);
1200 else if (info->direction == 1)
1202 if (tsnumber < info->min_tsn1)
1203 info->min_tsn1 = tsnumber;
1204 if (tsnumber > info->max_tsn1)
1205 info->max_tsn1 = tsnumber;
1206 info->instream1 = tvb_get_ntohs(sctp_info->tvb[0],INIT_CHUNK_NUMBER_OF_INBOUND_STREAMS_OFFSET);
1207 info->outstream1 = tvb_get_ntohs(sctp_info->tvb[0],INIT_CHUNK_NUMBER_OF_OUTBOUND_STREAMS_OFFSET);
1208 /*info->initack_dir=1;*/
1209 info->tsn1 = g_list_prepend(info->tsn1, tsn);
1211 info->chunk_count[tvb_get_guint8(sctp_info->tvb[0],0)]++;
1212 if (info->direction == 1)
1213 info->ep1_chunk_count[tvb_get_guint8(sctp_info->tvb[0],0)]++;
1215 info->ep2_chunk_count[tvb_get_guint8(sctp_info->tvb[0],0)]++;
1216 info = add_chunk_count(&tmp_info.src, info, info->direction, tvb_get_guint8(sctp_info->tvb[0],0));
1217 for (chunk_number = 1; chunk_number < sctp_info->number_of_tvbs; chunk_number++)
1219 type = tvb_get_ntohs(sctp_info->tvb[chunk_number],0);
1220 if (type == IPV4ADDRESS_PARAMETER_ID)
1222 store = g_malloc(sizeof (address));
1223 store->type = AT_IPv4;;
1225 store->data = g_malloc(4);
1226 tvb_memcpy(sctp_info->tvb[chunk_number], (guint8 *)(store->data),IPV4_ADDRESS_OFFSET, 4);
1227 info = add_address(store, info, info->direction);
1229 else if (type == IPV6ADDRESS_PARAMETER_ID)
1231 store = g_malloc(sizeof (address));
1232 store->type = AT_IPv6;;
1234 store->data = g_malloc(16);
1235 tvb_memcpy(sctp_info->tvb[chunk_number], (guint8 *)(store->data),IPV6_ADDRESS_OFFSET, IPV6_ADDRESS_LENGTH);
1236 info = add_address(store, info, info->direction);
1239 if ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_ACK_CHUNK_ID)
1241 info->initack = TRUE;
1242 info->initack_dir = info->direction;
1245 if ((tvb_get_guint8(sctp_info->tvb[0],0)) == SCTP_INIT_CHUNK_ID)
1252 if (((tvb_get_guint8(sctp_info->tvb[0],0)) != SCTP_INIT_ACK_CHUNK_ID) &&
1253 ((tvb_get_guint8(sctp_info->tvb[0],0)) != SCTP_DATA_CHUNK_ID) &&
1254 ((tvb_get_guint8(sctp_info->tvb[0],0)) != SCTP_SACK_CHUNK_ID))
1256 sack = g_malloc(sizeof(tsn_t));
1258 tsn = g_malloc(sizeof(tsn_t));
1261 for (chunk_number = 0; chunk_number < sctp_info->number_of_tvbs; chunk_number++)
1263 if ((tvb_get_guint8(sctp_info->tvb[chunk_number],0)) < 12)
1265 info->chunk_count[tvb_get_guint8(sctp_info->tvb[chunk_number],0)]++;
1266 if (info->direction == 1)
1267 info->ep1_chunk_count[tvb_get_guint8(sctp_info->tvb[chunk_number],0)]++;
1269 info->ep2_chunk_count[tvb_get_guint8(sctp_info->tvb[chunk_number],0)]++;
1270 info = add_chunk_count(&tmp_info.src, info,info->direction, tvb_get_guint8(sctp_info->tvb[chunk_number],0));
1274 info->chunk_count[12]++;
1275 if (info->direction == 1)
1276 info->ep1_chunk_count[12]++;
1278 info->ep2_chunk_count[12]++;
1279 info = add_chunk_count(&tmp_info.src, info, info->direction,12);
1281 if ((tvb_get_guint8(sctp_info->tvb[chunk_number],0)) == SCTP_DATA_CHUNK_ID)
1283 tsnumber = tvb_get_ntohl((sctp_info->tvb)[chunk_number], DATA_CHUNK_TSN_OFFSET);
1284 t_s_n = g_malloc(16);
1285 tvb_memcpy(sctp_info->tvb[chunk_number], (guint8 *)(t_s_n),0, 16);
1286 tsn->tsns = g_list_append(tsn->tsns, t_s_n);
1288 length=tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET)-DATA_CHUNK_HEADER_LENGTH;
1289 info->n_data_chunks++;
1290 info->n_data_bytes+=length;
1291 tsn_s = g_malloc(sizeof(struct tsn_sort));
1292 tsn_s->tsnumber = tsnumber;
1293 tsn_s->secs = tsn->secs;
1294 tsn_s->usecs = tsn->usecs;
1296 tsn_s->length = length;
1298 if (info->direction == 1)
1300 if(tsnumber < info->min_tsn1)
1301 info->min_tsn1 = tsnumber;
1302 if ((info->init == TRUE || (info->initack == TRUE && info->initack_dir == 1))&& tsnumber >= info->min_tsn1 && tsnumber <= info->max_tsn1)
1304 length = tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET)-DATA_CHUNK_HEADER_LENGTH;
1305 info->n_data_chunks_ep1++;
1306 info->n_data_bytes_ep1 += length;
1308 if(tsnumber > info->max_tsn1)
1310 info->max_tsn1 = tsnumber;
1311 length = tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET)-DATA_CHUNK_HEADER_LENGTH;
1312 info->n_data_chunks_ep1++;
1313 info->n_data_bytes_ep1 += length;
1315 if (info->init == FALSE)
1316 info->outstream1 = tvb_get_ntohs((sctp_info->tvb)[chunk_number], DATA_CHUNK_STREAM_ID_OFFSET)+1;
1317 if (info->initack == FALSE)
1318 info->instream2 = tvb_get_ntohs((sctp_info->tvb)[chunk_number], DATA_CHUNK_STREAM_ID_OFFSET)+1;
1320 g_ptr_array_add(info->sort_tsn1, tsn_s);
1321 info->n_array_tsn1++;
1323 else if (info->direction == 2)
1326 if(tsnumber < info->min_tsn2)
1327 info->min_tsn2 = tsnumber;
1329 if ((info->initack == TRUE && info->initack_dir == 2)&& tsnumber >= info->min_tsn2 && tsnumber <= info->max_tsn2)
1331 length = tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET)-DATA_CHUNK_HEADER_LENGTH;
1332 info->n_data_chunks_ep2++;
1333 info->n_data_bytes_ep2+=length;
1335 if(tsnumber > info->max_tsn2)
1337 info->max_tsn2 = tsnumber;
1338 length = tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET)-DATA_CHUNK_HEADER_LENGTH;
1339 info->n_data_chunks_ep2++;
1340 info->n_data_bytes_ep2+=length;
1342 if (info->init == FALSE)
1343 info->instream1 = tvb_get_ntohs((sctp_info->tvb)[chunk_number], DATA_CHUNK_STREAM_ID_OFFSET)+1;
1344 if (info->initack == FALSE)
1345 info->outstream2 = tvb_get_ntohs((sctp_info->tvb)[chunk_number], DATA_CHUNK_STREAM_ID_OFFSET)+1;
1347 g_ptr_array_add(info->sort_tsn2, tsn_s);
1348 info->n_array_tsn2++;
1351 else if (tvb_get_guint8(sctp_info->tvb[chunk_number],0) == SCTP_SACK_CHUNK_ID)
1353 tsnumber = tvb_get_ntohl((sctp_info->tvb)[chunk_number], SACK_CHUNK_CUMULATIVE_TSN_ACK_OFFSET);
1354 length = tvb_get_ntohs(sctp_info->tvb[chunk_number], CHUNK_LENGTH_OFFSET);
1355 t_s_n = g_malloc(length);
1356 tvb_memcpy(sctp_info->tvb[chunk_number], (guint8 *)(t_s_n),0, length);
1357 sack->tsns = g_list_append(sack->tsns, t_s_n);
1359 tsn_s = g_malloc(sizeof(struct tsn_sort));
1360 tsn_s->tsnumber = tsnumber;
1361 tsn_s->secs = tsn->secs;
1362 tsn_s->usecs = tsn->usecs;
1364 tsn_s->length = tvb_get_ntohl(sctp_info->tvb[chunk_number], SACK_CHUNK_ADV_REC_WINDOW_CREDIT_OFFSET);
1367 if (info->direction == 2)
1369 if(tsnumber < info->min_tsn1)
1370 info->min_tsn1 = tsnumber;
1371 if(tsnumber > info->max_tsn1)
1372 info->max_tsn1 = tsnumber;
1373 if (tsn_s->length > info->max_window1)
1374 info->max_window1 = tsn_s->length;
1375 g_ptr_array_add(info->sort_sack1, tsn_s);
1376 info->n_sack_chunks_ep1++;
1378 else if (info->direction == 1)
1381 if(tsnumber < info->min_tsn2)
1382 info->min_tsn2 = tsnumber;
1383 if(tsnumber > info->max_tsn2)
1384 info->max_tsn2 = tsnumber;
1385 if (tsn_s->length > info->max_window2)
1386 info->max_window2 = tsn_s->length;
1387 g_ptr_array_add(info->sort_sack2, tsn_s);
1388 info->n_sack_chunks_ep2++;
1395 if (datachunk == TRUE)
1397 if (info->direction == 1)
1398 info->tsn1 = g_list_prepend(info->tsn1, tsn);
1399 else if (info->direction == 2)
1400 info->tsn2 = g_list_prepend(info->tsn2, tsn);
1402 if (sackchunk == TRUE)
1404 if (info->direction == 1)
1405 info->sack2 = g_list_prepend(info->sack2, sack);
1406 else if(info->direction == 2)
1407 info->sack1 = g_list_prepend(info->sack1, sack);
1409 info->n_tvbs += sctp_info->number_of_tvbs;
1410 sctp_tapinfo_struct.sum_tvbs += sctp_info->number_of_tvbs;
1411 info = calc_checksum(sctp_info, info);
1418 /* XXX just copied from gtk/rpc_stat.c */
1419 void protect_thread_critical_region(void);
1420 void unprotect_thread_critical_region(void);
1422 /****************************************************************************/
1424 remove_tap_listener_sctp_stat(void)
1426 if (sctp_tapinfo_struct.is_registered) {
1427 protect_thread_critical_region();
1428 remove_tap_listener(&sctp_tapinfo_struct);
1429 unprotect_thread_critical_region();
1430 sctp_tapinfo_struct.is_registered = FALSE;
1435 void sctp_stat_scan(void)
1437 if (!sctp_tapinfo_struct.is_registered)
1438 register_tap_listener_sctp_stat();
1441 const sctp_allassocs_info_t* sctp_stat_get_info(void)
1443 return &sctp_tapinfo_struct;
1448 gtk_sctpstat_init(char *dummy _U_)
1453 static void sctp_update(void *dummy _U_)
1455 if (get_stat_dlg()!=NULL)
1456 sctp_stat_dlg_update();
1460 register_tap_listener_sctp_stat(void)
1462 GString *error_string;
1464 if (!sctp_tapinfo_struct.is_registered)
1466 register_tap_listener_cmd_arg("sctp",gtk_sctpstat_init);
1467 if ((error_string = register_tap_listener("sctp", &sctp_tapinfo_struct, NULL, reset, packet, sctp_update))) {
1468 simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, error_string->str);
1469 g_string_free(error_string, TRUE);
1472 sctp_tapinfo_struct.is_registered=TRUE;