logstash-codec-netflow 3.14.1 → 4.0.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 11eeb7718eb1146533c6b6f1745dfbbd3d267f24
4
- data.tar.gz: 0618d031da52613490941fce6df6c92021791fa8
3
+ metadata.gz: 4d93e056a9df39efb7dff2feb887a661a4231313
4
+ data.tar.gz: f2e47894941ea4090de24a78028e4b6ec4efc3a6
5
5
  SHA512:
6
- metadata.gz: 590fa8a90f09134a83af9a7907393c0f0bf1fa942c850db1a6daa749506e26347dfdd202a4e4a4d8cf078d0322e3510567b0eb00f020fe51f99a150a188df375
7
- data.tar.gz: 5ad744cbb78da117c1b8936a01d1e0fc645feb11da895aa96214564655e4231b192ba52359817e6e26000c6f4190a9dff7676c14343bae5d5c32ca7b225d2acf
6
+ metadata.gz: a5cdc4f265bb0e91fcd0db9ce19e3b678bc04cb640a094742ba45b38b881526a563ba51342a982d377103eb55a9ee89cc455d03481cf4e409a6065166d2a772c
7
+ data.tar.gz: 64e22086639e4595a4b0a3fd988471d5c095b4370046df7d732d03531336bc47a60129c3a57fa267099660951e36f1b99603c04e1b02c431882086b0372b540d
@@ -1,3 +1,7 @@
1
+ ## 4.0.0
2
+
3
+ - Added support for RFC6759 decoding of application_id. **This is a breaking change to the way application_id is decoded. The format changes from e.g. 0:40567 to 0..12356..40567**
4
+
1
5
  ## 3.14.1
2
6
 
3
7
  - Fixes exception when receiving Netflow 9 from H3C devices
@@ -36,6 +36,7 @@ Contributors:
36
36
  * Will Rigby (wrigby)
37
37
  * Yehonatan Devorkin (Devorkin)
38
38
  * Rojuinex
39
+ * Sjaak01
39
40
  * debadair
40
41
  * HenryTheSir
41
42
  * hkshirish
@@ -472,6 +472,29 @@ class LogStash::Codecs::Netflow < LogStash::Codecs::Base
472
472
  field
473
473
  end # def string_field
474
474
 
475
+ def get_rfc6759_application_id_class(field,length)
476
+ case length
477
+ when 2
478
+ field[0] = :Application_Id16
479
+ when 3
480
+ field[0] = :Application_Id24
481
+ when 4
482
+ field[0] = :Application_Id32
483
+ when 5
484
+ field[0] = :Application_Id40
485
+ when 7
486
+ field[0] = :Application_Id56
487
+ when 8
488
+ field[0] = :Application_Id64
489
+ when 9
490
+ field[0] = :Application_Id72
491
+ else
492
+ @logger.warn("Unsupported application_id length encountered, skipping", :field => field, :length => length)
493
+ nil
494
+ end
495
+ field[0]
496
+ end
497
+
475
498
  def netflow_field_for(type, length, template_id)
476
499
  if @netflow_fields.include?(type)
477
500
  field = @netflow_fields[type].clone
@@ -509,23 +532,7 @@ class LogStash::Codecs::Netflow < LogStash::Codecs::Base
509
532
  end
510
533
  field[0] = uint_field(length, field[0])
511
534
  when :application_id
512
- case length
513
- when 2
514
- field[0] = :Application_Id16
515
- when 3
516
- field[0] = :Application_Id24
517
- when 4
518
- field[0] = :Application_Id32
519
- when 5
520
- field[0] = :Application_Id40
521
- when 8
522
- field[0] = :Application_Id64
523
- when 9
524
- field[0] = :Application_Id72
525
- else
526
- @logger.warn("Unsupported application_id length encountered, skipping", :field => field, :length => length)
527
- nil
528
- end
535
+ field[0] = get_rfc6759_application_id_class(field,length)
529
536
  when :skip
530
537
  field += [nil, {:length => length.to_i}]
531
538
  when :string
@@ -573,6 +580,8 @@ class LogStash::Codecs::Netflow < LogStash::Codecs::Base
573
580
  field[0] = uint_field(length, 4)
574
581
  when :uint16
575
582
  field[0] = uint_field(length, 2)
583
+ when :application_id
584
+ field[0] = get_rfc6759_application_id_class(field,length)
576
585
  end
577
586
 
578
587
  @logger.debug("Definition complete", :field => field)
@@ -139,10 +139,11 @@ class Application_Id16 < BinData::Primitive
139
139
  end
140
140
 
141
141
  def get
142
- self.classification_id.to_s + ":" + self.selector_id.to_s
142
+ self.classification_id.to_s + ".." + self.selector_id.to_s
143
143
  end
144
144
  end
145
145
 
146
+
146
147
  class Application_Id24 < BinData::Primitive
147
148
  endian :big
148
149
  uint8 :classification_id
@@ -156,10 +157,11 @@ class Application_Id24 < BinData::Primitive
156
157
  end
157
158
 
158
159
  def get
159
- self.classification_id.to_s + ":" + self.selector_id.to_s
160
+ self.classification_id.to_s + ".." + self.selector_id.to_s
160
161
  end
161
162
  end
162
163
 
164
+
163
165
  class Application_Id32 < BinData::Primitive
164
166
  endian :big
165
167
  uint8 :classification_id
@@ -173,10 +175,11 @@ class Application_Id32 < BinData::Primitive
173
175
  end
174
176
 
175
177
  def get
176
- self.classification_id.to_s + ":" + self.selector_id.to_s
178
+ self.classification_id.to_s + ".." + self.selector_id.to_s
177
179
  end
178
180
  end
179
181
 
182
+
180
183
  class Application_Id40 < BinData::Primitive
181
184
  endian :big
182
185
  uint8 :classification_id
@@ -190,41 +193,130 @@ class Application_Id40 < BinData::Primitive
190
193
  end
191
194
 
192
195
  def get
193
- self.classification_id.to_s + ":" + self.selector_id.to_s
196
+ self.classification_id.to_s + ".." + self.selector_id.to_s
197
+ end
198
+ end
199
+
200
+
201
+ class Appid56PanaL7Pen < BinData::Record
202
+ # RFC6759 chapter 4.1: PANA-L7-PEN
203
+ # This implements the "application ids MAY be encoded in a smaller number of bytes"
204
+ # Used in Application_Id56 choice statement
205
+ endian :big
206
+ uint32 :pen_id
207
+ uint16 :selector_id
208
+ end
209
+
210
+
211
+ class Application_Id56 < BinData::Primitive
212
+ endian :big
213
+ uint8 :classification_id
214
+ choice :selector_id, :selection => :classification_id do
215
+ # for classification engine id 20 we switch to Appid64PanaL7Pen to decode
216
+ appid56_pana_l7_pen 20
217
+ uint48 :default
218
+ end
219
+
220
+ def set(val)
221
+ unless val.nil?
222
+ self.classification_id=val.to_i<<48
223
+ if self.classification_id == 20
224
+ # classification engine id 20 (PANA_L7_PEN) contains a 4-byte PEN:
225
+ self.pen_id = val.to_i-((val.to_i>>48)<<48)>>16
226
+ self.selector_id = val.to_i-((val.to_i>>16)<<16)
227
+ else
228
+ self.selector_id = val.to_i-((val.to_i>>48)<<48)
229
+ end
230
+ end
231
+ end
232
+
233
+ def get
234
+ if self.classification_id == 20
235
+ self.classification_id.to_s + ".." + self.selector_id[:pen_id].to_s + ".." + self.selector_id[:selector_id].to_s
236
+ else
237
+ self.classification_id.to_s + ".." + self.selector_id.to_s
238
+ end
194
239
  end
195
240
  end
196
241
 
242
+
243
+ class Appid64PanaL7Pen < BinData::Record
244
+ # RFC6759 chapter 4.1: PANA-L7-PEN
245
+ # This implements the 3 bytes default selector id length
246
+ # Used in Application_Id64 choice statement
247
+ endian :big
248
+ uint32 :pen_id
249
+ uint24 :selector_id
250
+ end
251
+
197
252
  class Application_Id64 < BinData::Primitive
198
253
  endian :big
199
254
  uint8 :classification_id
200
- uint56 :selector_id
255
+ choice :selector_id, :selection => :classification_id do
256
+ # for classification engine id 20 we switch to Appid64PanaL7Pen to decode
257
+ appid64_pana_l7_pen 20
258
+ uint56 :default
259
+ end
201
260
 
202
261
  def set(val)
203
262
  unless val.nil?
204
263
  self.classification_id=val.to_i<<56
205
- self.selector_id = val.to_i-((val.to_i>>56)<<56)
264
+ if self.classification_id == 20
265
+ # classification engine id 20 (PANA_L7_PEN) contains a 4-byte PEN:
266
+ self.pen_id = val.to_i-((val.to_i>>56)<<56)>>24
267
+ self.selector_id = val.to_i-((val.to_i>>24)<<24)
268
+ else
269
+ self.selector_id = val.to_i-((val.to_i>>56)<<56)
270
+ end
206
271
  end
207
272
  end
208
273
 
209
274
  def get
210
- self.classification_id.to_s + ":" + self.selector_id.to_s
275
+ if self.classification_id == 20
276
+ self.classification_id.to_s + ".." + self.selector_id[:pen_id].to_s + ".." + self.selector_id[:selector_id].to_s
277
+ else
278
+ self.classification_id.to_s + ".." + self.selector_id.to_s
279
+ end
211
280
  end
212
281
  end
213
282
 
283
+ class Appid72PanaL7Pen < BinData::Record
284
+ # RFC6759 chapter 4.1: PANA-L7-PEN
285
+ # This implements the "application ids MAY be encoded with a larger length"
286
+ # Used in Application_Id72 choice statement
287
+ endian :big
288
+ uint32 :pen_id
289
+ uint32 :selector_id
290
+ end
291
+
214
292
  class Application_Id72 < BinData::Primitive
215
293
  endian :big
216
294
  uint8 :classification_id
217
- uint64 :selector_id
295
+ choice :selector_id, :selection => :classification_id do
296
+ # for classification engine id 20 we switch to Appid72PanaL7Pen to decode
297
+ appid72_pana_l7_pen 20
298
+ uint64 :default
299
+ end
218
300
 
219
301
  def set(val)
220
302
  unless val.nil?
221
- self.classification_id=val.to_i<<64
222
- self.selector_id = val.to_i-((val.to_i>>64)<<64)
303
+ self.classification_id = val.to_i<<64
304
+ if self.classification_id == 20
305
+ # classification engine id 20 (PANA_L7_PEN) contains a 4-byte PEN:
306
+ self.pen_id = val.to_i-((val.to_i>>64)<<64)>>32
307
+ self.selector_id = val.to_i-((val.to_i>>32)<<32)
308
+ else
309
+ self.selector_id = val.to_i-((val.to_i>>64)<<64)
310
+ end
223
311
  end
224
312
  end
225
313
 
226
314
  def get
227
- self.classification_id.to_s + ":" + self.selector_id.to_s
315
+ if self.classification_id == 20
316
+ self.classification_id.to_s + ".." + self.selector_id[:pen_id].to_s + ".." + self.selector_id[:selector_id].to_s
317
+ else
318
+ self.classification_id.to_s + ".." + self.selector_id.to_s
319
+ end
228
320
  end
229
321
  end
230
322
 
@@ -1,7 +1,7 @@
1
1
  Gem::Specification.new do |s|
2
2
 
3
3
  s.name = 'logstash-codec-netflow'
4
- s.version = '3.14.1'
4
+ s.version = '4.0.0'
5
5
  s.licenses = ['Apache License (2.0)']
6
6
  s.summary = "Reads Netflow v5, Netflow v9 and IPFIX data"
7
7
  s.description = "This gem is a Logstash plugin required to be installed on top of the Logstash core pipeline using $LS_HOME/bin/logstash-plugin install gemname. This gem is not a stand-alone program"
@@ -1024,8 +1024,6 @@ describe LogStash::Codecs::Netflow do
1024
1024
 
1025
1025
  end
1026
1026
 
1027
-
1028
-
1029
1027
  context "Netflow 9 IE150 IE151" do
1030
1028
  let(:data) do
1031
1029
  packets = []
@@ -1103,6 +1101,66 @@ describe LogStash::Codecs::Netflow do
1103
1101
 
1104
1102
  end
1105
1103
 
1104
+
1105
+ context "Netflow 9 Fortigate FortiOS 54x appid" do
1106
+ let(:data) do
1107
+ packets = []
1108
+ packets << IO.read(File.join(File.dirname(__FILE__), "netflow9_test_fortigate_fortios_542_appid_tpl258-269.dat"), :mode => "rb")
1109
+ packets << IO.read(File.join(File.dirname(__FILE__), "netflow9_test_fortigate_fortios_542_appid_data258_262.dat"), :mode => "rb")
1110
+ end
1111
+
1112
+ let(:json_events) do
1113
+ events = []
1114
+ events << <<-END
1115
+ {
1116
+ "netflow": {
1117
+ "output_snmp": 2,
1118
+ "forwarding_status": {
1119
+ "reason": 0,
1120
+ "status": 1
1121
+ },
1122
+ "xlate_src_port": 45380,
1123
+ "in_pkts": 6,
1124
+ "ipv4_dst_addr": "182.50.136.239",
1125
+ "first_switched": "2018-05-11T00:54:10.999Z",
1126
+ "flowset_id": 262,
1127
+ "l4_src_port": 45380,
1128
+ "xlate_dst_port": 0,
1129
+ "version": 9,
1130
+ "application_id": "20..12356..36660",
1131
+ "flow_seq_num": 350,
1132
+ "ipv4_src_addr": "192.168.100.151",
1133
+ "in_bytes": 748,
1134
+ "protocol": 6,
1135
+ "flow_end_reason": 3,
1136
+ "last_switched": "2018-05-11T00:54:10.999Z",
1137
+ "input_snmp": 8,
1138
+ "out_pkts": 6,
1139
+ "out_bytes": 748,
1140
+ "xlate_src_addr_ipv4": "10.0.0.250",
1141
+ "xlate_dst_addr_ipv4": "0.0.0.0",
1142
+ "l4_dst_port": 80
1143
+ },
1144
+ "@timestamp": "2018-05-11T00:54:11.000Z",
1145
+ "@version": "1"
1146
+ }
1147
+ END
1148
+ events.map{|event| event.gsub(/\s+/, "")}
1149
+ end
1150
+
1151
+ it "should decode raw data" do
1152
+ expect(decode.size).to eq(17)
1153
+ expect(decode[1].get("[netflow][application_id]")).to eq("20..12356..40568")
1154
+ expect(decode[2].get("[netflow][application_id]")).to eq("20..12356..40568")
1155
+ expect(decode[16].get("[netflow][application_id]")).to eq("20..12356..0")
1156
+ end
1157
+
1158
+ it "should serialize to json" do
1159
+ expect(JSON.parse(decode[0].to_json)).to eq(JSON.parse(json_events[0]))
1160
+ end
1161
+
1162
+ end
1163
+
1106
1164
  context "IPFIX Nokia BRAS" do
1107
1165
  let(:data) do
1108
1166
  packets = []
@@ -1352,7 +1410,7 @@ describe LogStash::Codecs::Netflow do
1352
1410
  "l4_src_port": 0,
1353
1411
  "nprobe_proto_name": "\u0000\u00c1\u0000\u0000\u0001\u00ac\u0010\u0000d\u00e4O\u00ef\u00ff\u00ff\u00fa\u0007",
1354
1412
  "version": 9,
1355
- "application_id": "0:82",
1413
+ "application_id": "0..82",
1356
1414
  "flow_seq_num": 2,
1357
1415
  "ipv4_src_addr": "0.0.0.0",
1358
1416
  "protocol": 0,
@@ -1372,7 +1430,7 @@ describe LogStash::Codecs::Netflow do
1372
1430
  it "should decode raw data" do
1373
1431
  expect(decode.size).to eq(1)
1374
1432
  expect(decode[0].get("[netflow][nprobe_proto]")).to eq(82)
1375
- expect(decode[0].get("[netflow][application_id]")).to eq("0:82")
1433
+ expect(decode[0].get("[netflow][application_id]")).to eq("0..82")
1376
1434
  expect(decode[0].get("[netflow][in_bytes]")).to eq(82)
1377
1435
  end
1378
1436
 
@@ -2291,7 +2349,7 @@ describe LogStash::Codecs::Netflow do
2291
2349
  "application_description": "ARGUS",
2292
2350
  "flowset_id": 260,
2293
2351
  "version": 9,
2294
- "application_id": "1:13"
2352
+ "application_id": "1..13"
2295
2353
  },
2296
2354
  "@timestamp": "2017-02-14T11:09:59.000Z",
2297
2355
  "@version": "1"
@@ -2302,7 +2360,7 @@ describe LogStash::Codecs::Netflow do
2302
2360
 
2303
2361
  it "should decode raw data" do
2304
2362
  expect(decode.size).to eq(15)
2305
- expect(decode[14].get("[netflow][application_id]")).to eq("1:13")
2363
+ expect(decode[14].get("[netflow][application_id]")).to eq("1..13")
2306
2364
  expect(decode[14].get("[netflow][application_description]")).to eq("ARGUS")
2307
2365
  end
2308
2366
 
@@ -2345,7 +2403,7 @@ describe LogStash::Codecs::Netflow do
2345
2403
  "udp_dst_port": 161,
2346
2404
  "src_mask": 0,
2347
2405
  "version": 9,
2348
- "application_id": "5:38",
2406
+ "application_id": "5..38",
2349
2407
  "flow_seq_num": 1509134,
2350
2408
  "ipv4_src_addr": "10.10.172.60",
2351
2409
  "in_src_mac": "00:18:19:9e:6c:01",
@@ -2362,7 +2420,7 @@ describe LogStash::Codecs::Netflow do
2362
2420
 
2363
2421
  it "should decode raw data" do
2364
2422
  expect(decode.size).to eq(5)
2365
- expect(decode[4].get("[netflow][application_id]")).to eq("5:38")
2423
+ expect(decode[4].get("[netflow][application_id]")).to eq("5..38")
2366
2424
  end
2367
2425
 
2368
2426
  it "should serialize to json" do
@@ -2388,7 +2446,7 @@ describe LogStash::Codecs::Netflow do
2388
2446
  "staMacAddress": "34:02:86:75:c0:51",
2389
2447
  "flowset_id": 261,
2390
2448
  "version": 9,
2391
- "application_id": "13:431",
2449
+ "application_id": "13..431",
2392
2450
  "flow_seq_num": 78,
2393
2451
  "in_bytes": 80973880,
2394
2452
  "postIpDiffServCodePoint": 0,
@@ -2405,7 +2463,7 @@ describe LogStash::Codecs::Netflow do
2405
2463
 
2406
2464
  it "should decode raw data" do
2407
2465
  expect(decode.size).to eq(19)
2408
- expect(decode[18].get("[netflow][application_id]")).to eq("13:431")
2466
+ expect(decode[18].get("[netflow][application_id]")).to eq("13..431")
2409
2467
  end
2410
2468
 
2411
2469
  it "should serialize to json" do
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: logstash-codec-netflow
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.14.1
4
+ version: 4.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Elastic
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-05-23 00:00:00.000000000 Z
11
+ date: 2018-05-31 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  requirement: !ruby/object:Gem::Requirement
@@ -138,6 +138,8 @@ files:
138
138
  - spec/codecs/netflow9_test_fortigate_fortios_521_data256.dat
139
139
  - spec/codecs/netflow9_test_fortigate_fortios_521_data257.dat
140
140
  - spec/codecs/netflow9_test_fortigate_fortios_521_tpl.dat
141
+ - spec/codecs/netflow9_test_fortigate_fortios_542_appid_data258_262.dat
142
+ - spec/codecs/netflow9_test_fortigate_fortios_542_appid_tpl258-269.dat
141
143
  - spec/codecs/netflow9_test_h3c_data3281.dat
142
144
  - spec/codecs/netflow9_test_h3c_tpl3281.dat
143
145
  - spec/codecs/netflow9_test_huawei_netstream_data.dat
@@ -254,6 +256,8 @@ test_files:
254
256
  - spec/codecs/netflow9_test_fortigate_fortios_521_data256.dat
255
257
  - spec/codecs/netflow9_test_fortigate_fortios_521_data257.dat
256
258
  - spec/codecs/netflow9_test_fortigate_fortios_521_tpl.dat
259
+ - spec/codecs/netflow9_test_fortigate_fortios_542_appid_data258_262.dat
260
+ - spec/codecs/netflow9_test_fortigate_fortios_542_appid_tpl258-269.dat
257
261
  - spec/codecs/netflow9_test_h3c_data3281.dat
258
262
  - spec/codecs/netflow9_test_h3c_tpl3281.dat
259
263
  - spec/codecs/netflow9_test_huawei_netstream_data.dat