3 * Routines to dissect WTLS component of WAP traffic.
5 * $Id: packet-wtls.c,v 1.4 2001/03/09 04:35:22 guy Exp $
7 * Ethereal - Network traffic analyzer
8 * By Gerald Combs <gerald@zing.org>
9 * Copyright 1998 Didier Jorand
11 * WAP dissector based on original work by Ben Fowler
12 * Updated by Neil Hunter <neil.hunter@energis-squared.com>
13 * WTLS support by Alexandre P. Ferreira (Splice IP)
15 * This program is free software; you can redistribute it and/or
16 * modify it under the terms of the GNU General Public License
17 * as published by the Free Software Foundation; either version 2
18 * of the License, or (at your option) any later version.
20 * This program is distributed in the hope that it will be useful,
21 * but WITHOUT ANY WARRANTY; without even the implied warranty of
22 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
23 * GNU General Public License for more details.
25 * You should have received a copy of the GNU General Public License
26 * along with this program; if not, write to the Free Software
27 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
37 #ifdef HAVE_SYS_TYPES_H
38 # include <sys/types.h>
41 #ifdef HAVE_NETINET_IN_H
42 # include <netinet/in.h>
45 #ifdef NEED_SNPRINTF_H
51 # include "snprintf.h"
57 #include "packet-wap.h"
58 #include "packet-wtls.h"
60 /* File scoped variables for the protocol and registered fields */
61 static int proto_wtls = HF_EMPTY;
63 /* These fields used by fixed part of header */
64 static int hf_wtls_record = HF_EMPTY;
65 static int hf_wtls_record_type = HF_EMPTY;
66 static int hf_wtls_record_length = HF_EMPTY;
67 static int hf_wtls_record_sequence = HF_EMPTY;
68 static int hf_wtls_record_ciphered = HF_EMPTY;
69 static int hf_wtls_hands = HF_EMPTY;
70 static int hf_wtls_hands_type = HF_EMPTY;
71 static int hf_wtls_hands_length = HF_EMPTY;
72 static int hf_wtls_hands_cli_hello = HF_EMPTY;
73 static int hf_wtls_hands_cli_hello_version = HF_EMPTY;
74 static int hf_wtls_hands_cli_hello_gmt = HF_EMPTY;
75 static int hf_wtls_hands_cli_hello_random = HF_EMPTY;
76 static int hf_wtls_hands_cli_hello_session = HF_EMPTY;
77 static int hf_wtls_hands_cli_hello_cli_key_id = HF_EMPTY;
78 static int hf_wtls_hands_cli_hello_trust_key_id = HF_EMPTY;
79 static int hf_wtls_hands_cli_hello_key_exchange =HF_EMPTY;
80 static int hf_wtls_hands_cli_hello_key_exchange_suite =HF_EMPTY;
81 static int hf_wtls_hands_cli_hello_key_parameter_index =HF_EMPTY;
82 static int hf_wtls_hands_cli_hello_key_parameter_set =HF_EMPTY;
83 static int hf_wtls_hands_cli_hello_key_identifier_type =HF_EMPTY;
84 static int hf_wtls_hands_cli_hello_cipher_suite =HF_EMPTY;
85 static int hf_wtls_hands_cli_hello_cipher_suite_item =HF_EMPTY;
86 static int hf_wtls_hands_cli_hello_cipher_bulk =HF_EMPTY;
87 static int hf_wtls_hands_cli_hello_cipher_mac =HF_EMPTY;
88 static int hf_wtls_hands_cli_hello_compression_methods =HF_EMPTY;
89 static int hf_wtls_hands_cli_hello_compression =HF_EMPTY;
90 static int hf_wtls_hands_cli_hello_sequence_mode =HF_EMPTY;
91 static int hf_wtls_hands_cli_hello_key_refresh =HF_EMPTY;
92 static int hf_wtls_hands_serv_hello = HF_EMPTY;
93 static int hf_wtls_hands_serv_hello_version = HF_EMPTY;
94 static int hf_wtls_hands_serv_hello_gmt = HF_EMPTY;
95 static int hf_wtls_hands_serv_hello_random = HF_EMPTY;
96 static int hf_wtls_hands_serv_hello_session = HF_EMPTY;
97 static int hf_wtls_hands_serv_hello_cli_key_id =HF_EMPTY;
98 static int hf_wtls_hands_serv_hello_cipher_suite_item =HF_EMPTY;
99 static int hf_wtls_hands_serv_hello_cipher_bulk =HF_EMPTY;
100 static int hf_wtls_hands_serv_hello_cipher_mac =HF_EMPTY;
101 static int hf_wtls_hands_serv_hello_compression =HF_EMPTY;
102 static int hf_wtls_hands_serv_hello_sequence_mode =HF_EMPTY;
103 static int hf_wtls_hands_serv_hello_key_refresh =HF_EMPTY;
104 static int hf_wtls_hands_certificates =HF_EMPTY;
105 static int hf_wtls_hands_certificate =HF_EMPTY;
106 static int hf_wtls_hands_certificate_type =HF_EMPTY;
107 static int hf_wtls_hands_certificate_wtls_version =HF_EMPTY;
108 static int hf_wtls_hands_certificate_wtls_signature_type =HF_EMPTY;
109 static int hf_wtls_hands_certificate_wtls_issuer_type =HF_EMPTY;
110 static int hf_wtls_hands_certificate_wtls_issuer_charset =HF_EMPTY;
111 static int hf_wtls_hands_certificate_wtls_issuer_name =HF_EMPTY;
112 static int hf_wtls_hands_certificate_wtls_valid_not_before =HF_EMPTY;
113 static int hf_wtls_hands_certificate_wtls_valid_not_after =HF_EMPTY;
114 static int hf_wtls_hands_certificate_wtls_subject_type =HF_EMPTY;
115 static int hf_wtls_hands_certificate_wtls_subject_charset =HF_EMPTY;
116 static int hf_wtls_hands_certificate_wtls_subject_name = HF_EMPTY;
117 static int hf_wtls_hands_certificate_wtls_public_key_type = HF_EMPTY;
118 static int hf_wtls_hands_certificate_wtls_key_parameter_index = HF_EMPTY;
119 static int hf_wtls_hands_certificate_wtls_key_parameter_set = HF_EMPTY;
120 static int hf_wtls_hands_certificate_wtls_rsa_exponent = HF_EMPTY;
121 static int hf_wtls_hands_certificate_wtls_rsa_modules = HF_EMPTY;
122 static int hf_wtls_hands_certificate_wtls_signature = HF_EMPTY;
123 static int hf_wtls_alert = HF_EMPTY;
124 static int hf_wtls_alert_level = HF_EMPTY;
125 static int hf_wtls_alert_description = HF_EMPTY;
127 /* Initialize the subtree pointers */
128 static gint ett_wtls = ETT_EMPTY;
129 static gint ett_wtls_rec = ETT_EMPTY;
130 static gint ett_wtls_msg_type = ETT_EMPTY;
131 static gint ett_wtls_msg_type_item = ETT_EMPTY;
132 static gint ett_wtls_msg_type_item_sub = ETT_EMPTY;
133 static gint ett_wtls_msg_type_item_sub_sub = ETT_EMPTY;
135 /* Handles for WTP and WSP dissectors */
136 static dissector_handle_t wtp_handle;
137 static dissector_handle_t wsp_handle;
139 static const value_string wtls_vals_record_type[] = {
140 { 0x01, "change_cipher_data" },
142 { 0x03, "handshake" },
143 { 0x04, "application_data" },
147 static const value_string wtls_vals_cipher_bulk[] = {
149 { 0x01, "RC5 CBC 40" },
150 { 0x02, "RC5 CBC 56" },
152 { 0x04, "DES CBC 40" },
154 { 0x06, "3DES CBC cwEDE40" },
155 { 0x07, "IDEA CBC 40" },
156 { 0x08, "IDEA CBC 56" },
157 { 0x09, "IDEA CBC" },
161 static const value_string wtls_vals_cipher_mac[] = {
166 { 0x04, "SHA XOR 40" },
173 static const value_string wtls_vals_handshake_type[] = {
174 { 0, "Hello Request" },
175 { 1, "Client Hello" },
176 { 2, "Server Hello" },
177 { 11, "Certificate" },
178 { 12, "Server Key Exchange" },
179 { 13, "Certificate Request" },
180 { 14, "Server Hello Done" },
181 { 15, "Certificate Verify" },
182 { 16, "Client Key Exchange" },
187 static const value_string wtls_vals_key_exchange_suite[] = {
189 { 1, "Shared Secret" },
190 { 2, "Diffie Hellman Anonymous" },
191 { 3, "Diffie Hellman Anonymous 512" },
192 { 4, "Diffie Hellman Anonymous 768" },
193 { 5, "RSA Anonymous" },
194 { 6, "RSA Anonymous 512" },
195 { 7, "RSA Anonymous 768" },
199 { 11, "EC Diffie Hellman Anonymous" },
200 { 12, "EC Diffie Hellman Anonymous 113" },
201 { 13, "EC Diffie Hellman Anonymous 131" },
202 { 14, "EC Diffie Hellman ECDSA" },
203 { 15, "EC Diffie Hellman Anonymous Uncomp" },
204 { 16, "EC Diffie Hellman Anonymous Uncomp 113" },
205 { 17, "EC Diffie Hellman Anonymous Uncomp 131" },
206 { 18, "EC Diffie Hellman ECDSA Uncomp" },
210 static const value_string wtls_vals_identifier_type[] = {
211 { 0, "No identifier" },
212 { 1, "Textual Name" },
213 { 2, "Binary Name" },
214 { 254, "SHA-1 Hash Publie Key" },
215 { 255, "x509 Distinguished Name" },
219 static const value_string wtls_vals_certificate_type[] = {
227 static const value_string wtls_vals_compression[] = {
232 static const value_string wtls_vals_sequence_mode[] = {
239 static const value_string wtls_vals_certificate_signature[] = {
246 static const value_string wtls_vals_public_key_type[] = {
253 static const value_string wtls_vals_alert_level[] = {
260 static const value_string wtls_vals_alert_description[] = {
261 { 0,"connection_close_notify"},
262 { 1,"session_close_notify"},
263 { 5,"no_connection"},
264 { 10,"unexpected_message"},
265 { 11,"time_required"},
266 { 20,"bad_record_mac"},
267 { 21,"decryption_failed"},
268 { 22,"record_overflow"},
269 { 30,"decompression_failure"},
270 { 40,"handshake_failure"},
271 { 42,"bad_certificate"},
272 { 43,"unsupported_certificate"},
273 { 44,"certificate_revoked"},
274 { 45,"certificate_expired"},
275 { 46,"certificate_unknown"},
276 { 47,"illegal_parameter"},
278 { 49,"access_denied"},
279 { 50,"decode_error"},
280 { 51,"decrypt_error"},
281 { 52,"unknown_key_id"},
282 { 53,"disabled_key_id"},
283 { 54,"key_exchange_disabled"},
284 { 55,"session_not_ready"},
285 { 56,"unknown_parameter_index"},
286 { 57,"duplicate_finished_received"},
287 { 60,"export_restriction"},
288 { 70,"protocol_version"},
289 { 71,"insufficient_security"},
290 { 80,"internal_error"},
291 { 90,"user_canceled"},
292 { 100,"no_renegotiation"},
296 #define WTLS_RECORD_TYPE_LENGTH 0x80
297 #define WTLS_RECORD_TYPE_SEQUENCE 0x40
298 #define WTLS_RECORD_TYPE_CIPHER_CUR 0x20
299 #define WTLS_RECORD_CONTENT_TYPE 0x0f
301 #define WTLS_ALERT 0x02
302 #define WTLS_PLAIN_HANDSHAKE 0x03
304 #define WTLS_HANDSHAKE_CLIENT_HELLO 1
305 #define WTLS_HANDSHAKE_SERVER_HELLO 2
306 #define WTLS_HANDSHAKE_CERTIFICATE 11
308 #define CERTIFICATE_WTLS 1
309 #define CERTIFICATE_X509 2
310 #define CERTIFICATE_X968 3
311 #define CERTIFICATE_URL 4
313 #define IDENTIFIER_NULL 0
314 #define IDENTIFIER_TEXT 1
315 #define IDENTIFIER_BIN 2
316 #define IDENTIFIER_SHA_1 254
317 #define IDENTIFIER_X509 255
319 #define PUBLIC_KEY_RSA 2
320 #define PUBLIC_KEY_ECDH 3
321 #define PUBLIC_KEY_ECDSA 4
323 static void dissect_wtls_handshake (proto_tree *, tvbuff_t *, guint, guint);
325 /* Code to actually dissect the packets */
327 dissect_wtls(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
329 frame_data *fdata = pinfo->fd;
335 guint offset_wtls = 0;
337 /* Set up structures we will need to add the protocol subtree and manage it */
339 proto_tree *wtls_tree;
340 proto_tree *wtls_rec_tree;
341 proto_tree *wtls_msg_type_tree;
343 if (check_col(fdata, COL_PROTOCOL))
345 switch ( pinfo->match_port )
347 case UDP_PORT_WTLS_WSP:
348 col_set_str(fdata, COL_PROTOCOL, "WTLS+WSP" );
350 case UDP_PORT_WTLS_WTP_WSP:
351 col_set_str(fdata, COL_PROTOCOL, "WTLS+WTP+WSP" );
356 /* Develop the string to put in the Info column */
357 if (check_col(fdata, COL_INFO)) {
358 col_set_str(fdata, COL_INFO, "WTLS" );
361 /* In the interest of speed, if "tree" is NULL, don't do any work not
362 necessary to generate protocol tree items. */
365 ti = proto_tree_add_item(tree, proto_wtls, tvb, offset_wtls,
366 tvb_length(tvb), bo_little_endian);
367 wtls_tree = proto_item_add_subtree(ti, ett_wtls);
369 for (offset_wtls=0; offset_wtls < (tvb_length(tvb)-1);) {
370 pdut = tvb_get_guint8 (tvb, offset_wtls);
372 offset = offset_wtls+1;
374 if (pdut & WTLS_RECORD_TYPE_SEQUENCE) {
377 if (pdut & WTLS_RECORD_TYPE_LENGTH) {
378 count = tvb_get_ntohs(tvb, offset);
380 count += offset-offset_wtls;
383 count = tvb_length (tvb)-offset_wtls;
385 ti = proto_tree_add_uint(wtls_tree, hf_wtls_record, tvb, offset_wtls,
387 wtls_rec_tree = proto_item_add_subtree(ti, ett_wtls_rec);
389 offset = offset_wtls;
391 ti = proto_tree_add_item (wtls_rec_tree, hf_wtls_record_type,
392 tvb,offset,1,bo_big_endian);
396 offset_wtls += count;
398 if (pdut & WTLS_RECORD_TYPE_SEQUENCE) {
399 ti = proto_tree_add_item (wtls_rec_tree, hf_wtls_record_sequence,
400 tvb,offset,2,bo_big_endian);
403 if (pdut & WTLS_RECORD_TYPE_LENGTH) {
404 count = tvb_get_ntohs(tvb, offset);
405 ti = proto_tree_add_item (wtls_rec_tree, hf_wtls_record_length,
406 tvb,offset,2,bo_big_endian);
410 count = tvb_length (tvb)-offset;
413 if (pdut & WTLS_RECORD_TYPE_CIPHER_CUR) {
414 ti = proto_tree_add_item (wtls_rec_tree, hf_wtls_record_ciphered,
415 tvb,offset,count,bo_big_endian);
419 switch (pdut & WTLS_RECORD_CONTENT_TYPE) {
420 case WTLS_PLAIN_HANDSHAKE :
421 dissect_wtls_handshake(wtls_rec_tree,tvb,offset,count);
424 ti = proto_tree_add_item(wtls_rec_tree, hf_wtls_alert, tvb, offset,
425 count, bo_little_endian);
426 wtls_msg_type_tree = proto_item_add_subtree(ti, ett_wtls_msg_type);
427 pdu_msg_type = tvb_get_guint8 (tvb, offset);
428 ti = proto_tree_add_item (wtls_msg_type_tree, hf_wtls_alert_level,
429 tvb,offset,1,bo_big_endian);
431 count = tvb_get_ntohs (tvb, offset);
432 ti = proto_tree_add_item (wtls_msg_type_tree, hf_wtls_alert_description,
433 tvb,offset,1,bo_big_endian);
444 dissect_wtls_handshake(proto_tree *tree, tvbuff_t *tvb, guint offset, guint count)
447 struct timeval timeValue;
451 guint public_key = 0;
456 proto_item *cli_key_item;
457 proto_tree *wtls_msg_type_tree;
458 proto_tree *wtls_msg_type_item_tree;
459 proto_tree *wtls_msg_type_item_sub_tree;
460 proto_tree *wtls_msg_type_item_sub_sub_tree;
462 pdu_msg_type = tvb_get_guint8 (tvb, offset);
463 ti = proto_tree_add_uint(tree, hf_wtls_hands, tvb, offset,count, pdu_msg_type);
464 wtls_msg_type_tree = proto_item_add_subtree(ti, ett_wtls_msg_type);
466 ti = proto_tree_add_item (wtls_msg_type_tree, hf_wtls_hands_type,
467 tvb,offset,1,bo_big_endian);
469 count = tvb_get_ntohs (tvb, offset);
470 ti = proto_tree_add_item (wtls_msg_type_tree, hf_wtls_hands_length,
471 tvb,offset,2,bo_big_endian);
473 switch(pdu_msg_type) {
474 case WTLS_HANDSHAKE_CLIENT_HELLO :
475 ti = proto_tree_add_item(wtls_msg_type_tree, hf_wtls_hands_cli_hello, tvb, offset,
476 count, bo_little_endian);
477 wtls_msg_type_item_tree = proto_item_add_subtree(ti, ett_wtls_msg_type_item);
478 ti = proto_tree_add_item (wtls_msg_type_item_tree, hf_wtls_hands_cli_hello_version,
479 tvb,offset,1,bo_big_endian);
481 timeValue.tv_sec = tvb_get_ntohl (tvb, offset);
482 timeValue.tv_usec = 0;
483 ti = proto_tree_add_time (wtls_msg_type_item_tree, hf_wtls_hands_cli_hello_gmt, tvb,
484 offset, 4, &timeValue);
486 ti = proto_tree_add_item (wtls_msg_type_item_tree, hf_wtls_hands_cli_hello_random,
487 tvb,offset,12,bo_big_endian);
489 count = tvb_get_guint8(tvb, offset);
490 ti = proto_tree_add_item (wtls_msg_type_item_tree, hf_wtls_hands_cli_hello_session,
491 tvb,offset,count+1,bo_big_endian);
493 count = tvb_get_ntohs (tvb, offset);
494 ti = proto_tree_add_item(wtls_msg_type_item_tree,
495 hf_wtls_hands_cli_hello_cli_key_id, tvb, offset,
496 count+2, bo_little_endian);
497 wtls_msg_type_item_sub_tree = proto_item_add_subtree(ti, ett_wtls_msg_type_item_sub);
499 for (;count > 0;count-=client_size) {
500 value = tvb_get_guint8 (tvb, offset);
501 cli_key_item = proto_tree_add_uint(wtls_msg_type_item_sub_tree,
502 hf_wtls_hands_cli_hello_key_exchange, tvb, offset,1,
505 wtls_msg_type_item_sub_sub_tree = proto_item_add_subtree(cli_key_item,
506 ett_wtls_msg_type_item_sub_sub);
507 ti = proto_tree_add_uint(wtls_msg_type_item_sub_sub_tree,
508 hf_wtls_hands_cli_hello_key_exchange_suite,
511 value = tvb_get_guint8 (tvb, offset);
512 ti = proto_tree_add_item(wtls_msg_type_item_sub_sub_tree,
513 hf_wtls_hands_cli_hello_key_parameter_index,
514 tvb,offset,1,bo_big_endian);
518 size = tvb_get_ntohs (tvb, offset);
519 ti = proto_tree_add_item(wtls_msg_type_item_sub_sub_tree,
520 hf_wtls_hands_cli_hello_key_parameter_set,
521 tvb,offset,size+2,bo_big_endian);
525 value = tvb_get_guint8 (tvb, offset);
526 ti = proto_tree_add_item(wtls_msg_type_item_sub_sub_tree,
527 hf_wtls_hands_cli_hello_key_identifier_type,
528 tvb,offset,1,bo_big_endian);
531 proto_item_set_len(cli_key_item, client_size);
533 count = tvb_get_ntohs (tvb, offset);
534 ti = proto_tree_add_item(wtls_msg_type_item_tree,
535 hf_wtls_hands_cli_hello_trust_key_id, tvb, offset,
536 count+2, bo_little_endian);
537 wtls_msg_type_item_sub_tree = proto_item_add_subtree(ti, ett_wtls_msg_type_item_sub);
539 for (;count > 0;count-=client_size) {
540 value = tvb_get_guint8 (tvb, offset);
541 cli_key_item = proto_tree_add_uint(wtls_msg_type_item_sub_tree,
542 hf_wtls_hands_cli_hello_key_exchange, tvb, offset,1,
545 wtls_msg_type_item_sub_sub_tree = proto_item_add_subtree(cli_key_item,
546 ett_wtls_msg_type_item_sub_sub);
547 ti = proto_tree_add_uint(wtls_msg_type_item_sub_sub_tree,
548 hf_wtls_hands_cli_hello_key_exchange_suite,
551 value = tvb_get_guint8 (tvb, offset);
552 ti = proto_tree_add_item(wtls_msg_type_item_sub_sub_tree,
553 hf_wtls_hands_cli_hello_key_parameter_index,
554 tvb,offset,1,bo_big_endian);
558 size = tvb_get_ntohs (tvb, offset);
559 ti = proto_tree_add_item(wtls_msg_type_item_sub_sub_tree,
560 hf_wtls_hands_cli_hello_key_parameter_set,
561 tvb,offset,size+2,bo_big_endian);
565 value = tvb_get_guint8 (tvb, offset);
566 ti = proto_tree_add_item(wtls_msg_type_item_sub_sub_tree,
567 hf_wtls_hands_cli_hello_key_identifier_type,
568 tvb,offset,1,bo_big_endian);
571 proto_item_set_len(cli_key_item, client_size);
573 count = tvb_get_guint8 (tvb, offset);
574 ti = proto_tree_add_item(wtls_msg_type_item_tree,
575 hf_wtls_hands_cli_hello_cipher_suite, tvb, offset,
576 count+1, bo_little_endian);
577 wtls_msg_type_item_sub_tree = proto_item_add_subtree(ti, ett_wtls_msg_type_item_sub);
579 for (;count > 0;count-=client_size) {
580 cli_key_item = proto_tree_add_item(wtls_msg_type_item_sub_tree,
581 hf_wtls_hands_cli_hello_cipher_suite_item, tvb, offset,1,
584 wtls_msg_type_item_sub_sub_tree = proto_item_add_subtree(cli_key_item,
585 ett_wtls_msg_type_item_sub_sub);
586 ti = proto_tree_add_item(wtls_msg_type_item_sub_sub_tree,
587 hf_wtls_hands_cli_hello_cipher_bulk,
588 tvb,offset,1,bo_big_endian);
590 value = tvb_get_guint8 (tvb, offset);
591 ti = proto_tree_add_item(wtls_msg_type_item_sub_sub_tree,
592 hf_wtls_hands_cli_hello_cipher_mac,
593 tvb,offset,1,bo_big_endian);
596 proto_item_set_len(cli_key_item, client_size);
598 count = tvb_get_guint8 (tvb, offset);
599 ti = proto_tree_add_item(wtls_msg_type_item_tree,
600 hf_wtls_hands_cli_hello_compression_methods, tvb, offset,
601 count+1, bo_little_endian);
602 wtls_msg_type_item_sub_tree = proto_item_add_subtree(ti, ett_wtls_msg_type_item_sub);
604 for (;count > 0;count-=client_size) {
606 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
607 hf_wtls_hands_cli_hello_compression, tvb, offset,1,
612 ti = proto_tree_add_item(wtls_msg_type_item_tree,
613 hf_wtls_hands_cli_hello_sequence_mode, tvb, offset,
614 1, bo_little_endian);
616 ti = proto_tree_add_item(wtls_msg_type_item_tree,
617 hf_wtls_hands_cli_hello_key_refresh, tvb, offset,
618 1, bo_little_endian);
620 case WTLS_HANDSHAKE_SERVER_HELLO :
621 ti = proto_tree_add_item(wtls_msg_type_tree, hf_wtls_hands_serv_hello, tvb, offset,
622 count, bo_little_endian);
623 wtls_msg_type_item_tree = proto_item_add_subtree(ti, ett_wtls_msg_type_item);
624 ti = proto_tree_add_item (wtls_msg_type_item_tree, hf_wtls_hands_serv_hello_version,
625 tvb,offset,1,bo_big_endian);
627 timeValue.tv_sec = tvb_get_ntohl (tvb, offset);
628 timeValue.tv_usec = 0;
629 ti = proto_tree_add_time (wtls_msg_type_item_tree, hf_wtls_hands_serv_hello_gmt, tvb,
630 offset, 4, &timeValue);
632 ti = proto_tree_add_item (wtls_msg_type_item_tree, hf_wtls_hands_serv_hello_random,
633 tvb,offset,12,bo_big_endian);
635 count = tvb_get_guint8(tvb, offset);
636 ti = proto_tree_add_item (wtls_msg_type_item_tree, hf_wtls_hands_serv_hello_session,
637 tvb,offset,count+1,bo_big_endian);
639 ti = proto_tree_add_item(wtls_msg_type_item_tree,
640 hf_wtls_hands_serv_hello_cli_key_id,
641 tvb,offset,1,bo_big_endian);
643 cli_key_item = proto_tree_add_item(wtls_msg_type_item_tree,
644 hf_wtls_hands_serv_hello_cipher_suite_item, tvb, offset,2,
646 wtls_msg_type_item_sub_tree = proto_item_add_subtree(cli_key_item,
647 ett_wtls_msg_type_item_sub);
648 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
649 hf_wtls_hands_serv_hello_cipher_bulk,
650 tvb,offset,1,bo_big_endian);
652 value = tvb_get_guint8 (tvb, offset);
653 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
654 hf_wtls_hands_serv_hello_cipher_mac,
655 tvb,offset,1,bo_big_endian);
657 ti = proto_tree_add_item(wtls_msg_type_item_tree,
658 hf_wtls_hands_serv_hello_compression, tvb, offset,1,
661 ti = proto_tree_add_item(wtls_msg_type_item_tree,
662 hf_wtls_hands_serv_hello_sequence_mode, tvb, offset,
663 1, bo_little_endian);
665 ti = proto_tree_add_item(wtls_msg_type_item_tree,
666 hf_wtls_hands_serv_hello_key_refresh, tvb, offset,
667 1, bo_little_endian);
670 case WTLS_HANDSHAKE_CERTIFICATE :
671 ti = proto_tree_add_item(wtls_msg_type_tree, hf_wtls_hands_certificates,
672 tvb, offset,count, bo_little_endian);
673 wtls_msg_type_item_tree = proto_item_add_subtree(ti, ett_wtls_msg_type_item);
674 count = tvb_get_ntohs (tvb, offset);
676 for (;count > 0;count-=client_size) {
677 cli_key_item = proto_tree_add_item(wtls_msg_type_item_tree,
678 hf_wtls_hands_certificate, tvb, offset,1,
681 wtls_msg_type_item_sub_tree = proto_item_add_subtree(cli_key_item,
682 ett_wtls_msg_type_item_sub);
683 proto_item_set_len(cli_key_item, client_size);
684 value = tvb_get_guint8 (tvb, offset);
685 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
686 hf_wtls_hands_certificate_type, tvb, offset,1,
691 case CERTIFICATE_WTLS:
692 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
693 hf_wtls_hands_certificate_wtls_version,
698 signature = tvb_get_guint8 (tvb, offset);
699 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
700 hf_wtls_hands_certificate_wtls_signature_type,
705 value = tvb_get_guint8 (tvb, offset);
706 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
707 hf_wtls_hands_certificate_wtls_issuer_type,
713 case IDENTIFIER_NULL :
715 case IDENTIFIER_TEXT :
716 ti = proto_tree_add_item(
717 wtls_msg_type_item_sub_tree,
718 hf_wtls_hands_certificate_wtls_issuer_charset,
723 value = tvb_get_guint8 (tvb, offset);
724 strncpy(valStr,tvb_get_ptr (tvb, offset+1, value),value);
726 ti = proto_tree_add_string(
727 wtls_msg_type_item_sub_tree,
728 hf_wtls_hands_certificate_wtls_issuer_name,
732 client_size+=1+value;
734 case IDENTIFIER_BIN :
736 case IDENTIFIER_SHA_1 :
738 case IDENTIFIER_X509 :
741 timeValue.tv_sec = tvb_get_ntohl (tvb, offset);
742 timeValue.tv_usec = 0;
743 ti = proto_tree_add_time (wtls_msg_type_item_sub_tree,
744 hf_wtls_hands_certificate_wtls_valid_not_before,
745 tvb, offset, 4, &timeValue);
748 timeValue.tv_sec = tvb_get_ntohl (tvb, offset);
749 timeValue.tv_usec = 0;
750 ti = proto_tree_add_time (wtls_msg_type_item_sub_tree,
751 hf_wtls_hands_certificate_wtls_valid_not_after,
752 tvb, offset, 4, &timeValue);
755 value = tvb_get_guint8 (tvb, offset);
756 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
757 hf_wtls_hands_certificate_wtls_subject_type,
763 case IDENTIFIER_NULL :
765 case IDENTIFIER_TEXT :
766 ti = proto_tree_add_item(
767 wtls_msg_type_item_sub_tree,
768 hf_wtls_hands_certificate_wtls_subject_charset,
773 value = tvb_get_guint8 (tvb, offset);
774 strncpy(valStr,tvb_get_ptr (tvb, offset+1, value),value);
776 ti = proto_tree_add_string(
777 wtls_msg_type_item_sub_tree,
778 hf_wtls_hands_certificate_wtls_subject_name,
782 client_size+=1+value;
784 case IDENTIFIER_BIN :
786 case IDENTIFIER_SHA_1 :
788 case IDENTIFIER_X509 :
791 public_key = tvb_get_guint8 (tvb, offset);
792 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
793 hf_wtls_hands_certificate_wtls_public_key_type,
798 value = tvb_get_guint8 (tvb, offset);
799 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
800 hf_wtls_hands_certificate_wtls_key_parameter_index,
801 tvb,offset,1,bo_big_endian);
805 size = tvb_get_ntohs (tvb, offset);
806 ti = proto_tree_add_item(wtls_msg_type_item_sub_tree,
807 hf_wtls_hands_certificate_wtls_key_parameter_set,
808 tvb,offset,size+2,bo_big_endian);
812 switch (public_key) {
813 case PUBLIC_KEY_RSA :
814 value = tvb_get_ntohs (tvb, offset);
815 ti = proto_tree_add_uint(wtls_msg_type_item_sub_tree,
816 hf_wtls_hands_certificate_wtls_rsa_exponent,
817 tvb,offset,value+2,value*8);
819 client_size+=2+value;
820 value = tvb_get_ntohs (tvb, offset);
821 ti = proto_tree_add_uint(wtls_msg_type_item_sub_tree,
822 hf_wtls_hands_certificate_wtls_rsa_modules,
823 tvb,offset,value+2,value*8);
825 client_size+=2+value;
827 case PUBLIC_KEY_ECDH :
829 case PUBLIC_KEY_ECDSA :
832 value = tvb_get_ntohs (tvb, offset);
833 ti = proto_tree_add_uint(wtls_msg_type_item_sub_tree,
834 hf_wtls_hands_certificate_wtls_signature,
835 tvb,offset,2+value,value*8);
837 client_size+=2+value;
839 case CERTIFICATE_X509:
840 case CERTIFICATE_X968:
841 value = tvb_get_ntohs (tvb, offset);
844 client_size += value;
847 case CERTIFICATE_URL:
848 value = tvb_get_guint8 (tvb, offset);
851 client_size += value;
855 proto_item_set_len(cli_key_item, client_size);
864 /* Register the protocol with Ethereal */
866 proto_register_wtls(void)
869 /* Setup list of header fields */
870 static hf_register_info hf[] = {
874 FT_UINT8, BASE_NONE, VALS ( wtls_vals_record_type ), 0x0f,
878 { &hf_wtls_record_type,
881 FT_UINT8, BASE_NONE, VALS ( wtls_vals_record_type ), 0x0f,
885 { &hf_wtls_record_length,
887 "wsp.wtls.rec_length",
888 FT_UINT16, BASE_DEC, NULL, 0x00,
892 { &hf_wtls_record_sequence,
895 FT_UINT16, BASE_DEC, NULL, 0x00,
899 { &hf_wtls_record_ciphered,
901 "wsp.wtls.rec_cipher",
902 FT_NONE, BASE_DEC, NULL, 0x00,
908 "wsp.wtls.handshake",
909 FT_UINT8, BASE_HEX, VALS ( wtls_vals_handshake_type ), 0x00,
913 { &hf_wtls_hands_type,
915 "wsp.wtls.handshake.type",
916 FT_UINT8, BASE_HEX, VALS ( wtls_vals_handshake_type ), 0x00,
920 { &hf_wtls_hands_length,
922 "wsp.wtls.handshake.length",
923 FT_UINT16, BASE_DEC, NULL, 0x00,
927 { &hf_wtls_hands_cli_hello,
929 "wsp.wtls.handshake.client_hello",
930 FT_NONE, BASE_NONE,NULL, 0x00,
934 { &hf_wtls_hands_cli_hello_version,
936 "wsp.wtls.handshake.client_hello.version",
937 FT_UINT8, BASE_DEC, NULL, 0x00,
941 { &hf_wtls_hands_cli_hello_gmt,
943 "wsp.wtls.handshake.client_hello.gmt",
944 FT_ABSOLUTE_TIME, BASE_NONE, NULL, 0x00,
948 { &hf_wtls_hands_cli_hello_random,
950 "wsp.wtls.handshake.client_hello.random",
951 FT_NONE, BASE_DEC, NULL, 0x00,
955 { &hf_wtls_hands_cli_hello_session,
957 "wsp.wtls.handshake.client_hello.sessionid",
958 FT_NONE, BASE_DEC, NULL, 0x00,
962 { &hf_wtls_hands_cli_hello_cli_key_id,
964 "wsp.wtls.handshake.client_hello.client_keys_id",
965 FT_NONE, BASE_DEC, NULL, 0x00,
969 { &hf_wtls_hands_cli_hello_trust_key_id,
971 "wsp.wtls.handshake.client_hello.trusted_keys_id",
972 FT_NONE, BASE_DEC, NULL, 0x00,
976 { &hf_wtls_hands_cli_hello_key_exchange,
978 "wsp.wtls.handshake.client_hello.key.key_exchange",
979 FT_UINT8, BASE_HEX, VALS ( wtls_vals_key_exchange_suite ), 0x00,
983 { &hf_wtls_hands_cli_hello_key_exchange_suite,
985 "wsp.wtls.handshake.client_hello.key.key_exchange.suite",
986 FT_UINT8, BASE_HEX, VALS ( wtls_vals_key_exchange_suite ), 0x00,
990 { &hf_wtls_hands_cli_hello_key_parameter_index,
992 "wsp.wtls.handshake.client_hello.parameter_index",
993 FT_UINT8, BASE_DEC, NULL, 0x00,
997 { &hf_wtls_hands_cli_hello_key_parameter_set,
999 "wsp.wtls.handshake.client_hello.parameter",
1000 FT_STRING, BASE_NONE, NULL, 0x00,
1004 { &hf_wtls_hands_cli_hello_key_identifier_type,
1005 { "Identifier Type",
1006 "wsp.wtls.handshake.client_hello.ident_type",
1007 FT_UINT8, BASE_HEX, VALS ( wtls_vals_identifier_type ), 0x00,
1011 { &hf_wtls_hands_cli_hello_cipher_suite,
1013 "wsp.wtls.handshake.client_hello.ciphers",
1014 FT_NONE, BASE_DEC, NULL, 0x00,
1018 { &hf_wtls_hands_cli_hello_cipher_suite_item,
1020 "wsp.wtls.handshake.client_hello.cipher",
1021 FT_NONE, BASE_DEC, NULL, 0x00,
1025 { &hf_wtls_hands_cli_hello_cipher_bulk,
1027 "wsp.wtls.handshake.client_hello.cipher.bulk",
1028 FT_UINT8, BASE_HEX, VALS ( wtls_vals_cipher_bulk ), 0x00,
1032 { &hf_wtls_hands_cli_hello_cipher_mac,
1034 "wsp.wtls.handshake.client_hello.cipher.mac",
1035 FT_UINT8, BASE_HEX, VALS ( wtls_vals_cipher_mac ), 0x00,
1039 { &hf_wtls_hands_cli_hello_compression_methods,
1040 { "Compression Methods",
1041 "wsp.wtls.handshake.client_hello.comp_methods",
1042 FT_NONE, BASE_DEC, NULL, 0x00,
1043 "Compression Methods"
1046 { &hf_wtls_hands_cli_hello_compression,
1048 "wsp.wtls.handshake.client_hello.compression",
1049 FT_UINT8, BASE_HEX, VALS ( wtls_vals_compression ), 0x00,
1053 { &hf_wtls_hands_cli_hello_sequence_mode,
1055 "wsp.wtls.handshake.client_hello.sequence_mode",
1056 FT_UINT8, BASE_HEX, VALS ( wtls_vals_sequence_mode ), 0x00,
1060 { &hf_wtls_hands_cli_hello_key_refresh,
1062 "wsp.wtls.handshake.client_hello.refresh",
1063 FT_UINT8, BASE_DEC,NULL, 0x00,
1067 { &hf_wtls_hands_serv_hello,
1069 "wsp.wtls.handshake.server_hello",
1070 FT_NONE, BASE_NONE,NULL, 0x00,
1074 { &hf_wtls_hands_serv_hello_version,
1076 "wsp.wtls.handshake.server_hello.version",
1077 FT_UINT8, BASE_DEC, NULL, 0x00,
1081 { &hf_wtls_hands_serv_hello_gmt,
1083 "wsp.wtls.handshake.server_hello.gmt",
1084 FT_ABSOLUTE_TIME, BASE_NONE, NULL, 0x00,
1088 { &hf_wtls_hands_serv_hello_random,
1090 "wsp.wtls.handshake.server_hello.random",
1091 FT_NONE, BASE_DEC, NULL, 0x00,
1095 { &hf_wtls_hands_serv_hello_session,
1097 "wsp.wtls.handshake.server_hello.sessionid",
1098 FT_NONE, BASE_DEC, NULL, 0x00,
1102 { &hf_wtls_hands_serv_hello_cli_key_id,
1104 "wsp.wtls.handshake.server_hello.key",
1105 FT_UINT8, BASE_HEX, NULL, 0x00,
1109 { &hf_wtls_hands_serv_hello_cipher_suite_item,
1111 "wsp.wtls.handshake.server_hello.cipher",
1112 FT_NONE, BASE_DEC, NULL, 0x00,
1116 { &hf_wtls_hands_serv_hello_cipher_bulk,
1118 "wsp.wtls.handshake.server_hello.cipher.bulk",
1119 FT_UINT8, BASE_HEX, VALS ( wtls_vals_cipher_bulk ), 0x00,
1123 { &hf_wtls_hands_serv_hello_cipher_mac,
1125 "wsp.wtls.handshake.server_hello.cipher.mac",
1126 FT_UINT8, BASE_HEX, VALS ( wtls_vals_cipher_mac ), 0x00,
1130 { &hf_wtls_hands_serv_hello_compression,
1132 "wsp.wtls.handshake.server_hello.compression",
1133 FT_UINT8, BASE_HEX, VALS ( wtls_vals_compression ), 0x00,
1137 { &hf_wtls_hands_serv_hello_sequence_mode,
1139 "wsp.wtls.handshake.server_hello.sequence_mode",
1140 FT_UINT8, BASE_HEX, VALS ( wtls_vals_sequence_mode ), 0x00,
1144 { &hf_wtls_hands_serv_hello_key_refresh,
1146 "wsp.wtls.handshake.server_hello.refresh",
1147 FT_UINT8, BASE_DEC,NULL, 0x00,
1151 { &hf_wtls_hands_certificates,
1153 "wsp.wtls.handshake.certificates",
1154 FT_NONE, BASE_DEC, NULL, 0x00,
1158 { &hf_wtls_hands_certificate,
1160 "wsp.wtls.handshake.certificate",
1161 FT_NONE, BASE_DEC, NULL, 0x00,
1165 { &hf_wtls_hands_certificate_type,
1167 "wsp.wtls.handshake.certificate.type",
1168 FT_UINT8, BASE_HEX, VALS ( wtls_vals_certificate_type ), 0x00,
1172 { &hf_wtls_hands_certificate_wtls_version,
1174 "wsp.wtls.handshake.certificate.version",
1175 FT_UINT8, BASE_HEX, NULL, 0x00,
1179 { &hf_wtls_hands_certificate_wtls_signature_type,
1181 "wsp.wtls.handshake.certificate.signature.type",
1182 FT_UINT8, BASE_HEX, VALS ( wtls_vals_certificate_signature ), 0x00,
1186 { &hf_wtls_hands_certificate_wtls_signature,
1188 "wsp.wtls.handshake.certificate.signature.signature",
1189 FT_UINT32, BASE_DEC, NULL, 0x00,
1193 { &hf_wtls_hands_certificate_wtls_issuer_type,
1195 "wsp.wtls.handshake.certificate.issuer.type",
1196 FT_UINT8, BASE_HEX, VALS ( wtls_vals_identifier_type ), 0x00,
1200 { &hf_wtls_hands_certificate_wtls_issuer_charset,
1202 "wsp.wtls.handshake.certificate.issuer.charset",
1203 FT_UINT16, BASE_HEX, VALS ( vals_character_sets ), 0x00,
1207 { &hf_wtls_hands_certificate_wtls_issuer_name,
1209 "wsp.wtls.handshake.certificate.issuer.name",
1210 FT_STRING, BASE_NONE, NULL, 0x00,
1214 { &hf_wtls_hands_certificate_wtls_valid_not_before,
1215 { "Valid not before",
1216 "wsp.wtls.handshake.certificate.before",
1217 FT_ABSOLUTE_TIME, BASE_NONE, NULL, 0x00,
1221 { &hf_wtls_hands_certificate_wtls_valid_not_after,
1222 { "Valid not after",
1223 "wsp.wtls.handshake.certificate.after",
1224 FT_ABSOLUTE_TIME, BASE_NONE, NULL, 0x00,
1228 { &hf_wtls_hands_certificate_wtls_subject_type,
1230 "wsp.wtls.handshake.certificate.subject.type",
1231 FT_UINT8, BASE_HEX, VALS ( wtls_vals_identifier_type ), 0x00,
1235 { &hf_wtls_hands_certificate_wtls_subject_charset,
1237 "wsp.wtls.handshake.certificate.subject.charset",
1238 FT_UINT16, BASE_HEX, VALS ( vals_character_sets ), 0x00,
1242 { &hf_wtls_hands_certificate_wtls_subject_name,
1244 "wsp.wtls.handshake.certificate.subject.name",
1245 FT_STRING, BASE_NONE, NULL, 0x00,
1249 { &hf_wtls_hands_certificate_wtls_public_key_type,
1250 { "Public Key Type",
1251 "wsp.wtls.handshake.certificate.public.type",
1252 FT_UINT8, BASE_HEX, VALS ( wtls_vals_public_key_type ), 0x00,
1256 { &hf_wtls_hands_certificate_wtls_key_parameter_index,
1257 { "Parameter Index",
1258 "wsp.wtls.handshake.certificate.parameter_index",
1259 FT_UINT8, BASE_DEC, NULL, 0x00,
1263 { &hf_wtls_hands_certificate_wtls_key_parameter_set,
1265 "wsp.wtls.handshake.certificate.parameter",
1266 FT_STRING, BASE_NONE, NULL, 0x00,
1270 { &hf_wtls_hands_certificate_wtls_rsa_exponent,
1271 { "RSA Exponent Size",
1272 "wsp.wtls.handshake.certificate.rsa.exponent",
1273 FT_UINT32, BASE_DEC, NULL, 0x00,
1277 { &hf_wtls_hands_certificate_wtls_rsa_modules,
1278 { "RSA Modulus Size",
1279 "wsp.wtls.handshake.certificate.rsa.modulus",
1280 FT_UINT32, BASE_DEC, NULL, 0x00,
1287 FT_NONE, BASE_HEX, NULL, 0x00,
1291 { &hf_wtls_alert_level,
1293 "wsp.wtls.alert.level",
1294 FT_UINT8, BASE_HEX, VALS ( wtls_vals_alert_level ), 0x00,
1298 { &hf_wtls_alert_description,
1300 "wsp.wtls.alert.description",
1301 FT_UINT8, BASE_HEX, VALS ( wtls_vals_alert_description ), 0x00,
1307 /* Setup protocol subtree array */
1308 static gint *ett[] = {
1312 &ett_wtls_msg_type_item,
1313 &ett_wtls_msg_type_item_sub,
1314 &ett_wtls_msg_type_item_sub_sub,
1317 /* Register the protocol name and description */
1318 proto_wtls = proto_register_protocol(
1319 "Wireless Transport Layer Security", /* protocol name for use by ethereal */
1320 "WTLS", /* short version of name */
1321 "wap-wtls" /* Abbreviated protocol name, should Match IANA
1322 < URL:http://www.isi.edu/in-notes/iana/assignments/port-numbers/ >
1326 /* Required function calls to register the header fields and subtrees used */
1327 proto_register_field_array(proto_wtls, hf, array_length(hf));
1328 proto_register_subtree_array(ett, array_length(ett));
1330 register_dissector("wtls", dissect_wtls, proto_wtls);
1334 proto_reg_handoff_wtls(void)
1337 * Get handles for the IP WTP and WSP dissectors
1339 wtp_handle = find_dissector("wtp");
1340 wsp_handle = find_dissector("wsp");
1342 dissector_add("udp.port", UDP_PORT_WTLS_WSP, dissect_wtls, proto_wtls);
1343 dissector_add("udp.port", UDP_PORT_WTLS_WTP_WSP, dissect_wtls, proto_wtls);