/src/wireshark/epan/dissectors/packet-rtse.c
Line | Count | Source |
1 | | /* Do not modify this file. Changes will be overwritten. */ |
2 | | /* Generated automatically by the ASN.1 to Wireshark dissector compiler */ |
3 | | /* packet-rtse.c */ |
4 | | /* asn2wrs.py -b -q -L -p rtse -c ./rtse.cnf -s ./packet-rtse-template -D . -O ../.. rtse.asn */ |
5 | | |
6 | | /* packet-rtse-template.c |
7 | | * Routines for RTSE packet dissection |
8 | | * Graeme Lunt 2005 |
9 | | * |
10 | | * Wireshark - Network traffic analyzer |
11 | | * By Gerald Combs <gerald@wireshark.org> |
12 | | * Copyright 1998 Gerald Combs |
13 | | * |
14 | | * SPDX-License-Identifier: GPL-2.0-or-later |
15 | | */ |
16 | | |
17 | | #include "config.h" |
18 | | |
19 | | #include <epan/packet.h> |
20 | | #include <epan/conversation.h> |
21 | | #include <epan/prefs.h> |
22 | | #include <epan/reassemble.h> |
23 | | #include <epan/asn1.h> |
24 | | #include <epan/expert.h> |
25 | | |
26 | | #include <wsutil/array.h> |
27 | | #include <wsutil/str_util.h> |
28 | | |
29 | | #include "packet-ber.h" |
30 | | #include "packet-pres.h" |
31 | | #include "packet-acse.h" |
32 | | #include "packet-ros.h" |
33 | | #include "packet-rtse.h" |
34 | | |
35 | | void proto_register_rtse(void); |
36 | | void proto_reg_handoff_rtse(void); |
37 | | |
38 | | /* Initialize the protocol and registered fields */ |
39 | | static int proto_rtse; |
40 | | |
41 | | static bool open_request=false; |
42 | | static uint32_t app_proto=0; |
43 | | |
44 | | static proto_tree *top_tree; |
45 | | |
46 | | /* Preferences */ |
47 | | static bool rtse_reassemble = true; |
48 | | |
49 | | static int hf_rtse_rtorq_apdu; /* RTORQapdu */ |
50 | | static int hf_rtse_rtoac_apdu; /* RTOACapdu */ |
51 | | static int hf_rtse_rtorj_apdu; /* RTORJapdu */ |
52 | | static int hf_rtse_rttp_apdu; /* RTTPapdu */ |
53 | | static int hf_rtse_rttr_apdu; /* RTTRapdu */ |
54 | | static int hf_rtse_rtab_apdu; /* RTABapdu */ |
55 | | static int hf_rtse_checkpointSize; /* INTEGER */ |
56 | | static int hf_rtse_windowSize; /* INTEGER */ |
57 | | static int hf_rtse_dialogueMode; /* T_dialogueMode */ |
58 | | static int hf_rtse_connectionDataRQ; /* ConnectionData */ |
59 | | static int hf_rtse_applicationProtocol; /* T_applicationProtocol */ |
60 | | static int hf_rtse_connectionDataAC; /* ConnectionData */ |
61 | | static int hf_rtse_refuseReason; /* RefuseReason */ |
62 | | static int hf_rtse_userDataRJ; /* T_userDataRJ */ |
63 | | static int hf_rtse_abortReason; /* AbortReason */ |
64 | | static int hf_rtse_reflectedParameter; /* BIT_STRING */ |
65 | | static int hf_rtse_userdataAB; /* T_userdataAB */ |
66 | | static int hf_rtse_open; /* T_open */ |
67 | | static int hf_rtse_recover; /* SessionConnectionIdentifier */ |
68 | | static int hf_rtse_callingSSuserReference; /* CallingSSuserReference */ |
69 | | static int hf_rtse_commonReference; /* CommonReference */ |
70 | | static int hf_rtse_additionalReferenceInformation; /* AdditionalReferenceInformation */ |
71 | | static int hf_rtse_t61String; /* T_t61String */ |
72 | | static int hf_rtse_octetString; /* T_octetString */ |
73 | | |
74 | | /* Initialize the subtree pointers */ |
75 | | static int ett_rtse; |
76 | | static int ett_rtse_RTSE_apdus; |
77 | | static int ett_rtse_RTORQapdu; |
78 | | static int ett_rtse_RTOACapdu; |
79 | | static int ett_rtse_RTORJapdu; |
80 | | static int ett_rtse_RTABapdu; |
81 | | static int ett_rtse_ConnectionData; |
82 | | static int ett_rtse_SessionConnectionIdentifier; |
83 | | static int ett_rtse_CallingSSuserReference; |
84 | | |
85 | | static expert_field ei_rtse_dissector_oid_not_implemented; |
86 | | static expert_field ei_rtse_unknown_rtse_pdu; |
87 | | static expert_field ei_rtse_abstract_syntax; |
88 | | |
89 | | static dissector_table_t rtse_oid_dissector_table; |
90 | | static dissector_handle_t rtse_handle; |
91 | | static int ett_rtse_unknown; |
92 | | |
93 | | static reassembly_table rtse_reassembly_table; |
94 | | |
95 | | static int hf_rtse_segment_data; |
96 | | static int hf_rtse_fragments; |
97 | | static int hf_rtse_fragment; |
98 | | static int hf_rtse_fragment_overlap; |
99 | | static int hf_rtse_fragment_overlap_conflicts; |
100 | | static int hf_rtse_fragment_multiple_tails; |
101 | | static int hf_rtse_fragment_too_long_fragment; |
102 | | static int hf_rtse_fragment_error; |
103 | | static int hf_rtse_fragment_count; |
104 | | static int hf_rtse_reassembled_in; |
105 | | static int hf_rtse_reassembled_length; |
106 | | |
107 | | static int ett_rtse_fragment; |
108 | | static int ett_rtse_fragments; |
109 | | |
110 | | static const fragment_items rtse_frag_items = { |
111 | | /* Fragment subtrees */ |
112 | | &ett_rtse_fragment, |
113 | | &ett_rtse_fragments, |
114 | | /* Fragment fields */ |
115 | | &hf_rtse_fragments, |
116 | | &hf_rtse_fragment, |
117 | | &hf_rtse_fragment_overlap, |
118 | | &hf_rtse_fragment_overlap_conflicts, |
119 | | &hf_rtse_fragment_multiple_tails, |
120 | | &hf_rtse_fragment_too_long_fragment, |
121 | | &hf_rtse_fragment_error, |
122 | | &hf_rtse_fragment_count, |
123 | | /* Reassembled in field */ |
124 | | &hf_rtse_reassembled_in, |
125 | | /* Reassembled length field */ |
126 | | &hf_rtse_reassembled_length, |
127 | | /* Reassembled data field */ |
128 | | NULL, |
129 | | /* Tag */ |
130 | | "RTSE fragments" |
131 | | }; |
132 | | |
133 | | void |
134 | | register_rtse_oid_dissector_handle(const char *oid, dissector_handle_t dissector, int proto, const char *name, bool uses_ros) |
135 | 128 | { |
136 | | /* XXX: Note that this fcn is called from proto_reg_handoff in *other* dissectors ... */ |
137 | | |
138 | 128 | static dissector_handle_t ros_handle = NULL; |
139 | | |
140 | 128 | if (ros_handle == NULL) |
141 | 16 | ros_handle = find_dissector("ros"); |
142 | | |
143 | | /* register RTSE with the BER (ACSE) */ |
144 | 128 | register_ber_oid_dissector_handle(oid, rtse_handle, proto, name); |
145 | | |
146 | 128 | if (uses_ros) { |
147 | | /* make sure we call ROS ... */ |
148 | 48 | dissector_add_string("rtse.oid", oid, ros_handle); |
149 | | |
150 | | /* and then tell ROS how to dissect the AS*/ |
151 | 48 | if (dissector != NULL) |
152 | 16 | register_ros_oid_dissector_handle(oid, dissector, proto, name, true); |
153 | | |
154 | 80 | } else { |
155 | | /* otherwise we just remember how to dissect the AS */ |
156 | 80 | dissector_add_string("rtse.oid", oid, dissector); |
157 | 80 | } |
158 | 128 | } |
159 | | |
160 | | static int |
161 | | call_rtse_oid_callback(const char *oid, tvbuff_t *tvb, int offset, packet_info *pinfo, proto_tree *tree, void* data) |
162 | 0 | { |
163 | 0 | tvbuff_t *next_tvb; |
164 | 0 | int len; |
165 | |
|
166 | 0 | next_tvb = tvb_new_subset_remaining(tvb, offset); |
167 | |
|
168 | 0 | if ((len = dissector_try_string_with_data(rtse_oid_dissector_table, oid, next_tvb, pinfo, tree, true, data)) == 0) { |
169 | 0 | proto_item *item; |
170 | 0 | proto_tree *next_tree; |
171 | |
|
172 | 0 | next_tree = proto_tree_add_subtree_format(tree, next_tvb, 0, -1, ett_rtse_unknown, &item, |
173 | 0 | "RTSE: Dissector for OID:%s not implemented. Contact Wireshark developers if you want this supported", oid); |
174 | |
|
175 | 0 | expert_add_info_format(pinfo, item, &ei_rtse_dissector_oid_not_implemented, |
176 | 0 | "RTSE: Dissector for OID %s not implemented", oid); |
177 | 0 | len = dissect_unknown_ber(pinfo, next_tvb, offset, next_tree); |
178 | 0 | } |
179 | |
|
180 | 0 | offset += len; |
181 | |
|
182 | 0 | return offset; |
183 | 0 | } |
184 | | |
185 | | static unsigned |
186 | | call_rtse_external_type_callback(bool implicit_tag _U_, tvbuff_t *tvb, unsigned offset, asn1_ctx_t *actx, proto_tree *tree, int hf_index _U_) |
187 | 0 | { |
188 | 0 | const char *oid = NULL; |
189 | |
|
190 | 0 | if (actx->external.indirect_ref_present) { |
191 | |
|
192 | 0 | oid = (const char *)find_oid_by_pres_ctx_id(actx->pinfo, actx->external.indirect_reference); |
193 | |
|
194 | 0 | if (!oid) |
195 | 0 | proto_tree_add_expert_format(tree, actx->pinfo, &ei_rtse_abstract_syntax, tvb, offset, tvb_captured_length_remaining(tvb, offset), |
196 | 0 | "Unable to determine abstract syntax for indirect reference: %d.", actx->external.indirect_reference); |
197 | 0 | } else if (actx->external.direct_ref_present) { |
198 | 0 | oid = actx->external.direct_reference; |
199 | 0 | } |
200 | |
|
201 | 0 | if (oid) |
202 | 0 | offset = call_rtse_oid_callback(oid, tvb, offset, actx->pinfo, top_tree ? top_tree : tree, actx->private_data); |
203 | |
|
204 | 0 | return offset; |
205 | 0 | } |
206 | | |
207 | | |
208 | | |
209 | | static unsigned |
210 | 0 | dissect_rtse_INTEGER(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
211 | 0 | offset = dissect_ber_integer(implicit_tag, actx, tree, tvb, offset, hf_index, |
212 | 0 | NULL); |
213 | |
|
214 | 0 | return offset; |
215 | 0 | } |
216 | | |
217 | | |
218 | | static const value_string rtse_T_dialogueMode_vals[] = { |
219 | | { 0, "monologue" }, |
220 | | { 1, "twa" }, |
221 | | { 0, NULL } |
222 | | }; |
223 | | |
224 | | |
225 | | static unsigned |
226 | 0 | dissect_rtse_T_dialogueMode(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
227 | 0 | offset = dissect_ber_integer(implicit_tag, actx, tree, tvb, offset, hf_index, |
228 | 0 | NULL); |
229 | |
|
230 | 0 | return offset; |
231 | 0 | } |
232 | | |
233 | | |
234 | | |
235 | | static unsigned |
236 | 0 | dissect_rtse_T_open(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
237 | |
|
238 | 0 | struct SESSION_DATA_STRUCTURE* session = (struct SESSION_DATA_STRUCTURE*)actx->private_data; |
239 | 0 | const char *oid = NULL; |
240 | |
|
241 | 0 | switch(app_proto) { |
242 | 0 | case 1: /* mts-transfer-protocol-1984 */ |
243 | 0 | oid = "applicationProtocol.1"; |
244 | 0 | break; |
245 | 0 | case 12: /* mts-transfer-protocol */ |
246 | 0 | oid = "applicationProtocol.12"; |
247 | 0 | break; |
248 | 0 | default: |
249 | 0 | if(session && session->pres_ctx_id) |
250 | 0 | oid = find_oid_by_pres_ctx_id(actx->pinfo, session->pres_ctx_id); |
251 | 0 | break; |
252 | 0 | } |
253 | | |
254 | 0 | if(!oid) /* XXX: problem here is we haven't decoded the applicationProtocol yet - so we make assumptions! */ |
255 | 0 | oid = "applicationProtocol.12"; |
256 | |
|
257 | 0 | if(oid) { |
258 | |
|
259 | 0 | offset = call_rtse_oid_callback(oid, tvb, offset, actx->pinfo, top_tree ? top_tree : tree, session); |
260 | 0 | } |
261 | | |
262 | | /* else XXX: need to flag we can't find the presentation context */ |
263 | | |
264 | |
|
265 | 0 | return offset; |
266 | 0 | } |
267 | | |
268 | | |
269 | | |
270 | | static unsigned |
271 | 0 | dissect_rtse_T_t61String(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
272 | 0 | tvbuff_t *string = NULL; |
273 | 0 | offset = dissect_ber_restricted_string(implicit_tag, BER_UNI_TAG_TeletexString, |
274 | 0 | actx, tree, tvb, offset, hf_index, |
275 | 0 | &string); |
276 | |
|
277 | 0 | if(open_request && string) |
278 | 0 | col_append_fstr(actx->pinfo->cinfo, COL_INFO, " %s", tvb_get_string_enc(actx->pinfo->pool, string, 0, |
279 | 0 | tvb_reported_length(string), ENC_T61)); |
280 | | |
281 | |
|
282 | 0 | return offset; |
283 | 0 | } |
284 | | |
285 | | |
286 | | |
287 | | static unsigned |
288 | 0 | dissect_rtse_T_octetString(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
289 | 0 | tvbuff_t *string = NULL; |
290 | 0 | offset = dissect_ber_octet_string(implicit_tag, actx, tree, tvb, offset, hf_index, |
291 | 0 | &string); |
292 | |
|
293 | 0 | if(open_request && string) |
294 | 0 | col_append_fstr(actx->pinfo->cinfo, COL_INFO, " %s", tvb_format_text(actx->pinfo->pool, string, 0, tvb_reported_length(string))); |
295 | | |
296 | |
|
297 | 0 | return offset; |
298 | 0 | } |
299 | | |
300 | | |
301 | | static const value_string rtse_CallingSSuserReference_vals[] = { |
302 | | { 0, "t61String" }, |
303 | | { 1, "octetString" }, |
304 | | { 0, NULL } |
305 | | }; |
306 | | |
307 | | static const ber_choice_t CallingSSuserReference_choice[] = { |
308 | | { 0, &hf_rtse_t61String , BER_CLASS_UNI, BER_UNI_TAG_TeletexString, BER_FLAGS_NOOWNTAG, dissect_rtse_T_t61String }, |
309 | | { 1, &hf_rtse_octetString , BER_CLASS_UNI, BER_UNI_TAG_OCTETSTRING, BER_FLAGS_NOOWNTAG, dissect_rtse_T_octetString }, |
310 | | { 0, NULL, 0, 0, 0, NULL } |
311 | | }; |
312 | | |
313 | | static unsigned |
314 | 0 | dissect_rtse_CallingSSuserReference(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
315 | 0 | offset = dissect_ber_choice(actx, tree, tvb, offset, |
316 | 0 | CallingSSuserReference_choice, hf_index, ett_rtse_CallingSSuserReference, |
317 | 0 | NULL); |
318 | |
|
319 | 0 | return offset; |
320 | 0 | } |
321 | | |
322 | | |
323 | | |
324 | | static unsigned |
325 | 0 | dissect_rtse_CommonReference(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
326 | 0 | char *string = NULL; |
327 | 0 | offset = dissect_ber_UTCTime(implicit_tag, actx, tree, tvb, offset, hf_index, &string, NULL); |
328 | |
|
329 | 0 | if(open_request && string) |
330 | 0 | col_append_fstr(actx->pinfo->cinfo, COL_INFO, " %s", string); |
331 | | |
332 | |
|
333 | 0 | return offset; |
334 | 0 | } |
335 | | |
336 | | |
337 | | |
338 | | static unsigned |
339 | 0 | dissect_rtse_AdditionalReferenceInformation(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
340 | 0 | offset = dissect_ber_restricted_string(implicit_tag, BER_UNI_TAG_TeletexString, |
341 | 0 | actx, tree, tvb, offset, hf_index, |
342 | 0 | NULL); |
343 | |
|
344 | 0 | return offset; |
345 | 0 | } |
346 | | |
347 | | |
348 | | static const ber_sequence_t SessionConnectionIdentifier_sequence[] = { |
349 | | { &hf_rtse_callingSSuserReference, BER_CLASS_ANY/*choice*/, -1/*choice*/, BER_FLAGS_NOOWNTAG|BER_FLAGS_NOTCHKTAG, dissect_rtse_CallingSSuserReference }, |
350 | | { &hf_rtse_commonReference, BER_CLASS_UNI, BER_UNI_TAG_UTCTime, BER_FLAGS_NOOWNTAG, dissect_rtse_CommonReference }, |
351 | | { &hf_rtse_additionalReferenceInformation, BER_CLASS_CON, 0, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_AdditionalReferenceInformation }, |
352 | | { NULL, 0, 0, 0, NULL } |
353 | | }; |
354 | | |
355 | | static unsigned |
356 | 0 | dissect_rtse_SessionConnectionIdentifier(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
357 | 0 | if(open_request){ |
358 | 0 | col_append_str(actx->pinfo->cinfo, COL_INFO, "Recover"); |
359 | 0 | } |
360 | 0 | offset = dissect_ber_sequence(implicit_tag, actx, tree, tvb, offset, |
361 | 0 | SessionConnectionIdentifier_sequence, hf_index, ett_rtse_SessionConnectionIdentifier); |
362 | | |
363 | | |
364 | |
|
365 | 0 | return offset; |
366 | 0 | } |
367 | | |
368 | | |
369 | | static const value_string rtse_ConnectionData_vals[] = { |
370 | | { 0, "open" }, |
371 | | { 1, "recover" }, |
372 | | { 0, NULL } |
373 | | }; |
374 | | |
375 | | static const ber_choice_t ConnectionData_choice[] = { |
376 | | { 0, &hf_rtse_open , BER_CLASS_CON, 0, 0, dissect_rtse_T_open }, |
377 | | { 1, &hf_rtse_recover , BER_CLASS_CON, 1, BER_FLAGS_IMPLTAG, dissect_rtse_SessionConnectionIdentifier }, |
378 | | { 0, NULL, 0, 0, 0, NULL } |
379 | | }; |
380 | | |
381 | | static unsigned |
382 | 0 | dissect_rtse_ConnectionData(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
383 | 0 | offset = dissect_ber_choice(actx, tree, tvb, offset, |
384 | 0 | ConnectionData_choice, hf_index, ett_rtse_ConnectionData, |
385 | 0 | NULL); |
386 | |
|
387 | 0 | return offset; |
388 | 0 | } |
389 | | |
390 | | |
391 | | static const value_string rtse_T_applicationProtocol_vals[] = { |
392 | | { 12, "mts-transfer-protocol" }, |
393 | | { 1, "mts-transfer-protocol-1984" }, |
394 | | { 0, NULL } |
395 | | }; |
396 | | |
397 | | |
398 | | static unsigned |
399 | 0 | dissect_rtse_T_applicationProtocol(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
400 | |
|
401 | 0 | offset = dissect_ber_integer(true, actx, tree, tvb, offset, hf_index, &app_proto); |
402 | | |
403 | |
|
404 | 0 | return offset; |
405 | 0 | } |
406 | | |
407 | | |
408 | | static const ber_sequence_t RTORQapdu_set[] = { |
409 | | { &hf_rtse_checkpointSize , BER_CLASS_CON, 0, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_INTEGER }, |
410 | | { &hf_rtse_windowSize , BER_CLASS_CON, 1, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_INTEGER }, |
411 | | { &hf_rtse_dialogueMode , BER_CLASS_CON, 2, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_T_dialogueMode }, |
412 | | { &hf_rtse_connectionDataRQ, BER_CLASS_CON, 3, BER_FLAGS_NOTCHKTAG, dissect_rtse_ConnectionData }, |
413 | | { &hf_rtse_applicationProtocol, BER_CLASS_CON, 4, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_T_applicationProtocol }, |
414 | | { NULL, 0, 0, 0, NULL } |
415 | | }; |
416 | | |
417 | | unsigned |
418 | 0 | dissect_rtse_RTORQapdu(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
419 | 0 | struct SESSION_DATA_STRUCTURE* session = (struct SESSION_DATA_STRUCTURE*)actx->private_data; |
420 | |
|
421 | 0 | if(session != NULL) |
422 | 0 | session->ros_op = (ROS_OP_BIND | ROS_OP_ARGUMENT); |
423 | 0 | open_request=true; |
424 | 0 | offset = dissect_ber_set(implicit_tag, actx, tree, tvb, offset, |
425 | 0 | RTORQapdu_set, hf_index, ett_rtse_RTORQapdu); |
426 | |
|
427 | 0 | open_request=false; |
428 | | |
429 | |
|
430 | 0 | return offset; |
431 | 0 | } |
432 | | |
433 | | |
434 | | static const ber_sequence_t RTOACapdu_set[] = { |
435 | | { &hf_rtse_checkpointSize , BER_CLASS_CON, 0, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_INTEGER }, |
436 | | { &hf_rtse_windowSize , BER_CLASS_CON, 1, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_INTEGER }, |
437 | | { &hf_rtse_connectionDataAC, BER_CLASS_CON, 2, BER_FLAGS_NOTCHKTAG, dissect_rtse_ConnectionData }, |
438 | | { NULL, 0, 0, 0, NULL } |
439 | | }; |
440 | | |
441 | | unsigned |
442 | 0 | dissect_rtse_RTOACapdu(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
443 | 0 | struct SESSION_DATA_STRUCTURE* session = (struct SESSION_DATA_STRUCTURE*)actx->private_data; |
444 | |
|
445 | 0 | if(session != NULL) |
446 | 0 | session->ros_op = (ROS_OP_BIND | ROS_OP_RESULT); |
447 | |
|
448 | 0 | offset = dissect_ber_set(implicit_tag, actx, tree, tvb, offset, |
449 | 0 | RTOACapdu_set, hf_index, ett_rtse_RTOACapdu); |
450 | | |
451 | | |
452 | |
|
453 | 0 | return offset; |
454 | 0 | } |
455 | | |
456 | | |
457 | | static const value_string rtse_RefuseReason_vals[] = { |
458 | | { 0, "rtsBusy" }, |
459 | | { 1, "cannotRecover" }, |
460 | | { 2, "validationFailure" }, |
461 | | { 3, "unacceptableDialogueMode" }, |
462 | | { 0, NULL } |
463 | | }; |
464 | | |
465 | | |
466 | | static unsigned |
467 | 0 | dissect_rtse_RefuseReason(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
468 | 0 | int32_t reason; |
469 | |
|
470 | 0 | offset = dissect_ber_integer(implicit_tag, actx, tree, tvb, offset, hf_index, |
471 | 0 | (uint32_t*)&reason); |
472 | | |
473 | |
|
474 | 0 | col_append_fstr(actx->pinfo->cinfo, COL_INFO, " (%s)", val_to_str(actx->pinfo->pool, reason, rtse_RefuseReason_vals, "reason(%d)")); |
475 | | |
476 | |
|
477 | 0 | return offset; |
478 | 0 | } |
479 | | |
480 | | |
481 | | |
482 | | static unsigned |
483 | 0 | dissect_rtse_T_userDataRJ(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
484 | 0 | struct SESSION_DATA_STRUCTURE* session = (struct SESSION_DATA_STRUCTURE*)actx->private_data; |
485 | 0 | const char *oid = NULL; |
486 | |
|
487 | 0 | switch(app_proto) { |
488 | 0 | case 1: /* mts-transfer-protocol-1984 */ |
489 | 0 | oid = "applicationProtocol.1"; |
490 | 0 | break; |
491 | 0 | case 12: /* mts-transfer-protocol */ |
492 | 0 | oid = "applicationProtocol.12"; |
493 | 0 | break; |
494 | 0 | default: |
495 | 0 | if(session && session->pres_ctx_id) |
496 | 0 | oid = find_oid_by_pres_ctx_id(actx->pinfo, session->pres_ctx_id); |
497 | 0 | break; |
498 | 0 | } |
499 | | |
500 | 0 | if(!oid) /* XXX: problem here is we haven't decoded the applicationProtocol yet - so we make assumptions! */ |
501 | 0 | oid = "applicationProtocol.12"; |
502 | |
|
503 | 0 | if(oid) { |
504 | 0 | if(session != NULL) |
505 | 0 | session->ros_op = (ROS_OP_BIND | ROS_OP_ERROR); |
506 | |
|
507 | 0 | offset = call_rtse_oid_callback(oid, tvb, offset, actx->pinfo, top_tree ? top_tree : tree, session); |
508 | 0 | } |
509 | | |
510 | |
|
511 | 0 | return offset; |
512 | 0 | } |
513 | | |
514 | | |
515 | | static const ber_sequence_t RTORJapdu_set[] = { |
516 | | { &hf_rtse_refuseReason , BER_CLASS_CON, 0, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_RefuseReason }, |
517 | | { &hf_rtse_userDataRJ , BER_CLASS_CON, 1, BER_FLAGS_OPTIONAL, dissect_rtse_T_userDataRJ }, |
518 | | { NULL, 0, 0, 0, NULL } |
519 | | }; |
520 | | |
521 | | unsigned |
522 | 0 | dissect_rtse_RTORJapdu(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
523 | 0 | col_append_str(actx->pinfo->cinfo, COL_INFO, "Refuse"); |
524 | |
|
525 | 0 | offset = dissect_ber_set(implicit_tag, actx, tree, tvb, offset, |
526 | 0 | RTORJapdu_set, hf_index, ett_rtse_RTORJapdu); |
527 | | |
528 | | |
529 | |
|
530 | 0 | return offset; |
531 | 0 | } |
532 | | |
533 | | |
534 | | |
535 | | static unsigned |
536 | 0 | dissect_rtse_RTTPapdu(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
537 | 0 | int32_t priority; |
538 | |
|
539 | 0 | col_append_str(actx->pinfo->cinfo, COL_INFO, "Turn-Please"); |
540 | |
|
541 | 0 | offset = dissect_ber_integer(implicit_tag, actx, tree, tvb, offset, hf_index, |
542 | 0 | (uint32_t*)&priority); |
543 | | |
544 | |
|
545 | 0 | col_append_fstr(actx->pinfo->cinfo, COL_INFO, " (%d)", priority); |
546 | | |
547 | |
|
548 | 0 | return offset; |
549 | 0 | } |
550 | | |
551 | | |
552 | | |
553 | | static unsigned |
554 | 0 | dissect_rtse_RTTRapdu(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
555 | 0 | tvbuff_t *next_tvb = NULL; |
556 | 0 | struct SESSION_DATA_STRUCTURE* session = (struct SESSION_DATA_STRUCTURE*)actx->private_data; |
557 | |
|
558 | 0 | offset = dissect_ber_octet_string(false, actx, tree, tvb, offset, hf_index, &next_tvb); |
559 | |
|
560 | 0 | if(next_tvb) { |
561 | | |
562 | | /* XXX: we should check is this is an EXTERNAL first */ |
563 | | |
564 | | /* ROS won't do this for us */ |
565 | 0 | if(session) |
566 | 0 | session->ros_op = (ROS_OP_INVOKE | ROS_OP_ARGUMENT); |
567 | |
|
568 | 0 | offset = dissect_ber_external_type(false, tree, next_tvb, 0, actx, -1, call_rtse_external_type_callback); |
569 | 0 | } |
570 | | |
571 | | |
572 | |
|
573 | 0 | return offset; |
574 | 0 | } |
575 | | |
576 | | |
577 | | static const value_string rtse_AbortReason_vals[] = { |
578 | | { 0, "localSystemProblem" }, |
579 | | { 1, "invalidParameter" }, |
580 | | { 2, "unrecognizedActivity" }, |
581 | | { 3, "temporaryProblem" }, |
582 | | { 4, "protocolError" }, |
583 | | { 5, "permanentProblem" }, |
584 | | { 6, "userError" }, |
585 | | { 7, "transferCompleted" }, |
586 | | { 0, NULL } |
587 | | }; |
588 | | |
589 | | |
590 | | static unsigned |
591 | 0 | dissect_rtse_AbortReason(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
592 | 0 | int32_t reason = -1; |
593 | |
|
594 | 0 | offset = dissect_ber_integer(implicit_tag, actx, tree, tvb, offset, hf_index, |
595 | 0 | (uint32_t*)&reason); |
596 | | |
597 | |
|
598 | 0 | col_append_fstr(actx->pinfo->cinfo, COL_INFO, " (%s)", val_to_str(actx->pinfo->pool, reason, rtse_AbortReason_vals, "reason(%d)")); |
599 | | |
600 | |
|
601 | 0 | return offset; |
602 | 0 | } |
603 | | |
604 | | |
605 | | |
606 | | static unsigned |
607 | 0 | dissect_rtse_BIT_STRING(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
608 | 0 | offset = dissect_ber_bitstring(implicit_tag, actx, tree, tvb, offset, |
609 | 0 | NULL, 0, hf_index, -1, |
610 | 0 | NULL); |
611 | |
|
612 | 0 | return offset; |
613 | 0 | } |
614 | | |
615 | | |
616 | | |
617 | | static unsigned |
618 | 0 | dissect_rtse_T_userdataAB(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
619 | | /*XXX not implemented yet */ |
620 | | |
621 | |
|
622 | 0 | return offset; |
623 | 0 | } |
624 | | |
625 | | |
626 | | static const ber_sequence_t RTABapdu_set[] = { |
627 | | { &hf_rtse_abortReason , BER_CLASS_CON, 0, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_AbortReason }, |
628 | | { &hf_rtse_reflectedParameter, BER_CLASS_CON, 1, BER_FLAGS_OPTIONAL|BER_FLAGS_IMPLTAG, dissect_rtse_BIT_STRING }, |
629 | | { &hf_rtse_userdataAB , BER_CLASS_CON, 2, BER_FLAGS_OPTIONAL, dissect_rtse_T_userdataAB }, |
630 | | { NULL, 0, 0, 0, NULL } |
631 | | }; |
632 | | |
633 | | unsigned |
634 | 0 | dissect_rtse_RTABapdu(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
635 | 0 | col_append_str(actx->pinfo->cinfo, COL_INFO, "Abort"); |
636 | |
|
637 | 0 | offset = dissect_ber_set(implicit_tag, actx, tree, tvb, offset, |
638 | 0 | RTABapdu_set, hf_index, ett_rtse_RTABapdu); |
639 | | |
640 | | |
641 | |
|
642 | 0 | return offset; |
643 | 0 | } |
644 | | |
645 | | |
646 | | static const ber_choice_t RTSE_apdus_choice[] = { |
647 | | { 0, &hf_rtse_rtorq_apdu , BER_CLASS_CON, 16, BER_FLAGS_IMPLTAG, dissect_rtse_RTORQapdu }, |
648 | | { 1, &hf_rtse_rtoac_apdu , BER_CLASS_CON, 17, BER_FLAGS_IMPLTAG, dissect_rtse_RTOACapdu }, |
649 | | { 2, &hf_rtse_rtorj_apdu , BER_CLASS_CON, 18, BER_FLAGS_IMPLTAG, dissect_rtse_RTORJapdu }, |
650 | | { 3, &hf_rtse_rttp_apdu , BER_CLASS_UNI, BER_UNI_TAG_INTEGER, BER_FLAGS_NOOWNTAG, dissect_rtse_RTTPapdu }, |
651 | | { 4, &hf_rtse_rttr_apdu , BER_CLASS_UNI, BER_UNI_TAG_OCTETSTRING, BER_FLAGS_NOOWNTAG, dissect_rtse_RTTRapdu }, |
652 | | { 5, &hf_rtse_rtab_apdu , BER_CLASS_CON, 22, BER_FLAGS_IMPLTAG, dissect_rtse_RTABapdu }, |
653 | | { 0, NULL, 0, 0, 0, NULL } |
654 | | }; |
655 | | |
656 | | static unsigned |
657 | 0 | dissect_rtse_RTSE_apdus(bool implicit_tag _U_, tvbuff_t *tvb _U_, unsigned offset _U_, asn1_ctx_t *actx _U_, proto_tree *tree _U_, int hf_index _U_) { |
658 | 0 | offset = dissect_ber_choice(actx, tree, tvb, offset, |
659 | 0 | RTSE_apdus_choice, hf_index, ett_rtse_RTSE_apdus, |
660 | 0 | NULL); |
661 | |
|
662 | 0 | return offset; |
663 | 0 | } |
664 | | |
665 | | |
666 | | /* |
667 | | * Dissect RTSE PDUs inside a PPDU. |
668 | | */ |
669 | | static int |
670 | | dissect_rtse(tvbuff_t *tvb, packet_info *pinfo, proto_tree *parent_tree, void* data) |
671 | 1 | { |
672 | 1 | unsigned offset = 0; |
673 | 1 | unsigned old_offset; |
674 | 1 | proto_item *item; |
675 | 1 | proto_tree *tree; |
676 | 1 | proto_tree *next_tree=NULL; |
677 | 1 | tvbuff_t *next_tvb = NULL; |
678 | 1 | tvbuff_t *data_tvb = NULL; |
679 | 1 | fragment_head *frag_msg = NULL; |
680 | 1 | uint32_t fragment_length; |
681 | 1 | uint32_t rtse_id = 0; |
682 | 1 | bool data_handled = false; |
683 | 1 | struct SESSION_DATA_STRUCTURE* session; |
684 | 1 | conversation_t *conversation = NULL; |
685 | 1 | asn1_ctx_t asn1_ctx; |
686 | 1 | asn1_ctx_init(&asn1_ctx, ASN1_ENC_BER, true, pinfo); |
687 | | |
688 | | /* do we have application context from the acse dissector? */ |
689 | 1 | if (data == NULL) |
690 | 1 | return 0; |
691 | 0 | session = (struct SESSION_DATA_STRUCTURE*)data; |
692 | | |
693 | | /* save parent_tree so subdissectors can create new top nodes */ |
694 | 0 | top_tree=parent_tree; |
695 | |
|
696 | 0 | asn1_ctx.private_data = session; |
697 | |
|
698 | 0 | col_set_str(pinfo->cinfo, COL_PROTOCOL, "RTSE"); |
699 | 0 | col_clear(pinfo->cinfo, COL_INFO); |
700 | |
|
701 | 0 | if (rtse_reassemble && |
702 | 0 | ((session->spdu_type == SES_DATA_TRANSFER) || |
703 | 0 | (session->spdu_type == SES_MAJOR_SYNC_POINT))) |
704 | 0 | { |
705 | | /* Use conversation index as fragment id */ |
706 | 0 | conversation = find_conversation_pinfo(pinfo, 0); |
707 | 0 | if (conversation != NULL) { |
708 | 0 | rtse_id = conversation->conv_index; |
709 | 0 | } |
710 | 0 | session->rtse_reassemble = true; |
711 | 0 | } |
712 | 0 | if (rtse_reassemble && session->spdu_type == SES_MAJOR_SYNC_POINT) { |
713 | 0 | frag_msg = fragment_end_seq_next (&rtse_reassembly_table, |
714 | 0 | pinfo, rtse_id, NULL); |
715 | 0 | next_tvb = process_reassembled_data (tvb, offset, pinfo, "Reassembled RTSE", |
716 | 0 | frag_msg, &rtse_frag_items, NULL, parent_tree); |
717 | 0 | } |
718 | |
|
719 | 0 | item = proto_tree_add_item(parent_tree, proto_rtse, next_tvb ? next_tvb : tvb, 0, -1, ENC_NA); |
720 | 0 | tree = proto_item_add_subtree(item, ett_rtse); |
721 | |
|
722 | 0 | if (rtse_reassemble && session->spdu_type == SES_DATA_TRANSFER) { |
723 | | /* strip off the OCTET STRING encoding - including any CONSTRUCTED OCTET STRING */ |
724 | 0 | dissect_ber_octet_string(false, &asn1_ctx, tree, tvb, offset, hf_rtse_segment_data, &data_tvb); |
725 | |
|
726 | 0 | if (data_tvb) { |
727 | 0 | fragment_length = tvb_captured_length_remaining (data_tvb, 0); |
728 | 0 | proto_item_append_text(asn1_ctx.created_item, " (%u byte%s)", fragment_length, |
729 | 0 | plurality(fragment_length, "", "s")); |
730 | 0 | frag_msg = fragment_add_seq_next (&rtse_reassembly_table, |
731 | 0 | data_tvb, 0, pinfo, |
732 | 0 | rtse_id, NULL, |
733 | 0 | fragment_length, true); |
734 | 0 | if (frag_msg && pinfo->num != frag_msg->reassembled_in) { |
735 | | /* Add a "Reassembled in" link if not reassembled in this frame */ |
736 | 0 | proto_tree_add_uint (tree, *(rtse_frag_items.hf_reassembled_in), |
737 | 0 | data_tvb, 0, 0, frag_msg->reassembled_in); |
738 | 0 | } |
739 | 0 | pinfo->fragmented = true; |
740 | 0 | data_handled = true; |
741 | 0 | } else { |
742 | 0 | fragment_length = tvb_captured_length_remaining (tvb, offset); |
743 | 0 | } |
744 | |
|
745 | 0 | col_append_fstr(pinfo->cinfo, COL_INFO, "[RTSE fragment, %u byte%s]", |
746 | 0 | fragment_length, plurality(fragment_length, "", "s")); |
747 | 0 | } else if (rtse_reassemble && session->spdu_type == SES_MAJOR_SYNC_POINT) { |
748 | 0 | if (next_tvb) { |
749 | | /* ROS won't do this for us */ |
750 | 0 | session->ros_op = (ROS_OP_INVOKE | ROS_OP_ARGUMENT); |
751 | 0 | /*offset=*/dissect_ber_external_type(false, tree, next_tvb, 0, &asn1_ctx, -1, call_rtse_external_type_callback); |
752 | 0 | top_tree = NULL; |
753 | | /* Return other than 0 to indicate that we handled this packet */ |
754 | 0 | return 1; |
755 | 0 | } else { |
756 | 0 | offset = tvb_captured_length (tvb); |
757 | 0 | } |
758 | 0 | pinfo->fragmented = false; |
759 | 0 | data_handled = true; |
760 | 0 | } |
761 | | |
762 | 0 | if (!data_handled) { |
763 | 0 | while (tvb_reported_length_remaining(tvb, offset) > 0) { |
764 | 0 | old_offset=offset; |
765 | 0 | offset=dissect_rtse_RTSE_apdus(true, tvb, offset, &asn1_ctx, tree, -1); |
766 | 0 | if (offset == old_offset) { |
767 | 0 | next_tree = proto_tree_add_subtree(tree, tvb, offset, -1, |
768 | 0 | ett_rtse_unknown, &item, "Unknown RTSE PDU"); |
769 | 0 | expert_add_info (pinfo, item, &ei_rtse_unknown_rtse_pdu); |
770 | 0 | dissect_unknown_ber(pinfo, tvb, offset, next_tree); |
771 | 0 | break; |
772 | 0 | } |
773 | 0 | } |
774 | 0 | } |
775 | |
|
776 | 0 | top_tree = NULL; |
777 | 0 | return tvb_captured_length(tvb); |
778 | 0 | } |
779 | | |
780 | | /*--- proto_register_rtse -------------------------------------------*/ |
781 | 16 | void proto_register_rtse(void) { |
782 | | |
783 | | /* List of fields */ |
784 | 16 | static hf_register_info hf[] = |
785 | 16 | { |
786 | | /* Fragment entries */ |
787 | 16 | { &hf_rtse_segment_data, |
788 | 16 | { "RTSE segment data", "rtse.segment", FT_NONE, BASE_NONE, |
789 | 16 | NULL, 0x00, NULL, HFILL } }, |
790 | 16 | { &hf_rtse_fragments, |
791 | 16 | { "RTSE fragments", "rtse.fragments", FT_NONE, BASE_NONE, |
792 | 16 | NULL, 0x00, NULL, HFILL } }, |
793 | 16 | { &hf_rtse_fragment, |
794 | 16 | { "RTSE fragment", "rtse.fragment", FT_FRAMENUM, BASE_NONE, |
795 | 16 | NULL, 0x00, NULL, HFILL } }, |
796 | 16 | { &hf_rtse_fragment_overlap, |
797 | 16 | { "RTSE fragment overlap", "rtse.fragment.overlap", FT_BOOLEAN, |
798 | 16 | BASE_NONE, NULL, 0x0, NULL, HFILL } }, |
799 | 16 | { &hf_rtse_fragment_overlap_conflicts, |
800 | 16 | { "RTSE fragment overlapping with conflicting data", |
801 | 16 | "rtse.fragment.overlap.conflicts", FT_BOOLEAN, BASE_NONE, |
802 | 16 | NULL, 0x0, NULL, HFILL } }, |
803 | 16 | { &hf_rtse_fragment_multiple_tails, |
804 | 16 | { "RTSE has multiple tail fragments", |
805 | 16 | "rtse.fragment.multiple_tails", FT_BOOLEAN, BASE_NONE, |
806 | 16 | NULL, 0x0, NULL, HFILL } }, |
807 | 16 | { &hf_rtse_fragment_too_long_fragment, |
808 | 16 | { "RTSE fragment too long", "rtse.fragment.too_long_fragment", |
809 | 16 | FT_BOOLEAN, BASE_NONE, NULL, 0x0, NULL, HFILL } }, |
810 | 16 | { &hf_rtse_fragment_error, |
811 | 16 | { "RTSE defragmentation error", "rtse.fragment.error", FT_FRAMENUM, |
812 | 16 | BASE_NONE, NULL, 0x00, NULL, HFILL } }, |
813 | 16 | { &hf_rtse_fragment_count, |
814 | 16 | { "RTSE fragment count", "rtse.fragment.count", FT_UINT32, BASE_DEC, |
815 | 16 | NULL, 0x00, NULL, HFILL } }, |
816 | 16 | { &hf_rtse_reassembled_in, |
817 | 16 | { "Reassembled RTSE in frame", "rtse.reassembled.in", FT_FRAMENUM, BASE_NONE, |
818 | 16 | NULL, 0x00, "This RTSE packet is reassembled in this frame", HFILL } }, |
819 | 16 | { &hf_rtse_reassembled_length, |
820 | 16 | { "Reassembled RTSE length", "rtse.reassembled.length", FT_UINT32, BASE_DEC, |
821 | 16 | NULL, 0x00, "The total length of the reassembled payload", HFILL } }, |
822 | | |
823 | 16 | { &hf_rtse_rtorq_apdu, |
824 | 16 | { "rtorq-apdu", "rtse.rtorq_apdu_element", |
825 | 16 | FT_NONE, BASE_NONE, NULL, 0, |
826 | 16 | "RTORQapdu", HFILL }}, |
827 | 16 | { &hf_rtse_rtoac_apdu, |
828 | 16 | { "rtoac-apdu", "rtse.rtoac_apdu_element", |
829 | 16 | FT_NONE, BASE_NONE, NULL, 0, |
830 | 16 | "RTOACapdu", HFILL }}, |
831 | 16 | { &hf_rtse_rtorj_apdu, |
832 | 16 | { "rtorj-apdu", "rtse.rtorj_apdu_element", |
833 | 16 | FT_NONE, BASE_NONE, NULL, 0, |
834 | 16 | "RTORJapdu", HFILL }}, |
835 | 16 | { &hf_rtse_rttp_apdu, |
836 | 16 | { "rttp-apdu", "rtse.rttp_apdu", |
837 | 16 | FT_INT32, BASE_DEC, NULL, 0, |
838 | 16 | "RTTPapdu", HFILL }}, |
839 | 16 | { &hf_rtse_rttr_apdu, |
840 | 16 | { "rttr-apdu", "rtse.rttr_apdu", |
841 | 16 | FT_BYTES, BASE_NONE, NULL, 0, |
842 | 16 | "RTTRapdu", HFILL }}, |
843 | 16 | { &hf_rtse_rtab_apdu, |
844 | 16 | { "rtab-apdu", "rtse.rtab_apdu_element", |
845 | 16 | FT_NONE, BASE_NONE, NULL, 0, |
846 | 16 | "RTABapdu", HFILL }}, |
847 | 16 | { &hf_rtse_checkpointSize, |
848 | 16 | { "checkpointSize", "rtse.checkpointSize", |
849 | 16 | FT_INT32, BASE_DEC, NULL, 0, |
850 | 16 | "INTEGER", HFILL }}, |
851 | 16 | { &hf_rtse_windowSize, |
852 | 16 | { "windowSize", "rtse.windowSize", |
853 | 16 | FT_INT32, BASE_DEC, NULL, 0, |
854 | 16 | "INTEGER", HFILL }}, |
855 | 16 | { &hf_rtse_dialogueMode, |
856 | 16 | { "dialogueMode", "rtse.dialogueMode", |
857 | 16 | FT_INT32, BASE_DEC, VALS(rtse_T_dialogueMode_vals), 0, |
858 | 16 | NULL, HFILL }}, |
859 | 16 | { &hf_rtse_connectionDataRQ, |
860 | 16 | { "connectionDataRQ", "rtse.connectionDataRQ", |
861 | 16 | FT_UINT32, BASE_DEC, VALS(rtse_ConnectionData_vals), 0, |
862 | 16 | "ConnectionData", HFILL }}, |
863 | 16 | { &hf_rtse_applicationProtocol, |
864 | 16 | { "applicationProtocol", "rtse.applicationProtocol", |
865 | 16 | FT_INT32, BASE_DEC, VALS(rtse_T_applicationProtocol_vals), 0, |
866 | 16 | NULL, HFILL }}, |
867 | 16 | { &hf_rtse_connectionDataAC, |
868 | 16 | { "connectionDataAC", "rtse.connectionDataAC", |
869 | 16 | FT_UINT32, BASE_DEC, VALS(rtse_ConnectionData_vals), 0, |
870 | 16 | "ConnectionData", HFILL }}, |
871 | 16 | { &hf_rtse_refuseReason, |
872 | 16 | { "refuseReason", "rtse.refuseReason", |
873 | 16 | FT_INT32, BASE_DEC, VALS(rtse_RefuseReason_vals), 0, |
874 | 16 | NULL, HFILL }}, |
875 | 16 | { &hf_rtse_userDataRJ, |
876 | 16 | { "userDataRJ", "rtse.userDataRJ_element", |
877 | 16 | FT_NONE, BASE_NONE, NULL, 0, |
878 | 16 | NULL, HFILL }}, |
879 | 16 | { &hf_rtse_abortReason, |
880 | 16 | { "abortReason", "rtse.abortReason", |
881 | 16 | FT_INT32, BASE_DEC, VALS(rtse_AbortReason_vals), 0, |
882 | 16 | NULL, HFILL }}, |
883 | 16 | { &hf_rtse_reflectedParameter, |
884 | 16 | { "reflectedParameter", "rtse.reflectedParameter", |
885 | 16 | FT_BYTES, BASE_NONE, NULL, 0, |
886 | 16 | "BIT_STRING", HFILL }}, |
887 | 16 | { &hf_rtse_userdataAB, |
888 | 16 | { "userdataAB", "rtse.userdataAB_element", |
889 | 16 | FT_NONE, BASE_NONE, NULL, 0, |
890 | 16 | NULL, HFILL }}, |
891 | 16 | { &hf_rtse_open, |
892 | 16 | { "open", "rtse.open_element", |
893 | 16 | FT_NONE, BASE_NONE, NULL, 0, |
894 | 16 | NULL, HFILL }}, |
895 | 16 | { &hf_rtse_recover, |
896 | 16 | { "recover", "rtse.recover_element", |
897 | 16 | FT_NONE, BASE_NONE, NULL, 0, |
898 | 16 | "SessionConnectionIdentifier", HFILL }}, |
899 | 16 | { &hf_rtse_callingSSuserReference, |
900 | 16 | { "callingSSuserReference", "rtse.callingSSuserReference", |
901 | 16 | FT_UINT32, BASE_DEC, VALS(rtse_CallingSSuserReference_vals), 0, |
902 | 16 | NULL, HFILL }}, |
903 | 16 | { &hf_rtse_commonReference, |
904 | 16 | { "commonReference", "rtse.commonReference", |
905 | 16 | FT_STRING, BASE_NONE, NULL, 0, |
906 | 16 | NULL, HFILL }}, |
907 | 16 | { &hf_rtse_additionalReferenceInformation, |
908 | 16 | { "additionalReferenceInformation", "rtse.additionalReferenceInformation", |
909 | 16 | FT_STRING, BASE_NONE, NULL, 0, |
910 | 16 | NULL, HFILL }}, |
911 | 16 | { &hf_rtse_t61String, |
912 | 16 | { "t61String", "rtse.t61String", |
913 | 16 | FT_STRING, BASE_NONE, NULL, 0, |
914 | 16 | NULL, HFILL }}, |
915 | 16 | { &hf_rtse_octetString, |
916 | 16 | { "octetString", "rtse.octetString", |
917 | 16 | FT_BYTES, BASE_NONE, NULL, 0, |
918 | 16 | NULL, HFILL }}, |
919 | 16 | }; |
920 | | |
921 | | /* List of subtrees */ |
922 | 16 | static int *ett[] = { |
923 | 16 | &ett_rtse, |
924 | 16 | &ett_rtse_unknown, |
925 | 16 | &ett_rtse_fragment, |
926 | 16 | &ett_rtse_fragments, |
927 | 16 | &ett_rtse_RTSE_apdus, |
928 | 16 | &ett_rtse_RTORQapdu, |
929 | 16 | &ett_rtse_RTOACapdu, |
930 | 16 | &ett_rtse_RTORJapdu, |
931 | 16 | &ett_rtse_RTABapdu, |
932 | 16 | &ett_rtse_ConnectionData, |
933 | 16 | &ett_rtse_SessionConnectionIdentifier, |
934 | 16 | &ett_rtse_CallingSSuserReference, |
935 | 16 | }; |
936 | | |
937 | 16 | static ei_register_info ei[] = { |
938 | 16 | { &ei_rtse_dissector_oid_not_implemented, { "rtse.dissector_oid_not_implemented", PI_UNDECODED, PI_WARN, "RTSE: Dissector for OID not implemented", EXPFILL }}, |
939 | 16 | { &ei_rtse_unknown_rtse_pdu, { "rtse.unknown_rtse_pdu", PI_UNDECODED, PI_WARN, "Unknown RTSE PDU", EXPFILL }}, |
940 | 16 | { &ei_rtse_abstract_syntax, { "rtse.bad_abstract_syntax", PI_PROTOCOL, PI_WARN, "Unable to determine abstract syntax for indirect reference", EXPFILL }}, |
941 | 16 | }; |
942 | | |
943 | 16 | expert_module_t* expert_rtse; |
944 | 16 | module_t *rtse_module; |
945 | | |
946 | | /* Register protocol */ |
947 | 16 | proto_rtse = proto_register_protocol("X.228 OSI Reliable Transfer Service", "RTSE", "rtse"); |
948 | 16 | rtse_handle = register_dissector("rtse", dissect_rtse, proto_rtse); |
949 | | /* Register fields and subtrees */ |
950 | 16 | proto_register_field_array(proto_rtse, hf, array_length(hf)); |
951 | 16 | proto_register_subtree_array(ett, array_length(ett)); |
952 | 16 | expert_rtse = expert_register_protocol(proto_rtse); |
953 | 16 | expert_register_field_array(expert_rtse, ei, array_length(ei)); |
954 | | |
955 | 16 | reassembly_table_register (&rtse_reassembly_table, |
956 | 16 | &addresses_reassembly_table_functions); |
957 | | |
958 | 16 | rtse_module = prefs_register_protocol_subtree("OSI", proto_rtse, NULL); |
959 | | |
960 | 16 | prefs_register_bool_preference(rtse_module, "reassemble", |
961 | 16 | "Reassemble segmented RTSE datagrams", |
962 | 16 | "Whether segmented RTSE datagrams should be reassembled." |
963 | 16 | " To use this option, you must also enable" |
964 | 16 | " \"Allow subdissectors to reassemble TCP streams\"" |
965 | 16 | " in the TCP protocol settings.", &rtse_reassemble); |
966 | | |
967 | 16 | rtse_oid_dissector_table = register_dissector_table("rtse.oid", "RTSE OID Dissectors", proto_rtse, FT_STRING, STRING_CASE_SENSITIVE); |
968 | 16 | } |
969 | | |
970 | | |
971 | | /*--- proto_reg_handoff_rtse --- */ |
972 | 16 | void proto_reg_handoff_rtse(void) { |
973 | | |
974 | | |
975 | 16 | } |
976 | | |
977 | | /* |
978 | | * Editor modelines - https://www.wireshark.org/tools/modelines.html |
979 | | * |
980 | | * Local variables: |
981 | | * c-basic-offset: 4 |
982 | | * tab-width: 8 |
983 | | * indent-tabs-mode: nil |
984 | | * End: |
985 | | * |
986 | | * vi: set shiftwidth=4 tabstop=8 expandtab: |
987 | | * :indentSize=4:tabSize=8:noTabs=true: |
988 | | */ |