Use "proto_tree_add_item()" to add the URI string to the protocol tree,
[obnox/wireshark/wip.git] / packet-ddtp.c
1 /* packet-ddtp.c
2  * Routines for DDTP (Dynamic DNS Tools Protocol) packet disassembly
3  * see http://ddt.sourceforge.net/
4  * Olivier Abad <oabad@cybercable.fr>
5  *
6  * $Id: packet-ddtp.c,v 1.20 2002/01/24 09:20:47 guy Exp $
7  *
8  * Ethereal - Network traffic analyzer
9  * By Gerald Combs <gerald@ethereal.com>
10  * Copyright 2000
11  * 
12  * This program is free software; you can redistribute it and/or
13  * modify it under the terms of the GNU General Public License
14  * as published by the Free Software Foundation; either version 2
15  * of the License, or (at your option) any later version.
16  * 
17  * This program is distributed in the hope that it will be useful,
18  * but WITHOUT ANY WARRANTY; without even the implied warranty of
19  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
20  * GNU General Public License for more details.
21  * 
22  * You should have received a copy of the GNU General Public License
23  * along with this program; if not, write to the Free Software
24  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
25  *
26  */
27
28 #ifdef HAVE_CONFIG_H
29 #include "config.h"
30 #endif
31
32 #ifdef HAVE_SYS_TYPES_H
33 #include <sys/types.h>
34 #endif
35
36 /*#include <string.h>
37 #include <ctype.h>
38 #include <time.h>*/
39
40 #include <glib.h>
41 #ifdef HAVE_NETINET_IN_H
42 # include <netinet/in.h>
43 #endif
44 #include <epan/packet.h>
45 #include "packet-ddtp.h"
46
47 static int proto_ddtp = -1;
48 static int hf_ddtp_version = -1;
49 static int hf_ddtp_encrypt = -1;
50 static int hf_ddtp_hostid = -1;
51 static int hf_ddtp_msgtype = -1;
52 static int hf_ddtp_opcode = -1;
53 static int hf_ddtp_ipaddr = -1;
54 static int hf_ddtp_status = -1;
55
56 static int ett_ddtp = -1;
57
58 #define UDP_PORT_DDTP   1052
59
60 static const value_string vals_ddtp_version[] = {
61     { DDTP_VERSION_ERROR, "Protocol Error" },
62     { DDTP_VERSION_4,     "4" },
63     { DDTP_VERSION_5,     "5" },
64     { 0, NULL}
65 };
66
67 static const value_string vals_ddtp_encrypt[] = {
68     { DDTP_ENCRYPT_ERROR,     "Encryption Error" },
69     { DDTP_ENCRYPT_PLAINTEXT, "Plain text" },
70     { DDTP_ENCRYPT_BLOWFISH,  "Blowfish" },
71     { 0, NULL}
72 };
73
74 static const value_string vals_ddtp_msgtype[] = {
75     { DDTP_MESSAGE_ERROR, "Message Error" },
76     { DDTP_UPDATE_QUERY,  "Update Query" },
77     { DDTP_UPDATE_REPLY,  "Update Reply" },
78     { DDTP_ALIVE_QUERY,   "Alive Query" },
79     { DDTP_ALIVE_REPLY,   "Alive Reply" },
80     { 0, NULL}
81 };
82
83 static const value_string vals_ddtp_opcode[] = {
84     { DDTP_MARK_ONLINE,  "Mark online" },
85     { DDTP_MARK_OFFLINE, "Mark offline" },
86     { 0, NULL}
87 };
88
89 static const value_string vals_ddtp_status[] = {
90     { DDTP_UPDATE_SUCCEEDED, "Update succeeded" },
91     { DDTP_UPDATE_FAILED,    "Update failed" },
92     { DDTP_INVALID_PASSWORD, "Invalid password" },
93     { DDTP_INVALID_ACCOUNT,  "Invalid account" },
94     { DDTP_INVALID_OPCODE,   "Invalid opcode" },
95     { 0, NULL}
96 };
97
98 static void
99 dissect_ddtp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
100 {
101     proto_tree *ddtp_tree = NULL;
102     proto_item *ti;
103
104     if (check_col(pinfo->cinfo, COL_PROTOCOL)) {
105         /* Indicate what kind of message this is. */
106         col_set_str (pinfo->cinfo, COL_PROTOCOL, "DDTP");
107     }
108     if (check_col(pinfo->cinfo, COL_INFO)) {
109         /* In case we throw an exception below. */
110         col_clear (pinfo->cinfo, COL_INFO);
111     }
112     if (tree) {
113         ti = proto_tree_add_item(tree, proto_ddtp, tvb, 0, -1, FALSE);
114         ddtp_tree = proto_item_add_subtree(ti, ett_ddtp);
115
116         proto_tree_add_item(ddtp_tree, hf_ddtp_version, tvb, 0, 4, FALSE);
117         proto_tree_add_item(ddtp_tree, hf_ddtp_encrypt, tvb, 4, 4, FALSE);
118         proto_tree_add_item(ddtp_tree, hf_ddtp_hostid, tvb, 8, 4, FALSE);
119     }
120     if (tvb_get_ntohl(tvb, 4) == DDTP_ENCRYPT_PLAINTEXT) {
121         if (tree)
122             proto_tree_add_item(ddtp_tree, hf_ddtp_msgtype, tvb, 12, 4, FALSE);
123         switch (tvb_get_ntohl(tvb, 12)) {
124         case DDTP_MESSAGE_ERROR :
125             if (check_col(pinfo->cinfo, COL_INFO))
126                 col_set_str (pinfo->cinfo, COL_INFO, "Message Error");
127             break;
128         case DDTP_UPDATE_QUERY :
129             if (check_col(pinfo->cinfo, COL_INFO))
130                 col_set_str (pinfo->cinfo, COL_INFO, "Update Query");
131             if (tree) {
132                 proto_tree_add_item(ddtp_tree, hf_ddtp_opcode, tvb, 16, 4,
133                         FALSE);
134                 proto_tree_add_item(ddtp_tree, hf_ddtp_ipaddr, tvb, 20, 4,
135                         FALSE);
136             }
137             break;
138         case DDTP_UPDATE_REPLY :
139             if (check_col(pinfo->cinfo, COL_INFO))
140                 col_set_str (pinfo->cinfo, COL_INFO, "Update Reply");
141             if (tree) {
142                 proto_tree_add_item(ddtp_tree, hf_ddtp_status, tvb, 16, 4,
143                         FALSE);
144             }
145             break;
146         case DDTP_ALIVE_QUERY :
147             if (check_col(pinfo->cinfo, COL_INFO))
148                 col_set_str (pinfo->cinfo, COL_INFO, "Alive Query");
149             if (tree) {
150                 proto_tree_add_text(ddtp_tree, tvb, 16, 4, "Dummy : %u",
151                         tvb_get_ntohl(tvb, 16));
152             }
153             break;
154         case DDTP_ALIVE_REPLY :
155             if (check_col(pinfo->cinfo, COL_INFO))
156                 col_set_str (pinfo->cinfo, COL_INFO, "Alive Reply");
157             if (tree) {
158                 proto_tree_add_text(ddtp_tree, tvb, 16, 4, "Dummy : %u",
159                         tvb_get_ntohl(tvb, 16));
160             }
161             break;
162         default :
163             if (check_col(pinfo->cinfo, COL_INFO))
164                 col_set_str (pinfo->cinfo, COL_INFO, "Unknown type");
165             if (tree) {
166                 proto_tree_add_text(ddtp_tree, tvb, 12, 4, "Unknown type : %u",
167                         tvb_get_ntohl(tvb, 12));
168             }
169         }
170     } else {
171         if (check_col(pinfo->cinfo, COL_INFO))
172             col_set_str (pinfo->cinfo, COL_INFO, "Encrypted payload");
173     }
174 }
175
176 void
177 proto_register_ddtp(void)
178 {
179     static hf_register_info hf_ddtp[] = {
180         { &hf_ddtp_version,
181             { "Version", "ddtp.version", FT_UINT32, BASE_DEC, VALS(vals_ddtp_version), 0x0,
182                 "Version", HFILL }},
183         { &hf_ddtp_encrypt,
184             { "Encryption", "ddtp.encrypt", FT_UINT32, BASE_DEC, VALS(vals_ddtp_encrypt), 0x0,
185                 "Encryption type", HFILL }},
186         { &hf_ddtp_hostid,
187             { "Hostid", "ddtp.hostid", FT_UINT32, BASE_DEC, NULL, 0x0,
188                 "Host ID", HFILL }},
189         { &hf_ddtp_msgtype,
190             { "Message type", "ddtp.msgtype", FT_UINT32, BASE_DEC, VALS(vals_ddtp_msgtype), 0x0,
191                 "Message Type", HFILL }},
192         { &hf_ddtp_opcode,
193             { "Opcode", "ddtp.opcode", FT_UINT32, BASE_DEC, VALS(vals_ddtp_opcode), 0x0,
194                 "Update query opcode", HFILL }},
195         { &hf_ddtp_ipaddr,
196             { "IP address", "ddtp.ipaddr", FT_IPv4, BASE_NONE, NULL, 0x0,
197                 "IP address", HFILL }},
198         { &hf_ddtp_status,
199             { "Status", "ddtp.status", FT_UINT32, BASE_DEC, VALS(vals_ddtp_status), 0x0,
200                 "Update reply status", HFILL }}
201     };
202
203     static gint *ett[] = { &ett_ddtp };
204
205     proto_ddtp = proto_register_protocol("Dynamic DNS Tools Protocol",
206                                          "DDTP", "ddtp");
207     proto_register_field_array(proto_ddtp, hf_ddtp, array_length(hf_ddtp));
208     proto_register_subtree_array(ett, array_length(ett));
209 }
210
211 void
212 proto_reg_handoff_ddtp(void)
213 {
214     dissector_handle_t ddtp_handle;
215
216     ddtp_handle = create_dissector_handle(dissect_ddtp, proto_ddtp);
217     dissector_add("udp.port", UDP_PORT_DDTP, ddtp_handle);
218 }