Coverage Report

Created: 2025-02-15 06:25

/src/wireshark/epan/dissectors/packet-redback.c
Line
Count
Source (jump to first uncovered line)
1
/* packet-redback.c
2
 *
3
 * Wireshark - Network traffic analyzer
4
 * By Gerald Combs <gerald@wireshark.org>
5
 *
6
 * Ericsson SmartEdge tcpdump trace disassembly
7
 * Copyright 2005-2014 Florian Lohoff <f@zz.de>
8
 *
9
 * SPDX-License-Identifier: GPL-2.0-or-later
10
 */
11
#include "config.h"
12
13
#include <epan/packet.h>
14
#include <epan/expert.h>
15
#include <wiretap/wtap.h>
16
17
18
void proto_register_redback(void);
19
void proto_reg_handoff_redback(void);
20
21
static dissector_handle_t redback_handle;
22
23
static int ett_redback;
24
25
static dissector_table_t osinl_incl_subdissector_table;
26
static dissector_table_t osinl_excl_subdissector_table;
27
28
static dissector_handle_t ipv4_handle;
29
static dissector_handle_t ipv6_handle;
30
static dissector_handle_t ethnofcs_handle;
31
static dissector_handle_t clnp_handle;
32
static dissector_handle_t arp_handle;
33
static dissector_handle_t ppp_handle;
34
static dissector_handle_t ppphdlc_handle;
35
36
static int proto_redback;
37
38
static int hf_redback_circuit;
39
static int hf_redback_context;
40
static int hf_redback_dataoffset;
41
static int hf_redback_flags;
42
static int hf_redback_l3offset;
43
static int hf_redback_length;
44
static int hf_redback_padding;
45
static int hf_redback_protocol;
46
static int hf_redback_unknown;
47
48
static expert_field ei_redback_protocol;
49
50
static int
51
dissect_redback(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data _U_)
52
0
{
53
0
  uint16_t    l3off, dataoff, proto;
54
0
  proto_item  *ti, *protocol_item;
55
0
  proto_tree  *rbtree = NULL;
56
0
  tvbuff_t  *next_tvb;
57
58
0
  col_set_str(pinfo->cinfo,COL_PROTOCOL,"RBN");
59
60
0
  dataoff = tvb_get_ntohs(tvb, 20);
61
0
  l3off = tvb_get_ntohs(tvb, 22);
62
63
0
  ti = proto_tree_add_item(tree, proto_redback, tvb, 0, -1, ENC_NA);
64
0
  rbtree = proto_item_add_subtree(ti, ett_redback);
65
66
0
  proto_tree_add_item(rbtree, hf_redback_context, tvb, 0, 4, ENC_BIG_ENDIAN);
67
0
  proto_tree_add_item(rbtree, hf_redback_flags, tvb, 4, 4, ENC_BIG_ENDIAN);
68
0
  proto_tree_add_item(rbtree, hf_redback_circuit, tvb, 8, 8, ENC_BIG_ENDIAN);
69
0
  proto_tree_add_item(rbtree, hf_redback_length, tvb, 16, 2, ENC_BIG_ENDIAN);
70
0
  protocol_item = proto_tree_add_item(rbtree, hf_redback_protocol, tvb, 18, 2, ENC_BIG_ENDIAN);
71
0
  proto_tree_add_item(rbtree, hf_redback_dataoffset, tvb, 20, 2, ENC_BIG_ENDIAN);
72
0
  proto_tree_add_item(rbtree, hf_redback_l3offset, tvb, 22, 2, ENC_BIG_ENDIAN);
73
74
0
  if (dataoff > 24) {
75
0
    proto_tree_add_item(rbtree, hf_redback_padding, tvb, 24, dataoff-24, ENC_NA);
76
0
  }
77
78
0
  proto = tvb_get_ntohs(tvb, 18);
79
0
  switch(proto) {
80
0
    case 0x01:
81
      /*
82
       * IP on Ethernet - Incoming data points to an ethernet header
83
       * outgoing we have a pure IPv4 Packet
84
       */
85
0
      next_tvb = tvb_new_subset_remaining(tvb, dataoff);
86
0
      if (dataoff == l3off)
87
0
        call_dissector(ipv4_handle, next_tvb, pinfo, tree);
88
0
      else if (dataoff+2 == l3off)
89
0
        call_dissector(ppp_handle, next_tvb, pinfo, tree);
90
0
      else if (dataoff+4 == l3off)
91
0
        call_dissector(ppphdlc_handle, next_tvb, pinfo, tree);
92
0
      else
93
0
        call_dissector(ethnofcs_handle, next_tvb, pinfo, tree);
94
0
      break;
95
0
    case 0x02:
96
      /*
97
       * This is ISIS - Either incoming with ethernet FCS
98
       * and CLNP - passed to the eth dissector or in case
99
       * of outgoing it's pure ISIS and the linecard attaches
100
       * the ethernet and CLNP headers ...
101
       *
102
       */
103
0
      next_tvb = tvb_new_subset_remaining(tvb, dataoff);
104
0
      if (l3off > dataoff) {
105
0
        call_dissector(ethnofcs_handle, next_tvb, pinfo, tree);
106
0
      } else {
107
0
        uint8_t nlpid = tvb_get_uint8(tvb, dataoff);
108
0
        if(dissector_try_uint(osinl_incl_subdissector_table, nlpid, next_tvb, pinfo, tree))
109
0
          break;
110
0
        next_tvb = tvb_new_subset_remaining(tvb, dataoff+1);
111
0
        if(dissector_try_uint(osinl_excl_subdissector_table, nlpid, next_tvb, pinfo, tree))
112
0
          break;
113
0
        next_tvb = tvb_new_subset_remaining(tvb, dataoff);
114
0
        call_data_dissector(next_tvb, pinfo, tree);
115
0
      }
116
0
      break;
117
0
    case 0x06: {
118
      /*
119
       * PPP Messages e.g. LCP, IPCP etc - possibly on ethernet in case of PPPoE.
120
       * PPPoE messages are Protocol 8 ...
121
       */
122
0
      uint32_t    flags;
123
0
      flags = tvb_get_ntohl(tvb, 4);
124
125
0
      if (flags & 0x04000000) {
126
0
        next_tvb = tvb_new_subset_remaining(tvb, dataoff);
127
0
      } else {
128
0
        if (tree)
129
0
          proto_tree_add_item(rbtree, hf_redback_unknown, tvb, dataoff, 4, ENC_NA);
130
0
        next_tvb = tvb_new_subset_remaining(tvb, dataoff+4);
131
0
      }
132
133
0
      if (l3off == dataoff) {
134
0
        call_dissector(ppp_handle, next_tvb, pinfo, tree);
135
0
      } else {
136
0
        call_dissector(ethnofcs_handle, next_tvb, pinfo, tree);
137
0
      }
138
0
      break;
139
0
    }
140
0
    case 0x03: /* Unicast Ethernet tx - Seen with PPPoE PADO */
141
0
    case 0x04: /* Unicast Ethernet rx - Seen with ARP  */
142
0
    case 0x08: /* Broadcast Ethernet rx - Seen with PPPoE PADI */
143
0
      next_tvb = tvb_new_subset_remaining(tvb, dataoff);
144
0
      call_dissector(ethnofcs_handle, next_tvb, pinfo, tree);
145
0
      break;
146
0
    case 0x09: /* IPv6 either encapsulated as ethernet or native ip */
147
0
      next_tvb = tvb_new_subset_remaining(tvb, dataoff);
148
0
      if (dataoff == l3off)
149
0
        call_dissector(ipv6_handle, next_tvb, pinfo, tree);
150
0
      else
151
0
        call_dissector(ethnofcs_handle, next_tvb, pinfo, tree);
152
0
      break;
153
0
    default:
154
0
      expert_add_info(pinfo, protocol_item, &ei_redback_protocol);
155
0
      break;
156
0
  }
157
0
  return tvb_captured_length(tvb);
158
0
}
159
160
void
161
proto_register_redback(void)
162
14
{
163
14
  static hf_register_info hf[] = {
164
14
    { &hf_redback_context,
165
14
      { "Context", "redback.context",
166
14
        FT_UINT32, BASE_HEX, NULL, 0x0,
167
14
        NULL, HFILL }
168
14
    },
169
14
    { &hf_redback_flags,
170
14
      { "Flags", "redback.flags",
171
14
        FT_UINT32, BASE_HEX, NULL, 0x0,
172
14
        NULL, HFILL }
173
14
    },
174
14
    { &hf_redback_circuit,
175
14
      { "Circuit", "redback.circuit",
176
14
        FT_UINT64, BASE_HEX, NULL, 0x0,
177
14
        NULL, HFILL }
178
14
    },
179
14
    { &hf_redback_length,
180
14
      { "Length", "redback.length",
181
14
        FT_UINT16, BASE_DEC, NULL, 0x0,
182
14
        NULL, HFILL }
183
14
    },
184
14
    { &hf_redback_protocol,
185
14
      { "Protocol", "redback.protocol",
186
14
        FT_UINT16, BASE_DEC, NULL, 0x0,
187
14
        NULL, HFILL }
188
14
    },
189
14
    { &hf_redback_l3offset,
190
14
      { "Layer 3 Offset", "redback.l3offset",
191
14
        FT_UINT16, BASE_DEC, NULL, 0x0,
192
14
        NULL, HFILL }
193
14
    },
194
14
    { &hf_redback_dataoffset,
195
14
      { "Data Offset", "redback.dataoffset",
196
14
        FT_UINT16, BASE_DEC, NULL, 0x0,
197
14
        NULL, HFILL }
198
14
    },
199
14
    { &hf_redback_padding,
200
14
      { "Padding", "redback.padding",
201
14
        FT_BYTES, BASE_NONE, NULL, 0x0,
202
14
        NULL, HFILL }
203
14
    },
204
14
    { &hf_redback_unknown,
205
14
      { "Unknown", "redback.unknown",
206
14
        FT_BYTES, BASE_NONE, NULL, 0x0,
207
14
        NULL, HFILL }
208
14
    },
209
14
  };
210
211
14
  static int *ett[] = {
212
14
    &ett_redback
213
14
  };
214
215
14
  static ei_register_info ei[] = {
216
14
    { &ei_redback_protocol, { "redback.protocol.unknown", PI_PROTOCOL, PI_WARN, "Unknown Protocol Data", EXPFILL }},
217
14
  };
218
219
14
  expert_module_t* expert_redback;
220
221
14
  proto_redback = proto_register_protocol("Redback", "Redback", "redback");
222
14
  proto_register_field_array(proto_redback, hf, array_length(hf));
223
14
  redback_handle = register_dissector("redback", dissect_redback, proto_redback);
224
225
14
  proto_register_subtree_array(ett, array_length(ett));
226
14
  expert_redback = expert_register_protocol(proto_redback);
227
14
  expert_register_field_array(expert_redback, ei, array_length(ei));
228
14
}
229
230
void
231
proto_reg_handoff_redback(void)
232
14
{
233
14
  osinl_incl_subdissector_table = find_dissector_table("osinl.incl");
234
14
  osinl_excl_subdissector_table = find_dissector_table("osinl.excl");
235
236
14
  ipv4_handle = find_dissector_add_dependency("ip", proto_redback);
237
14
  ipv6_handle = find_dissector_add_dependency("ipv6", proto_redback);
238
14
  ethnofcs_handle = find_dissector_add_dependency("eth_withoutfcs", proto_redback);
239
14
  clnp_handle = find_dissector_add_dependency("clnp", proto_redback);
240
14
  arp_handle = find_dissector_add_dependency("arp", proto_redback);
241
14
  ppp_handle = find_dissector_add_dependency("ppp", proto_redback);
242
14
  ppphdlc_handle = find_dissector_add_dependency("ppp_hdlc", proto_redback);
243
244
14
  dissector_add_uint("wtap_encap", WTAP_ENCAP_REDBACK, redback_handle);
245
14
}
246
247
/*
248
 * Editor modelines  -  https://www.wireshark.org/tools/modelines.html
249
 *
250
 * Local variables:
251
 * c-basic-offset: 8
252
 * tab-width: 8
253
 * indent-tabs-mode: t
254
 * End:
255
 *
256
 * vi: set shiftwidth=8 tabstop=8 noexpandtab:
257
 * :indentSize=8:tabSize=8:noTabs=false:
258
 */