suricata
output-json.c
Go to the documentation of this file.
1 /* Copyright (C) 2007-2023 Open Information Security Foundation
2  *
3  * You can copy, redistribute or modify this Program under the terms of
4  * the GNU General Public License version 2 as published by the Free
5  * Software Foundation.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * version 2 along with this program; if not, write to the Free Software
14  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
15  * 02110-1301, USA.
16  */
17 
18 /**
19  * \file
20  *
21  * \author Tom DeCanio <td@npulsetech.com>
22  *
23  * Logs detection and monitoring events in JSON format.
24  *
25  */
26 
27 #include "suricata-common.h"
28 #include "flow.h"
29 #include "conf.h"
30 
31 #include "util-debug.h"
32 #include "util-var-name.h"
33 #include "util-macset.h"
34 
35 #include "util-unittest-helper.h"
36 
37 #include "detect-engine.h"
39 #include "util-syslog.h"
40 
41 /* Internal output plugins */
42 #include "output-eve-syslog.h"
43 #include "output-eve-null.h"
44 
45 #include "output.h"
46 #include "output-json.h"
47 
48 #include "util-byte.h"
49 #include "util-print.h"
50 #include "util-proto-name.h"
51 #include "util-buffer.h"
52 #include "util-logopenfile.h"
53 #include "util-log-redis.h"
54 #include "util-device-private.h"
55 #include "util-validate.h"
56 
57 #include "flow-var.h"
58 #include "flow-bit.h"
59 #include "flow-storage.h"
60 
62 
63 #define DEFAULT_LOG_FILENAME "eve.json"
64 #define MODULE_NAME "OutputJSON"
65 
66 #define MAX_JSON_SIZE 2048
67 
68 static void OutputJsonDeInitCtx(OutputCtx *);
69 static void CreateEveCommunityFlowId(SCJsonBuilder *js, const Flow *f, const uint16_t seed);
70 static int CreateJSONEther(
71  SCJsonBuilder *parent, const Packet *p, const Flow *f, enum SCOutputJsonLogDirection dir);
72 
73 static const char *TRAFFIC_ID_PREFIX = "traffic/id/";
74 static const char *TRAFFIC_LABEL_PREFIX = "traffic/label/";
75 static size_t traffic_id_prefix_len = 0;
76 static size_t traffic_label_prefix_len = 0;
77 
79 
80 void OutputJsonRegister (void)
81 {
83 
84  traffic_id_prefix_len = strlen(TRAFFIC_ID_PREFIX);
85  traffic_label_prefix_len = strlen(TRAFFIC_LABEL_PREFIX);
86 
87  // Register output file types that use the new eve filetype registration
88  // API.
91 }
92 
93 json_t *SCJsonString(const char *val)
94 {
95  if (val == NULL){
96  return NULL;
97  }
98  json_t * retval = json_string(val);
99  char retbuf[MAX_JSON_SIZE] = {0};
100  if (retval == NULL) {
101  uint32_t u = 0;
102  uint32_t offset = 0;
103  for (u = 0; u < strlen(val); u++) {
104  if (isprint(val[u])) {
105  PrintBufferData(retbuf, &offset, MAX_JSON_SIZE-1, "%c",
106  val[u]);
107  } else {
109  "\\x%02X", val[u]);
110  }
111  }
112  retbuf[offset] = '\0';
113  retval = json_string(retbuf);
114  }
115  return retval;
116 }
117 
118 /* Default Sensor ID value */
119 static int64_t sensor_id = -1; /* -1 = not defined */
120 
121 void EveFileInfo(SCJsonBuilder *jb, const File *ff, const uint64_t tx_id, const uint16_t flags)
122 {
123  SCJbSetStringFromBytes(jb, "filename", ff->name, ff->name_len);
124 
125  if (ff->sid_cnt > 0) {
126  SCJbOpenArray(jb, "sid");
127  for (uint32_t i = 0; ff->sid != NULL && i < ff->sid_cnt; i++) {
128  SCJbAppendUint(jb, ff->sid[i]);
129  }
130  SCJbClose(jb);
131  }
132 
133 #ifdef HAVE_MAGIC
134  if (ff->magic)
135  SCJbSetString(jb, "magic", (char *)ff->magic);
136 #endif
137  SCJbSetBool(jb, "gaps", ff->flags & FILE_HAS_GAPS);
138  switch (ff->state) {
139  case FILE_STATE_CLOSED:
140  JB_SET_STRING(jb, "state", "CLOSED");
141  if (ff->flags & FILE_MD5) {
142  SCJbSetHex(jb, "md5", (uint8_t *)ff->md5, (uint32_t)sizeof(ff->md5));
143  }
144  if (ff->flags & FILE_SHA1) {
145  SCJbSetHex(jb, "sha1", (uint8_t *)ff->sha1, (uint32_t)sizeof(ff->sha1));
146  }
147  break;
149  JB_SET_STRING(jb, "state", "TRUNCATED");
150  break;
151  case FILE_STATE_ERROR:
152  JB_SET_STRING(jb, "state", "ERROR");
153  break;
154  default:
155  JB_SET_STRING(jb, "state", "UNKNOWN");
156  break;
157  }
158 
159  if (ff->flags & FILE_SHA256) {
160  SCJbSetHex(jb, "sha256", (uint8_t *)ff->sha256, (uint32_t)sizeof(ff->sha256));
161  }
162 
163  if (flags & FILE_STORED) {
164  JB_SET_TRUE(jb, "stored");
165  SCJbSetUint(jb, "file_id", ff->file_store_id);
166  } else {
167  JB_SET_FALSE(jb, "stored");
168  if (flags & FILE_STORE) {
169  JB_SET_TRUE(jb, "storing");
170  }
171  }
172 
173  SCJbSetUint(jb, "size", FileTrackedSize(ff));
174  if (ff->end > 0) {
175  SCJbSetUint(jb, "start", ff->start);
176  SCJbSetUint(jb, "end", ff->end);
177  }
178  SCJbSetUint(jb, "tx_id", tx_id);
179 }
180 
181 static void EveAddPacketVars(const Packet *p, SCJsonBuilder *js_vars)
182 {
183  if (p == NULL || p->pktvar == NULL) {
184  return;
185  }
186  PktVar *pv = p->pktvar;
187  bool open = false;
188  while (pv != NULL) {
189  if (pv->key || pv->id > 0) {
190  if (!open) {
191  SCJbOpenArray(js_vars, "pktvars");
192  open = true;
193  }
194  SCJbStartObject(js_vars);
195 
196  if (pv->key != NULL) {
197  uint32_t offset = 0;
198  DEBUG_VALIDATE_BUG_ON(pv->key_len > UINT16_MAX);
199  uint8_t keybuf[pv->key_len + 1];
200  PrintStringsToBuffer(keybuf, &offset, pv->key_len + 1, pv->key, pv->key_len);
201  SCJbSetPrintAsciiString(js_vars, (char *)keybuf, pv->value, pv->value_len);
202  } else {
203  const char *varname = VarNameStoreLookupById(pv->id, VAR_TYPE_PKT_VAR);
204  SCJbSetPrintAsciiString(js_vars, varname, pv->value, pv->value_len);
205  }
206  SCJbClose(js_vars);
207  }
208  pv = pv->next;
209  }
210  if (open) {
211  SCJbClose(js_vars);
212  }
213 }
214 
215 /**
216  * \brief Check if string s has prefix prefix.
217  *
218  * \retval true if string has prefix
219  * \retval false if string does not have prefix
220  *
221  * TODO: Move to file with other string handling functions.
222  */
223 static bool SCStringHasPrefix(const char *s, const char *prefix)
224 {
225  return strncmp(s, prefix, strlen(prefix)) == 0;
226 }
227 
228 static void EveAddFlowVars(const Flow *f, SCJsonBuilder *js_root, SCJsonBuilder **js_traffic)
229 {
230  if (f == NULL || f->flowvar == NULL) {
231  return;
232  }
233  SCJsonBuilder *js_flowvars = NULL;
234  SCJsonBuilder *js_traffic_id = NULL;
235  SCJsonBuilder *js_traffic_label = NULL;
236  SCJsonBuilder *js_flowints = NULL;
237  SCJsonBuilder *js_entropyvals = NULL;
238  SCJsonBuilder *js_flowbits = NULL;
239  GenericVar *gv = f->flowvar;
240  while (gv != NULL) {
241  if (gv->type == DETECT_FLOWVAR || gv->type == DETECT_FLOWINT) {
242  FlowVar *fv = (FlowVar *)gv;
243  if (fv->datatype == FLOWVAR_TYPE_STR && fv->key == NULL) {
244  const char *varname = VarNameStoreLookupById(fv->idx,
246  if (varname) {
247  if (js_flowvars == NULL) {
248  js_flowvars = SCJbNewArray();
249  if (js_flowvars == NULL)
250  break;
251  }
252 
253  SCJbStartObject(js_flowvars);
254  SCJbSetPrintAsciiString(
255  js_flowvars, varname, fv->data.fv_str.value, fv->data.fv_str.value_len);
256  SCJbClose(js_flowvars);
257  }
258  } else if (fv->datatype == FLOWVAR_TYPE_STR && fv->key != NULL) {
259  if (js_flowvars == NULL) {
260  js_flowvars = SCJbNewArray();
261  if (js_flowvars == NULL)
262  break;
263  }
264 
265  // fv->keylen is uint16
266  uint8_t keybuf[fv->keylen + 1];
267  uint32_t offset = 0;
268  PrintStringsToBuffer(keybuf, &offset, fv->keylen + 1, fv->key, fv->keylen);
269 
270  SCJbStartObject(js_flowvars);
271  SCJbSetPrintAsciiString(js_flowvars, (const char *)keybuf, fv->data.fv_str.value,
272  fv->data.fv_str.value_len);
273  SCJbClose(js_flowvars);
274  } else if (fv->datatype == FLOWVAR_TYPE_FLOAT) {
275  const char *varname = VarNameStoreLookupById(fv->idx, VAR_TYPE_FLOW_FLOAT);
276  if (varname) {
277  if (js_entropyvals == NULL) {
278  js_entropyvals = SCJbNewObject();
279  if (js_entropyvals == NULL)
280  break;
281  }
282  SCJbSetFloat(js_entropyvals, varname, fv->data.fv_float.value);
283  }
284 
285  } else if (fv->datatype == FLOWVAR_TYPE_INT) {
286  const char *varname = VarNameStoreLookupById(fv->idx,
288  if (varname) {
289  if (js_flowints == NULL) {
290  js_flowints = SCJbNewObject();
291  if (js_flowints == NULL)
292  break;
293  }
294  SCJbSetUint(js_flowints, varname, fv->data.fv_int.value);
295  }
296  }
297  } else if (gv->type == DETECT_FLOWBITS) {
298  FlowBit *fb = (FlowBit *)gv;
299  const char *varname = VarNameStoreLookupById(fb->idx,
301  if (varname) {
302  if (SCStringHasPrefix(varname, TRAFFIC_ID_PREFIX)) {
303  if (js_traffic_id == NULL) {
304  js_traffic_id = SCJbNewArray();
305  if (unlikely(js_traffic_id == NULL)) {
306  break;
307  }
308  }
309  SCJbAppendString(js_traffic_id, &varname[traffic_id_prefix_len]);
310  } else if (SCStringHasPrefix(varname, TRAFFIC_LABEL_PREFIX)) {
311  if (js_traffic_label == NULL) {
312  js_traffic_label = SCJbNewArray();
313  if (unlikely(js_traffic_label == NULL)) {
314  break;
315  }
316  }
317  SCJbAppendString(js_traffic_label, &varname[traffic_label_prefix_len]);
318  } else {
319  if (js_flowbits == NULL) {
320  js_flowbits = SCJbNewArray();
321  if (unlikely(js_flowbits == NULL))
322  break;
323  }
324  SCJbAppendString(js_flowbits, varname);
325  }
326  }
327  }
328  gv = gv->next;
329  }
330  if (js_flowbits) {
331  SCJbClose(js_flowbits);
332  SCJbSetObject(js_root, "flowbits", js_flowbits);
333  SCJbFree(js_flowbits);
334  }
335  if (js_flowints) {
336  SCJbClose(js_flowints);
337  SCJbSetObject(js_root, "flowints", js_flowints);
338  SCJbFree(js_flowints);
339  }
340  if (js_entropyvals) {
341  SCJbClose(js_entropyvals);
342  SCJbSetObject(js_root, "entropy", js_entropyvals);
343  SCJbFree(js_entropyvals);
344  }
345  if (js_flowvars) {
346  SCJbClose(js_flowvars);
347  SCJbSetObject(js_root, "flowvars", js_flowvars);
348  SCJbFree(js_flowvars);
349  }
350 
351  if (js_traffic_id != NULL || js_traffic_label != NULL) {
352  *js_traffic = SCJbNewObject();
353  if (likely(*js_traffic != NULL)) {
354  if (js_traffic_id != NULL) {
355  SCJbClose(js_traffic_id);
356  SCJbSetObject(*js_traffic, "id", js_traffic_id);
357  SCJbFree(js_traffic_id);
358  }
359  if (js_traffic_label != NULL) {
360  SCJbClose(js_traffic_label);
361  SCJbSetObject(*js_traffic, "label", js_traffic_label);
362  SCJbFree(js_traffic_label);
363  }
364  SCJbClose(*js_traffic);
365  }
366  }
367 }
368 
369 void EveAddMetadata(const Packet *p, const Flow *f, SCJsonBuilder *js)
370 {
371  if ((p && p->pktvar) || (f && f->flowvar)) {
372  SCJsonBuilder *js_vars = SCJbNewObject();
373  if (js_vars) {
374  if (f && f->flowvar) {
375  SCJsonBuilder *js_traffic = NULL;
376  EveAddFlowVars(f, js_vars, &js_traffic);
377  if (js_traffic != NULL) {
378  SCJbSetObject(js, "traffic", js_traffic);
379  SCJbFree(js_traffic);
380  }
381  }
382  if (p && p->pktvar) {
383  EveAddPacketVars(p, js_vars);
384  }
385  SCJbClose(js_vars);
386  SCJbSetObject(js, "metadata", js_vars);
387  SCJbFree(js_vars);
388  }
389  }
390 }
391 
392 void EveAddCommonOptions(const OutputJsonCommonSettings *cfg, const Packet *p, const Flow *f,
394 {
395  if (cfg->include_suricata_version) {
396  SCJbSetString(js, "suricata_version", PROG_VER);
397  }
398  if (cfg->include_metadata) {
399  EveAddMetadata(p, f, js);
400  }
401  if (cfg->include_ethernet) {
402  CreateJSONEther(js, p, f, dir);
403  }
404  if (cfg->include_community_id && f != NULL) {
405  CreateEveCommunityFlowId(js, f, cfg->community_id_seed);
406  }
407  if (f != NULL && f->tenant_id > 0) {
408  SCJbSetUint(js, "tenant_id", f->tenant_id);
409  }
410 }
411 
412 /**
413  * \brief Jsonify a packet
414  *
415  * \param p Packet
416  * \param js JSON object
417  * \param max_length If non-zero, restricts the number of packet data bytes handled.
418  */
419 void EvePacket(const Packet *p, SCJsonBuilder *js, uint32_t max_length)
420 {
421  uint32_t max_len = max_length == 0 ? GET_PKT_LEN(p) : max_length;
422  SCJbSetBase64(js, "packet", GET_PKT_DATA(p), max_len);
423 
424  if (!SCJbOpenObject(js, "packet_info")) {
425  return;
426  }
427  if (!SCJbSetUint(js, "linktype", p->datalink)) {
428  SCJbClose(js);
429  return;
430  }
431 
432  const char *dl_name = DatalinkValueToName(p->datalink);
433 
434  // Intentionally ignore the return value from SCJbSetString and proceed
435  // so the jb object is closed
436  (void)SCJbSetString(js, "linktype_name", dl_name == NULL ? "n/a" : dl_name);
437 
438  SCJbClose(js);
439 }
440 
441 /** \brief jsonify tcp flags field
442  * Only add 'true' fields in an attempt to keep things reasonably compact.
443  */
444 void EveTcpFlags(const uint8_t flags, SCJsonBuilder *js)
445 {
446  if (flags & TH_SYN)
447  JB_SET_TRUE(js, "syn");
448  if (flags & TH_FIN)
449  JB_SET_TRUE(js, "fin");
450  if (flags & TH_RST)
451  JB_SET_TRUE(js, "rst");
452  if (flags & TH_PUSH)
453  JB_SET_TRUE(js, "psh");
454  if (flags & TH_ACK)
455  JB_SET_TRUE(js, "ack");
456  if (flags & TH_URG)
457  JB_SET_TRUE(js, "urg");
458  if (flags & TH_ECN)
459  JB_SET_TRUE(js, "ecn");
460  if (flags & TH_CWR)
461  JB_SET_TRUE(js, "cwr");
462 }
463 
466 {
467  Port sp, dp;
468 
469  const void *src_ip = NULL;
470  const void *dst_ip = NULL;
471 
472  switch (dir) {
473  case LOG_DIR_PACKET:
474  if (PacketIsIPv4(p)) {
475  src_ip = GET_IPV4_SRC_ADDR_PTR(p);
476  dst_ip = GET_IPV4_DST_ADDR_PTR(p);
477  } else if (PacketIsIPv6(p)) {
478  src_ip = GET_IPV6_SRC_ADDR(p);
479  dst_ip = GET_IPV6_DST_ADDR(p);
480  } else {
481  /* Not an IP packet so don't do anything */
482  return;
483  }
484  sp = p->sp;
485  dp = p->dp;
486  break;
487  case LOG_DIR_FLOW:
489  if ((PKT_IS_TOSERVER(p))) {
490  if (PacketIsIPv4(p)) {
491  src_ip = GET_IPV4_SRC_ADDR_PTR(p);
492  dst_ip = GET_IPV4_DST_ADDR_PTR(p);
493  } else if (PacketIsIPv6(p)) {
494  src_ip = GET_IPV6_SRC_ADDR(p);
495  dst_ip = GET_IPV6_DST_ADDR(p);
496  }
497  sp = p->sp;
498  dp = p->dp;
499  } else {
500  if (PacketIsIPv4(p)) {
501  src_ip = GET_IPV4_DST_ADDR_PTR(p);
502  dst_ip = GET_IPV4_SRC_ADDR_PTR(p);
503  } else if (PacketIsIPv6(p)) {
504  src_ip = GET_IPV6_DST_ADDR(p);
505  dst_ip = GET_IPV6_SRC_ADDR(p);
506  }
507  sp = p->dp;
508  dp = p->sp;
509  }
510  break;
512  if ((PKT_IS_TOCLIENT(p))) {
513  if (PacketIsIPv4(p)) {
514  src_ip = GET_IPV4_SRC_ADDR_PTR(p);
515  dst_ip = GET_IPV4_DST_ADDR_PTR(p);
516  } else if (PacketIsIPv6(p)) {
517  src_ip = GET_IPV6_SRC_ADDR(p);
518  dst_ip = GET_IPV6_DST_ADDR(p);
519  }
520  sp = p->sp;
521  dp = p->dp;
522  } else {
523  if (PacketIsIPv4(p)) {
524  src_ip = GET_IPV4_DST_ADDR_PTR(p);
525  dst_ip = GET_IPV4_SRC_ADDR_PTR(p);
526  } else if (PacketIsIPv6(p)) {
527  src_ip = GET_IPV6_DST_ADDR(p);
528  dst_ip = GET_IPV6_SRC_ADDR(p);
529  }
530  sp = p->dp;
531  dp = p->sp;
532  }
533  break;
534  default:
536  return;
537  }
538 
539  if (PacketIsIPv4(p)) {
540  PrintInet(AF_INET, (const void *)src_ip, addr->src_ip, JSON_ADDR_LEN);
541  PrintInet(AF_INET, (const void *)dst_ip, addr->dst_ip, JSON_ADDR_LEN);
542  } else if (PacketIsIPv6(p)) {
543  PrintInetIPv6((const void *)src_ip, addr->src_ip, sizeof(addr->src_ip), cfg->compress_ipv6);
544  PrintInetIPv6((const void *)dst_ip, addr->dst_ip, sizeof(addr->dst_ip), cfg->compress_ipv6);
545  }
546 
547  switch (p->proto) {
548  case IPPROTO_UDP:
549  case IPPROTO_TCP:
550  case IPPROTO_SCTP:
551  addr->sp = sp;
552  addr->dp = dp;
553  addr->log_port = true;
554  break;
555  default:
556  addr->log_port = false;
557  break;
558  }
559 
560  if (SCProtoNameValid(PacketGetIPProto(p))) {
561  strlcpy(addr->proto, known_proto[PacketGetIPProto(p)], sizeof(addr->proto));
562  } else {
563  snprintf(addr->proto, sizeof(addr->proto), "%" PRIu32, PacketGetIPProto(p));
564  }
565 }
566 
567 #define COMMUNITY_ID_BUF_SIZE 64
568 
569 static bool CalculateCommunityFlowIdv4(const Flow *f,
570  const uint16_t seed, unsigned char *base64buf)
571 {
572  struct {
573  uint16_t seed;
574  uint32_t src;
575  uint32_t dst;
576  uint8_t proto;
577  uint8_t pad0;
578  uint16_t sp;
579  uint16_t dp;
580  } __attribute__((__packed__)) ipv4;
581 
582  uint32_t src = f->src.addr_data32[0];
583  uint32_t dst = f->dst.addr_data32[0];
584  uint16_t sp = f->sp;
585  if (f->proto == IPPROTO_ICMP)
586  sp = f->icmp_s.type;
587  sp = htons(sp);
588  uint16_t dp = f->dp;
589  if (f->proto == IPPROTO_ICMP)
590  dp = f->icmp_d.type;
591  dp = htons(dp);
592 
593  ipv4.seed = htons(seed);
594  if (ntohl(src) < ntohl(dst) || (src == dst && ntohs(sp) < ntohs(dp))) {
595  ipv4.src = src;
596  ipv4.dst = dst;
597  ipv4.sp = sp;
598  ipv4.dp = dp;
599  } else {
600  ipv4.src = dst;
601  ipv4.dst = src;
602  ipv4.sp = dp;
603  ipv4.dp = sp;
604  }
605  ipv4.proto = f->proto;
606  ipv4.pad0 = 0;
607 
608  uint8_t hash[20];
609  if (SCSha1HashBuffer((const uint8_t *)&ipv4, sizeof(ipv4), hash, sizeof(hash)) == 1) {
610  strlcpy((char *)base64buf, "1:", COMMUNITY_ID_BUF_SIZE);
611  unsigned long out_len = COMMUNITY_ID_BUF_SIZE - 2;
612  if (SCBase64Encode(hash, sizeof(hash), base64buf + 2, &out_len) == SC_BASE64_OK) {
613  return true;
614  }
615  }
616  return false;
617 }
618 
619 static bool CalculateCommunityFlowIdv6(const Flow *f,
620  const uint16_t seed, unsigned char *base64buf)
621 {
622  struct {
623  uint16_t seed;
624  uint32_t src[4];
625  uint32_t dst[4];
626  uint8_t proto;
627  uint8_t pad0;
628  uint16_t sp;
629  uint16_t dp;
630  } __attribute__((__packed__)) ipv6;
631 
632  uint16_t sp = f->sp;
633  if (f->proto == IPPROTO_ICMPV6)
634  sp = f->icmp_s.type;
635  sp = htons(sp);
636  uint16_t dp = f->dp;
637  if (f->proto == IPPROTO_ICMPV6)
638  dp = f->icmp_d.type;
639  dp = htons(dp);
640 
641  ipv6.seed = htons(seed);
642  int cmp_r = memcmp(&f->src, &f->dst, sizeof(f->src));
643  if ((cmp_r < 0) || (cmp_r == 0 && ntohs(sp) < ntohs(dp))) {
644  memcpy(&ipv6.src, &f->src.addr_data32, 16);
645  memcpy(&ipv6.dst, &f->dst.addr_data32, 16);
646  ipv6.sp = sp;
647  ipv6.dp = dp;
648  } else {
649  memcpy(&ipv6.src, &f->dst.addr_data32, 16);
650  memcpy(&ipv6.dst, &f->src.addr_data32, 16);
651  ipv6.sp = dp;
652  ipv6.dp = sp;
653  }
654  ipv6.proto = f->proto;
655  ipv6.pad0 = 0;
656 
657  uint8_t hash[20];
658  if (SCSha1HashBuffer((const uint8_t *)&ipv6, sizeof(ipv6), hash, sizeof(hash)) == 1) {
659  strlcpy((char *)base64buf, "1:", COMMUNITY_ID_BUF_SIZE);
660  unsigned long out_len = COMMUNITY_ID_BUF_SIZE - 2;
661  if (SCBase64Encode(hash, sizeof(hash), base64buf + 2, &out_len) == SC_BASE64_OK) {
662  return true;
663  }
664  }
665  return false;
666 }
667 
668 static void CreateEveCommunityFlowId(SCJsonBuilder *js, const Flow *f, const uint16_t seed)
669 {
670  unsigned char buf[COMMUNITY_ID_BUF_SIZE];
671  if (f->flags & FLOW_IPV4) {
672  if (CalculateCommunityFlowIdv4(f, seed, buf)) {
673  SCJbSetString(js, "community_id", (const char *)buf);
674  }
675  } else if (f->flags & FLOW_IPV6) {
676  if (CalculateCommunityFlowIdv6(f, seed, buf)) {
677  SCJbSetString(js, "community_id", (const char *)buf);
678  }
679  }
680 }
681 
683 {
684  if (f == NULL) {
685  return;
686  }
687  uint64_t flow_id = FlowGetId(f);
688  SCJbSetUint(js, "flow_id", flow_id);
689  if (f->parent_id) {
690  SCJbSetUint(js, "parent_id", f->parent_id);
691  }
692 }
693 
694 void JSONFormatAndAddMACAddr(SCJsonBuilder *js, const char *key, const uint8_t *val, bool is_array)
695 {
696  char eth_addr[19];
697  (void) snprintf(eth_addr, 19, "%02x:%02x:%02x:%02x:%02x:%02x",
698  val[0], val[1], val[2], val[3], val[4], val[5]);
699  if (is_array) {
700  SCJbAppendString(js, eth_addr);
701  } else {
702  SCJbSetString(js, key, eth_addr);
703  }
704 }
705 
706 /* only required to traverse the MAC address set */
707 typedef struct JSONMACAddrInfo {
710 
711 static int MacSetIterateToJSON(uint8_t *val, MacSetSide side, void *data)
712 {
713  JSONMACAddrInfo *info = (JSONMACAddrInfo*) data;
714  if (side == MAC_SET_DST) {
715  JSONFormatAndAddMACAddr(info->dst, NULL, val, true);
716  } else {
717  JSONFormatAndAddMACAddr(info->src, NULL, val, true);
718  }
719  return 0;
720 }
721 
722 static int CreateJSONEther(
723  SCJsonBuilder *js, const Packet *p, const Flow *f, enum SCOutputJsonLogDirection dir)
724 {
725  if (p != NULL) {
726  /* this is a packet context, so we need to add scalar fields */
727  if (PacketIsEthernet(p)) {
728  const EthernetHdr *ethh = PacketGetEthernet(p);
729  SCJbOpenObject(js, "ether");
730  SCJbSetUint(js, "ether_type", SCNtohs(ethh->eth_type));
731  const uint8_t *src;
732  const uint8_t *dst;
733  switch (dir) {
735  // fallthrough
736  case LOG_DIR_FLOW:
737  if (PKT_IS_TOCLIENT(p)) {
738  src = ethh->eth_dst;
739  dst = ethh->eth_src;
740  } else {
741  src = ethh->eth_src;
742  dst = ethh->eth_dst;
743  }
744  break;
746  if (PKT_IS_TOSERVER(p)) {
747  src = ethh->eth_dst;
748  dst = ethh->eth_src;
749  } else {
750  src = ethh->eth_src;
751  dst = ethh->eth_dst;
752  }
753  break;
754  case LOG_DIR_PACKET:
755  default:
756  src = ethh->eth_src;
757  dst = ethh->eth_dst;
758  break;
759  }
760  JSONFormatAndAddMACAddr(js, "src_mac", src, false);
761  JSONFormatAndAddMACAddr(js, "dest_mac", dst, false);
762  SCJbClose(js);
763  } else if (f != NULL) {
764  /* When pseudopackets do not have associated ethernet metadata,
765  use the first set of mac addresses stored with their flow.
766  The first set of macs should come from the flow's first packet,
767  providing the most fitting representation of the event's ethernet. */
769  if (ms != NULL && MacSetSize(ms) > 0) {
770  uint8_t *src = MacSetGetFirst(ms, MAC_SET_SRC);
771  uint8_t *dst = MacSetGetFirst(ms, MAC_SET_DST);
772  if (dst != NULL && src != NULL) {
773  SCJbOpenObject(js, "ether");
774  JSONFormatAndAddMACAddr(js, "src_mac", src, false);
775  JSONFormatAndAddMACAddr(js, "dest_mac", dst, false);
776  SCJbClose(js);
777  }
778  }
779  }
780  } else if (f != NULL) {
781  /* we are creating an ether object in a flow context, so we need to
782  append to arrays */
784  if (ms != NULL && MacSetSize(ms) > 0) {
785  SCJbOpenObject(js, "ether");
786  JSONMACAddrInfo info;
787  info.dst = SCJbNewArray();
788  info.src = SCJbNewArray();
789  int ret = MacSetForEach(ms, MacSetIterateToJSON, &info);
790  if (unlikely(ret != 0)) {
791  /* should not happen, JSONFlowAppendMACAddrs is sane */
792  SCJbFree(info.dst);
793  SCJbFree(info.src);
794  SCJbClose(js);
795  return ret;
796  }
797  SCJbClose(info.dst);
798  SCJbClose(info.src);
799  /* case is handling netflow too so may need to revert */
800  if (dir == LOG_DIR_FLOW_TOCLIENT) {
801  SCJbSetObject(js, "dest_macs", info.src);
802  SCJbSetObject(js, "src_macs", info.dst);
803  } else {
805  SCJbSetObject(js, "dest_macs", info.dst);
806  SCJbSetObject(js, "src_macs", info.src);
807  }
808  SCJbFree(info.dst);
809  SCJbFree(info.src);
810  SCJbClose(js);
811  }
812  }
813  return 0;
814 }
815 
817  const char *event_type, JsonAddrInfo *addr, OutputJsonCtx *eve_ctx)
818 {
819  char timebuf[64];
820  const Flow *f = (const Flow *)p->flow;
821 
822  SCJsonBuilder *js = SCJbNewObject();
823  if (unlikely(js == NULL)) {
824  return NULL;
825  }
826 
827  CreateIsoTimeString(p->ts, timebuf, sizeof(timebuf));
828 
829  SCJbSetString(js, "timestamp", timebuf);
830 
831  CreateEveFlowId(js, f);
832 
833  /* sensor id */
834  if (sensor_id >= 0) {
835  SCJbSetUint(js, "sensor_id", sensor_id);
836  }
837 
838  /* input interface */
840  if (dev) {
841  SCJbSetString(js, "in_iface", dev->dev);
842  }
843 
844  /* pcap_cnt */
845  uint64_t pcap_cnt = PcapPacketCntGet(p);
846  if (pcap_cnt != 0) {
847  SCJbSetUint(js, "pcap_cnt", pcap_cnt);
848  }
849 
850  if (event_type) {
851  SCJbSetString(js, "event_type", event_type);
852  }
853 
854  /* vlan */
855  if (p->vlan_idx > 0) {
856  SCJbOpenArray(js, "vlan");
857  SCJbAppendUint(js, p->vlan_id[0]);
858  if (p->vlan_idx > 1) {
859  SCJbAppendUint(js, p->vlan_id[1]);
860  }
861  if (p->vlan_idx > 2) {
862  SCJbAppendUint(js, p->vlan_id[2]);
863  }
864  SCJbClose(js);
865  }
866 
867  /* 5-tuple */
868  JsonAddrInfo addr_info = json_addr_info_zero;
869  if (addr == NULL) {
870  JsonAddrInfoInit(p, dir, &addr_info, &eve_ctx->cfg);
871  addr = &addr_info;
872  }
873  if (addr->src_ip[0] != '\0') {
874  SCJbSetString(js, "src_ip", addr->src_ip);
875  }
876  if (addr->log_port) {
877  SCJbSetUint(js, "src_port", addr->sp);
878  }
879  if (addr->dst_ip[0] != '\0') {
880  SCJbSetString(js, "dest_ip", addr->dst_ip);
881  }
882  if (addr->log_port) {
883  SCJbSetUint(js, "dest_port", addr->dp);
884  }
885  if (addr->proto[0] != '\0') {
886  SCJbSetString(js, "proto", addr->proto);
887  }
888 
889  /* ip version */
890  if (PacketIsIPv4(p)) {
891  SCJbSetUint(js, "ip_v", 4);
892  } else if (PacketIsIPv6(p)) {
893  SCJbSetUint(js, "ip_v", 6);
894  }
895 
896  /* icmp */
897  switch (p->proto) {
898  case IPPROTO_ICMP:
899  if (PacketIsICMPv4(p)) {
900  SCJbSetUint(js, "icmp_type", p->icmp_s.type);
901  SCJbSetUint(js, "icmp_code", p->icmp_s.code);
902  }
903  break;
904  case IPPROTO_ICMPV6:
905  if (PacketIsICMPv6(p)) {
906  SCJbSetUint(js, "icmp_type", PacketGetICMPv6(p)->type);
907  SCJbSetUint(js, "icmp_code", PacketGetICMPv6(p)->code);
908  }
909  break;
910  case IPPROTO_IGMP:
911  if (PacketIsIGMP(p)) {
912  SCLogDebug("rgmp %s", BOOL2STR(p->l4.vars.igmp.rgmp));
913  if (!p->l4.vars.igmp.rgmp) {
914  SCJbOpenObject(js, "igmp");
915  SCJbSetUint(js, "type", PacketGetIGMP(p)->type);
916  SCJbSetUint(js, "version", p->l4.vars.igmp.version);
917  SCJbClose(js);
918  } else {
919  SCJbOpenObject(js, "rgmp");
920  SCJbSetUint(js, "type", PacketGetIGMP(p)->type);
921  SCJbClose(js);
922  }
923  }
924  break;
925  case IPPROTO_SCTP:
926  if (PacketIsSCTP(p)) {
927  SCJbOpenObject(js, "sctp");
928  SCJbSetUint(js, "vtag", SCTP_GET_RAW_VTAG(PacketGetSCTP(p)));
929  SCJbSetUint(js, "chunk_cnt", p->l4.vars.sctp.chunk_cnt);
930  const uint8_t cnt = p->l4.vars.sctp.tracked_chunk_cnt;
931  SCJbOpenArray(js, "chunk_types");
932  for (uint8_t i = 0; i < cnt; i++) {
933  const char *name = SCSctpChunkTypeToString(p->l4.vars.sctp.chunk_types[i]);
934  if (name) {
935  SCJbAppendString(js, name);
936  } else {
937  char unknown[16];
938  snprintf(unknown, sizeof(unknown), "unknown(%u)",
939  p->l4.vars.sctp.chunk_types[i]);
940  SCJbAppendString(js, unknown);
941  }
942  }
943  SCJbClose(js);
944  SCJbSetBool(js, "has_init", p->l4.vars.sctp.has_init);
945  SCJbSetBool(js, "has_init_ack", p->l4.vars.sctp.has_init_ack);
946  SCJbSetBool(js, "has_data", p->l4.vars.sctp.has_data);
947  SCJbSetBool(js, "has_abort", p->l4.vars.sctp.has_abort);
948  SCJbClose(js);
949  }
950  break;
951  }
952 
953  SCJbSetString(js, "pkt_src", PktSrcToString(p->pkt_src));
954 
955  if (eve_ctx != NULL) {
956  EveAddCommonOptions(&eve_ctx->cfg, p, f, js, dir);
957  }
958 
959  return js;
960 }
961 
963  const char *event_type, JsonAddrInfo *addr, uint64_t tx_id, OutputJsonCtx *eve_ctx)
964 {
965  SCJsonBuilder *js = CreateEveHeader(p, dir, event_type, addr, eve_ctx);
966  if (unlikely(js == NULL))
967  return NULL;
968 
969  /* tx id for correlation with other events */
970  SCJbSetUint(js, "tx_id", tx_id);
971 
972  return js;
973 }
974 
975 int OutputJSONMemBufferCallback(const char *str, size_t size, void *data)
976 {
977  OutputJSONMemBufferWrapper *wrapper = data;
978  MemBuffer **memb = wrapper->buffer;
979 
980  if (MEMBUFFER_OFFSET(*memb) + size >= MEMBUFFER_SIZE(*memb)) {
981  MemBufferExpand(memb, wrapper->expand_by);
982  }
983 
984  DEBUG_VALIDATE_BUG_ON(size > UINT32_MAX);
985  MemBufferWriteRaw((*memb), (const uint8_t *)str, (uint32_t)size);
986  return 0;
987 }
988 
989 int OutputJSONBuffer(json_t *js, LogFileCtx *file_ctx, MemBuffer **buffer)
990 {
991  if (file_ctx->sensor_name) {
992  json_object_set_new(js, "host",
993  json_string(file_ctx->sensor_name));
994  }
995 
996  if (file_ctx->is_pcap_offline) {
997  json_object_set_new(js, "pcap_filename", json_string(PcapFileGetFilename()));
998  }
999 
1000  if (file_ctx->prefix) {
1001  MemBufferWriteRaw((*buffer), (const uint8_t *)file_ctx->prefix, file_ctx->prefix_len);
1002  }
1003 
1004  OutputJSONMemBufferWrapper wrapper = {
1005  .buffer = buffer,
1006  .expand_by = JSON_OUTPUT_BUFFER_SIZE
1007  };
1008 
1009  int r = json_dump_callback(js, OutputJSONMemBufferCallback, &wrapper,
1010  file_ctx->json_flags);
1011  if (r != 0)
1012  return TM_ECODE_OK;
1013 
1014  LogFileWrite(file_ctx, *buffer);
1015  return 0;
1016 }
1017 
1020 {
1021  LogFileCtx *file_ctx = ctx->file_ctx;
1022  MemBuffer **buffer = &ctx->buffer;
1023  if (file_ctx->sensor_name) {
1024  SCJbSetString(js, "host", file_ctx->sensor_name);
1025  }
1026 
1027  if (file_ctx->is_pcap_offline) {
1028  SCJbSetString(js, "pcap_filename", PcapFileGetFilename());
1029  }
1030 
1031  SCEveRunCallbacks(tv, p, f, js);
1032 
1033  SCJbClose(js);
1034 
1035  MemBufferReset(*buffer);
1036 
1037  if (file_ctx->prefix) {
1038  MemBufferWriteRaw((*buffer), (const uint8_t *)file_ctx->prefix, file_ctx->prefix_len);
1039  }
1040 
1041  size_t jslen = SCJbLen(js);
1042  DEBUG_VALIDATE_BUG_ON(SCJbLen(js) > UINT32_MAX);
1043  size_t remaining = MEMBUFFER_SIZE(*buffer) - MEMBUFFER_OFFSET(*buffer);
1044  if (jslen >= remaining) {
1045  size_t expand_by = jslen + 1 - remaining;
1046  if (MemBufferExpand(buffer, (uint32_t)expand_by) < 0) {
1047  if (!ctx->too_large_warning) {
1048  /* Log a warning once, and include enough of the log
1049  * message to hopefully identify the event_type. */
1050  char partial[120];
1051  size_t partial_len = MIN(sizeof(partial), jslen);
1052  memcpy(partial, SCJbPtr(js), partial_len - 1);
1053  partial[partial_len - 1] = '\0';
1054  SCLogWarning("Formatted JSON EVE record too large, will be dropped: %s", partial);
1055  ctx->too_large_warning = true;
1056  }
1057  return;
1058  }
1059  }
1060 
1061  MemBufferWriteRaw((*buffer), SCJbPtr(js), (uint32_t)jslen);
1062  LogFileWrite(file_ctx, *buffer);
1063 }
1064 
1065 static inline enum LogFileType FileTypeFromConf(const char *typestr)
1066 {
1067  enum LogFileType log_filetype = LOGFILE_TYPE_NOTSET;
1068 
1069  if (typestr == NULL) {
1070  log_filetype = LOGFILE_TYPE_FILE;
1071  } else if (strcmp(typestr, "file") == 0 || strcmp(typestr, "regular") == 0) {
1072  log_filetype = LOGFILE_TYPE_FILE;
1073  } else if (strcmp(typestr, "unix_dgram") == 0) {
1074  log_filetype = LOGFILE_TYPE_UNIX_DGRAM;
1075  } else if (strcmp(typestr, "unix_stream") == 0) {
1076  log_filetype = LOGFILE_TYPE_UNIX_STREAM;
1077  } else if (strcmp(typestr, "redis") == 0) {
1078 #ifdef HAVE_LIBHIREDIS
1079  log_filetype = LOGFILE_TYPE_REDIS;
1080 #else
1081  FatalError("redis JSON output option is not compiled");
1082 #endif
1083  }
1084  SCLogDebug("type %s, file type value %d", typestr, log_filetype);
1085  return log_filetype;
1086 }
1087 
1088 static int LogFileTypePrepare(
1089  OutputJsonCtx *json_ctx, enum LogFileType log_filetype, SCConfNode *conf)
1090 {
1091 
1092  if (log_filetype == LOGFILE_TYPE_FILE || log_filetype == LOGFILE_TYPE_UNIX_DGRAM ||
1093  log_filetype == LOGFILE_TYPE_UNIX_STREAM) {
1094  if (SCConfLogOpenGeneric(conf, json_ctx->file_ctx, DEFAULT_LOG_FILENAME, 1) < 0) {
1095  return -1;
1096  }
1097  }
1098 #ifdef HAVE_LIBHIREDIS
1099  else if (log_filetype == LOGFILE_TYPE_REDIS) {
1100  SCLogRedisInit();
1101  SCConfNode *redis_node = SCConfNodeLookupChild(conf, "redis");
1102  if (!json_ctx->file_ctx->sensor_name) {
1103  char hostname[1024];
1104  gethostname(hostname, 1023);
1105  json_ctx->file_ctx->sensor_name = SCStrdup(hostname);
1106  }
1107  if (json_ctx->file_ctx->sensor_name == NULL) {
1108  return -1;
1109  }
1110 
1111  if (SCConfLogOpenRedis(redis_node, json_ctx->file_ctx) < 0) {
1112  return -1;
1113  }
1114  }
1115 #endif
1116  else if (log_filetype == LOGFILE_TYPE_FILETYPE) {
1117  if (json_ctx->file_ctx->threaded) {
1118  /* Prepare for threaded log output. */
1119  if (!SCLogOpenThreadedFile(NULL, NULL, json_ctx->file_ctx)) {
1120  return -1;
1121  }
1122  }
1123  if (json_ctx->filetype->Init(conf, json_ctx->file_ctx->threaded,
1124  &json_ctx->file_ctx->filetype.init_data) < 0) {
1125  return -1;
1126  }
1127  if (json_ctx->filetype->ThreadInit) {
1128  if (json_ctx->filetype->ThreadInit(json_ctx->file_ctx->filetype.init_data, 0,
1129  &json_ctx->file_ctx->filetype.thread_data) < 0) {
1130  return -1;
1131  }
1132  }
1133  json_ctx->file_ctx->filetype.filetype = json_ctx->filetype;
1134  }
1135 
1136  return 0;
1137 }
1138 
1139 /**
1140  * \brief Create a new LogFileCtx for "fast" output style.
1141  * \param conf The configuration node for this output.
1142  * \return A LogFileCtx pointer on success, NULL on failure.
1143  */
1145 {
1146  OutputInitResult result = { NULL, false };
1147  OutputCtx *output_ctx = NULL;
1148 
1149  OutputJsonCtx *json_ctx = SCCalloc(1, sizeof(OutputJsonCtx));
1150  if (unlikely(json_ctx == NULL)) {
1151  SCLogDebug("could not create new OutputJsonCtx");
1152  return result;
1153  }
1154 
1155  /* First lookup a sensor-name value in this outputs configuration
1156  * node (deprecated). If that fails, lookup the global one. */
1157  const char *sensor_name = SCConfNodeLookupChildValue(conf, "sensor-name");
1158  if (sensor_name != NULL) {
1159  SCLogWarning("Found deprecated eve-log setting \"sensor-name\". "
1160  "Please set sensor-name globally.");
1161  }
1162  else {
1163  (void)SCConfGet("sensor-name", &sensor_name);
1164  }
1165 
1166  json_ctx->file_ctx = LogFileNewCtx();
1167  if (unlikely(json_ctx->file_ctx == NULL)) {
1168  SCLogDebug("AlertJsonInitCtx: Could not create new LogFileCtx");
1169  goto error_exit;
1170  }
1171 
1172  if (sensor_name) {
1173  json_ctx->file_ctx->sensor_name = SCStrdup(sensor_name);
1174  if (json_ctx->file_ctx->sensor_name == NULL) {
1175  goto error_exit;
1176  }
1177  } else {
1178  json_ctx->file_ctx->sensor_name = NULL;
1179  }
1180 
1181  output_ctx = SCCalloc(1, sizeof(OutputCtx));
1182  if (unlikely(output_ctx == NULL)) {
1183  goto error_exit;
1184  }
1185 
1186  output_ctx->data = json_ctx;
1187  output_ctx->DeInit = OutputJsonDeInitCtx;
1188 
1189  if (conf) {
1190  const char *output_s = SCConfNodeLookupChildValue(conf, "filetype");
1191  // Backwards compatibility
1192  if (output_s == NULL) {
1193  output_s = SCConfNodeLookupChildValue(conf, "type");
1194  }
1195 
1196  enum LogFileType log_filetype = FileTypeFromConf(output_s);
1197  if (log_filetype == LOGFILE_TYPE_NOTSET) {
1198  SCEveFileType *filetype = SCEveFindFileType(output_s);
1199  if (filetype != NULL) {
1200  log_filetype = LOGFILE_TYPE_FILETYPE;
1201  json_ctx->filetype = filetype;
1202  } else
1203  FatalError("Invalid JSON output option: %s", output_s);
1204  }
1205 
1206  const SCConfNode *compress_ipv6 = SCConfNodeLookupChild(conf, "ipv6-compress");
1207  if (compress_ipv6 && compress_ipv6->val && SCConfValIsTrue(compress_ipv6->val)) {
1208  SCLogConfig("Will compress IPv6 addresses in EVE output per RFC 5952");
1209  json_ctx->cfg.compress_ipv6 = true;
1210  } else {
1211  json_ctx->cfg.compress_ipv6 = false;
1212  }
1213 
1214  const char *prefix = SCConfNodeLookupChildValue(conf, "prefix");
1215  if (prefix != NULL)
1216  {
1217  SCLogInfo("Using prefix '%s' for JSON messages", prefix);
1218  json_ctx->file_ctx->prefix = SCStrdup(prefix);
1219  if (json_ctx->file_ctx->prefix == NULL)
1220  {
1221  FatalError("Failed to allocate memory for eve-log.prefix setting.");
1222  }
1223  json_ctx->file_ctx->prefix_len = (uint32_t)strlen(prefix);
1224  }
1225 
1226  /* Threaded file output */
1227  const SCConfNode *threaded = SCConfNodeLookupChild(conf, "threaded");
1228  if (threaded && threaded->val && SCConfValIsTrue(threaded->val)) {
1229  SCLogConfig("Threaded EVE logging configured");
1230  json_ctx->file_ctx->threaded = true;
1231  } else {
1232  json_ctx->file_ctx->threaded = false;
1233  }
1234  if (LogFileTypePrepare(json_ctx, log_filetype, conf) < 0) {
1235  goto error_exit;
1236  }
1237 
1238  const char *sensor_id_s = SCConfNodeLookupChildValue(conf, "sensor-id");
1239  if (sensor_id_s != NULL) {
1240  if (StringParseUint64((uint64_t *)&sensor_id, 10, 0, sensor_id_s) < 0) {
1241  FatalError("Failed to initialize JSON output, "
1242  "invalid sensor-id: %s",
1243  sensor_id_s);
1244  }
1245  }
1246 
1247  /* Check if top-level metadata should be logged. */
1248  const SCConfNode *metadata = SCConfNodeLookupChild(conf, "metadata");
1249  if (metadata && metadata->val && SCConfValIsFalse(metadata->val)) {
1250  SCLogConfig("Disabling eve metadata logging.");
1251  json_ctx->cfg.include_metadata = false;
1252  } else {
1253  json_ctx->cfg.include_metadata = true;
1254  }
1255 
1256  /* Check if ethernet information should be logged. */
1257  const SCConfNode *ethernet = SCConfNodeLookupChild(conf, "ethernet");
1258  if (ethernet && ethernet->val && SCConfValIsTrue(ethernet->val)) {
1259  SCLogConfig("Enabling Ethernet MAC address logging.");
1260  json_ctx->cfg.include_ethernet = true;
1261  } else {
1262  json_ctx->cfg.include_ethernet = false;
1263  }
1264 
1265  const SCConfNode *suriver = SCConfNodeLookupChild(conf, "suricata-version");
1266  if (suriver && suriver->val && SCConfValIsTrue(suriver->val)) {
1267  SCLogConfig("Enabling Suricata version logging.");
1268  json_ctx->cfg.include_suricata_version = true;
1269  } else {
1270  json_ctx->cfg.include_suricata_version = false;
1271  }
1272 
1273  /* See if we want to enable the community id */
1274  const SCConfNode *community_id = SCConfNodeLookupChild(conf, "community-id");
1275  if (community_id && community_id->val && SCConfValIsTrue(community_id->val)) {
1276  SCLogConfig("Enabling eve community_id logging.");
1277  json_ctx->cfg.include_community_id = true;
1278  } else {
1279  json_ctx->cfg.include_community_id = false;
1280  }
1281  const char *cid_seed = SCConfNodeLookupChildValue(conf, "community-id-seed");
1282  if (cid_seed != NULL) {
1283  if (StringParseUint16(&json_ctx->cfg.community_id_seed,
1284  10, 0, cid_seed) < 0)
1285  {
1286  FatalError("Failed to initialize JSON output, "
1287  "invalid community-id-seed: %s",
1288  cid_seed);
1289  }
1290  }
1291 
1292  /* Do we have a global eve xff configuration? */
1293  const SCConfNode *xff = SCConfNodeLookupChild(conf, "xff");
1294  if (xff != NULL) {
1295  json_ctx->xff_cfg = SCCalloc(1, sizeof(HttpXFFCfg));
1296  if (likely(json_ctx->xff_cfg != NULL)) {
1297  HttpXFFGetCfg(conf, json_ctx->xff_cfg);
1298  }
1299  }
1300 
1301  const char *pcapfile_s = SCConfNodeLookupChildValue(conf, "pcap-file");
1302  if (pcapfile_s != NULL && SCConfValIsTrue(pcapfile_s)) {
1303  json_ctx->file_ctx->is_pcap_offline =
1305  }
1306  json_ctx->file_ctx->type = log_filetype;
1307  }
1308 
1309  SCLogDebug("returning output_ctx %p", output_ctx);
1310 
1311  result.ctx = output_ctx;
1312  result.ok = true;
1313  return result;
1314 
1315 error_exit:
1316  if (json_ctx->file_ctx) {
1317  if (json_ctx->file_ctx->prefix) {
1318  SCFree(json_ctx->file_ctx->prefix);
1319  }
1320  LogFileFreeCtx(json_ctx->file_ctx);
1321  }
1322  SCFree(json_ctx);
1323 
1324  if (output_ctx) {
1325  SCFree(output_ctx);
1326  }
1327  return result;
1328 }
1329 
1330 static void OutputJsonDeInitCtx(OutputCtx *output_ctx)
1331 {
1332  OutputJsonCtx *json_ctx = (OutputJsonCtx *)output_ctx->data;
1333  LogFileCtx *logfile_ctx = json_ctx->file_ctx;
1334  if (logfile_ctx->dropped) {
1335  SCLogWarning("%" PRIu64 " events were dropped due to slow or "
1336  "disconnected socket",
1337  logfile_ctx->dropped);
1338  }
1339  if (json_ctx->xff_cfg != NULL) {
1340  SCFree(json_ctx->xff_cfg);
1341  }
1342  LogFileFreeCtx(logfile_ctx);
1343  SCFree(json_ctx);
1344  SCFree(output_ctx);
1345 }
PKT_IS_TOCLIENT
#define PKT_IS_TOCLIENT(p)
Definition: decode.h:240
SCJsonBuilder
struct SCJsonBuilder SCJsonBuilder
Definition: detect-engine-helper.h:83
FlowVar_::fv_float
FlowVarTypeFloat fv_float
Definition: flow-var.h:66
util-device-private.h
util-byte.h
MacSetSide
MacSetSide
Definition: util-macset.h:28
Packet_::proto
uint8_t proto
Definition: decode.h:538
pad0
uint8_t pad0
Definition: decode-template.h:1
SCOutputJsonLogDirection
SCOutputJsonLogDirection
Definition: output-eve-bindgen.h:33
SCConfValIsTrue
int SCConfValIsTrue(const char *val)
Check if a value is true.
Definition: conf.c:577
detect-engine.h
LOGFILE_TYPE_REDIS
@ LOGFILE_TYPE_REDIS
Definition: util-logopenfile.h:42
LogFileCtx_::sensor_name
char * sensor_name
Definition: util-logopenfile.h:121
OutputJsonCtx_::xff_cfg
HttpXFFCfg * xff_cfg
Definition: output-json.h:81
Flow_::flags
uint64_t flags
Definition: flow.h:408
offset
uint64_t offset
Definition: util-streaming-buffer.h:0
CreateIsoTimeString
void CreateIsoTimeString(const SCTime_t ts, char *str, size_t size)
Definition: util-time.c:209
OutputJsonCtx_::cfg
OutputJsonCommonSettings cfg
Definition: output-json.h:80
HttpXFFGetCfg
void HttpXFFGetCfg(SCConfNode *conf, HttpXFFCfg *result)
Function to return XFF configuration from a configuration node.
Definition: app-layer-htp-xff.c:116
unlikely
#define unlikely(expr)
Definition: util-optimize.h:35
FILE_SHA256
#define FILE_SHA256
Definition: util-file.h:119
SCFlowGetStorageById
void * SCFlowGetStorageById(const Flow *f, SCFlowStorageId id)
Definition: flow-storage.c:37
LogFileNewCtx
LogFileCtx * LogFileNewCtx(void)
LogFileNewCtx() Get a new LogFileCtx.
Definition: util-logopenfile.c:734
PcapPacketCntGet
uint64_t PcapPacketCntGet(const Packet *p)
Definition: decode.c:1193
MemBufferExpand
int MemBufferExpand(MemBuffer **buffer, uint32_t expand_by)
expand membuffer by size of 'expand_by'
Definition: util-buffer.c:60
SCLogDebug
#define SCLogDebug(...)
Definition: util-debug.h:282
SCTPVars_::chunk_types
uint8_t chunk_types[SCTP_MAX_TRACKED_CHUNKS]
Definition: decode-sctp.h:82
name
const char * name
Definition: detect-engine-proto.c:47
Flow_::proto
uint8_t proto
Definition: flow.h:381
FlowVarTypeStr::value_len
uint16_t value_len
Definition: flow-var.h:41
FLOWVAR_TYPE_STR
#define FLOWVAR_TYPE_STR
Definition: flow-var.h:33
type
uint8_t type
Definition: decode-sctp.h:0
CreateEveHeader
SCJsonBuilder * CreateEveHeader(const Packet *p, enum SCOutputJsonLogDirection dir, const char *event_type, JsonAddrInfo *addr, OutputJsonCtx *eve_ctx)
Definition: output-json.c:816
JSON_OUTPUT_BUFFER_SIZE
#define JSON_OUTPUT_BUFFER_SIZE
Definition: output-json.h:54
TH_RST
#define TH_RST
Definition: decode-tcp.h:36
util-macset.h
OutputJsonCtx_
Definition: output-json.h:77
LogFileCtx_::json_flags
size_t json_flags
Definition: util-logopenfile.h:162
PrintInetIPv6
const char * PrintInetIPv6(const void *src, char *dst, socklen_t size, bool compress_ipv6)
Definition: util-print.c:209
Packet_::vlan_idx
uint8_t vlan_idx
Definition: decode.h:544
Flow_
Flow data structure.
Definition: flow.h:359
File_::state
FileState state
Definition: util-file.h:149
OutputJsonCommonSettings_
Definition: output-json.h:62
JsonAddrInfoInit
void JsonAddrInfoInit(const Packet *p, enum SCOutputJsonLogDirection dir, JsonAddrInfo *addr, OutputJsonCommonSettings *cfg)
Definition: output-json.c:464
TH_FIN
#define TH_FIN
Definition: decode-tcp.h:34
util-syslog.h
ctx
struct Thresholds ctx
LiveDevice_
Definition: util-device-private.h:32
LogFileCtx_
Definition: util-logopenfile.h:77
StringParseUint16
int StringParseUint16(uint16_t *res, int base, size_t len, const char *str)
Definition: util-byte.c:295
SCConfGet
int SCConfGet(const char *name, const char **vptr)
Retrieve the value of a configuration node.
Definition: conf.c:352
PktVar_::next
struct PktVar_ * next
Definition: decode.h:316
FILE_STORE
#define FILE_STORE
Definition: util-file.h:122
File_::file_store_id
uint32_t file_store_id
Definition: util-file.h:152
FlowVar_::fv_str
FlowVarTypeStr fv_str
Definition: flow-var.h:64
LiveDeviceGetById
LiveDevice * LiveDeviceGetById(const int id)
Definition: util-device.c:460
SCTPVars_::chunk_cnt
uint16_t chunk_cnt
Definition: decode-sctp.h:80
FlowVar_::keylen
FlowVarKeyLenType keylen
Definition: flow-var.h:58
LOGFILE_TYPE_NOTSET
@ LOGFILE_TYPE_NOTSET
Definition: util-logopenfile.h:45
SCProtoNameValid
bool SCProtoNameValid(uint16_t proto)
Function to check if the received protocol number is valid and do we have corresponding name entry fo...
Definition: util-proto-name.c:449
EveTcpFlags
void EveTcpFlags(const uint8_t flags, SCJsonBuilder *js)
jsonify tcp flags field Only add 'true' fields in an attempt to keep things reasonably compact.
Definition: output-json.c:444
output-eve-null.h
json_addr_info_zero
const JsonAddrInfo json_addr_info_zero
Definition: output-json.c:78
flow-bit.h
util-var-name.h
MIN
#define MIN(x, y)
Definition: suricata-common.h:413
util-log-redis.h
LOG_DIR_FLOW_TOSERVER
@ LOG_DIR_FLOW_TOSERVER
Definition: output-eve-bindgen.h:37
COMMUNITY_ID_BUF_SIZE
#define COMMUNITY_ID_BUF_SIZE
Definition: output-json.c:567
OutputJsonCommonSettings_::include_community_id
bool include_community_id
Definition: output-json.h:64
SCConfValIsFalse
int SCConfValIsFalse(const char *val)
Check if a value is false.
Definition: conf.c:602
OutputJSONMemBufferWrapper_::buffer
MemBuffer ** buffer
Definition: output-json.h:58
known_proto
const char * known_proto[256]
Definition: util-proto-name.c:39
p
Packet * p
Definition: fuzz_dataset.c:30
OutputJsonBuilderBuffer
void OutputJsonBuilderBuffer(ThreadVars *tv, const Packet *p, Flow *f, SCJsonBuilder *js, OutputJsonThreadCtx *ctx)
Definition: output-json.c:1018
SCTPVars_::has_init
bool has_init
Definition: decode-sctp.h:84
FILE_STATE_TRUNCATED
@ FILE_STATE_TRUNCATED
Definition: util-file.h:140
proto
uint8_t proto
Definition: decode-template.h:0
CreateEveFlowId
void CreateEveFlowId(SCJsonBuilder *js, const Flow *f)
Definition: output-json.c:682
SCConfNodeLookupChildValue
const char * SCConfNodeLookupChildValue(const SCConfNode *node, const char *name)
Lookup the value of a child configuration node by name.
Definition: conf.c:877
Flow_::dp
Port dp
Definition: flow.h:375
JSONMACAddrInfo::dst
SCJsonBuilder * dst
Definition: output-json.c:708
FLOWVAR_TYPE_INT
#define FLOWVAR_TYPE_INT
Definition: flow-var.h:34
JSONMACAddrInfo
struct JSONMACAddrInfo JSONMACAddrInfo
File_::sha1
uint8_t sha1[SC_SHA1_LEN]
Definition: util-file.h:163
FLOW_IPV4
#define FLOW_IPV4
Definition: flow.h:99
GET_IPV6_DST_ADDR
#define GET_IPV6_DST_ADDR(p)
Definition: decode.h:205
SCJsonString
json_t * SCJsonString(const char *val)
Definition: output-json.c:93
OutputJsonCommonSettings_::include_suricata_version
bool include_suricata_version
Definition: output-json.h:67
util-unittest-helper.h
OutputCtx_::data
void * data
Definition: tm-modules.h:91
TM_ECODE_OK
@ TM_ECODE_OK
Definition: tm-threads-common.h:81
PrintStringsToBuffer
void PrintStringsToBuffer(uint8_t *dst_buf, uint32_t *dst_buf_offset_ptr, uint32_t dst_buf_size, const uint8_t *src_buf, const uint32_t src_buf_len)
Definition: util-print.c:195
OutputJsonRegister
void OutputJsonRegister(void)
Definition: output-json.c:80
OutputCtx_
Definition: tm-modules.h:88
RUNMODE_UNIX_SOCKET
@ RUNMODE_UNIX_SOCKET
Definition: runmodes.h:42
strlcpy
size_t strlcpy(char *dst, const char *src, size_t siz)
Definition: util-strlcpyu.c:43
OutputJsonThreadCtx_
Definition: output-json.h:85
Packet_::icmp_s
struct Packet_::@32::@39 icmp_s
Packet_::datalink
int datalink
Definition: decode.h:652
Flow_::icmp_d
struct Flow_::@128::@134 icmp_d
File_::name_len
uint16_t name_len
Definition: util-file.h:148
FlowVar_::fv_int
FlowVarTypeInt fv_int
Definition: flow-var.h:65
LogFileCtx_::filetype
LogFileTypeCtx filetype
Definition: util-logopenfile.h:97
Flow_::dst
FlowAddress dst
Definition: flow.h:362
JsonAddrInfo_::dp
Port dp
Definition: output-json.h:45
File_::md5
uint8_t md5[SC_MD5_LEN]
Definition: util-file.h:161
SCRunmodeGet
SCRunMode SCRunmodeGet(void)
Get the current run mode.
Definition: suricata.c:302
LogFileWrite
int LogFileWrite(LogFileCtx *file_ctx, MemBuffer *buffer)
Definition: util-logopenfile.c:1117
util-debug.h
JB_SET_STRING
#define JB_SET_STRING(jb, key, val)
Definition: rust.h:36
Packet_::pktvar
PktVar * pktvar
Definition: decode.h:612
GenericVar_::next
struct GenericVar_ * next
Definition: util-var.h:57
GET_IPV4_DST_ADDR_PTR
#define GET_IPV4_DST_ADDR_PTR(p)
Definition: decode.h:200
PKT_IS_TOSERVER
#define PKT_IS_TOSERVER(p)
Definition: decode.h:239
DEFAULT_LOG_FILENAME
#define DEFAULT_LOG_FILENAME
Definition: output-json.c:63
EveAddCommonOptions
void EveAddCommonOptions(const OutputJsonCommonSettings *cfg, const Packet *p, const Flow *f, SCJsonBuilder *js, enum SCOutputJsonLogDirection dir)
Definition: output-json.c:392
File_::end
uint64_t end
Definition: util-file.h:173
DETECT_FLOWINT
@ DETECT_FLOWINT
Definition: detect-engine-register.h:71
OutputInitResult_::ctx
OutputCtx * ctx
Definition: output.h:47
LogFileCtx_::prefix_len
uint32_t prefix_len
Definition: util-logopenfile.h:138
DETECT_FLOWVAR
@ DETECT_FLOWVAR
Definition: detect-engine-register.h:69
Packet_::ts
SCTime_t ts
Definition: decode.h:570
output-json.h
FlowVar_::idx
uint32_t idx
Definition: flow-var.h:59
SCEveFileType_::ThreadInit
SCEveFileTypeThreadInitFunc ThreadInit
Initialize thread specific data.
Definition: output-eve-bindgen.h:161
JSONMACAddrInfo
Definition: output-json.c:707
PktVar_::value
uint8_t * value
Definition: decode.h:322
BOOL2STR
#define BOOL2STR(b)
Definition: util-debug.h:542
OutputRegisterModule
void OutputRegisterModule(const char *, const char *, OutputInitFunc)
OutputJsonInitCtx
OutputInitResult OutputJsonInitCtx(SCConfNode *conf)
Create a new LogFileCtx for "fast" output style.
Definition: output-json.c:1144
util-print.h
FlowVar_::key
uint8_t * key
Definition: flow-var.h:68
GET_PKT_DATA
#define GET_PKT_DATA(p)
Definition: decode.h:210
ThreadVars_
Per thread variable structure.
Definition: threadvars.h:57
SCTP_GET_RAW_VTAG
#define SCTP_GET_RAW_VTAG(sctph)
Definition: decode-sctp.h:94
PrintInet
const char * PrintInet(int af, const void *src, char *dst, socklen_t size)
Definition: util-print.c:238
FlowVarTypeFloat_::value
double value
Definition: flow-var.h:51
Packet_::sp
Port sp
Definition: decode.h:523
FileTrackedSize
uint64_t FileTrackedSize(const File *file)
get the size of the file
Definition: util-file.c:325
SCEveFileType_::Init
SCEveFileTypeInitFunc Init
Function to initialize this filetype.
Definition: output-eve-bindgen.h:140
PktSrcToString
const char * PktSrcToString(enum PktSrcEnum pkt_src)
Definition: decode.c:894
TH_ACK
#define TH_ACK
Definition: decode-tcp.h:38
JB_SET_TRUE
#define JB_SET_TRUE(jb, key)
Definition: rust.h:37
OutputInitResult_::ok
bool ok
Definition: output.h:48
LiveDevice_::dev
char * dev
Definition: util-device-private.h:33
SCLogWarning
#define SCLogWarning(...)
Macro used to log WARNING messages.
Definition: util-debug.h:262
PktVar_::key
uint8_t * key
Definition: decode.h:321
SyslogInitialize
void SyslogInitialize(void)
Definition: output-eve-syslog.c:99
LogFileCtx_::type
enum LogFileType type
Definition: util-logopenfile.h:109
LOG_DIR_FLOW
@ LOG_DIR_FLOW
Definition: output-eve-bindgen.h:35
LOGFILE_TYPE_FILE
@ LOGFILE_TYPE_FILE
Definition: util-logopenfile.h:39
IGMPVars_::rgmp
bool rgmp
Definition: decode-igmp.h:35
MAC_SET_DST
@ MAC_SET_DST
Definition: util-macset.h:28
JsonAddrInfo_::log_port
bool log_port
Definition: output-json.h:48
JsonAddrInfo_
Definition: output-json.h:41
source-pcap-file-helper.h
NullLogInitialize
void NullLogInitialize(void)
Definition: output-eve-null.c:66
Packet_
Definition: decode.h:516
EveFileInfo
void EveFileInfo(SCJsonBuilder *jb, const File *ff, const uint64_t tx_id, const uint16_t flags)
Definition: output-json.c:121
OutputJSONMemBufferWrapper_
Definition: output-json.h:57
GET_PKT_LEN
#define GET_PKT_LEN(p)
Definition: decode.h:209
MacSet_
Definition: util-macset.c:44
conf.h
Packet_::l4
struct PacketL4 l4
Definition: decode.h:616
JSONFormatAndAddMACAddr
void JSONFormatAndAddMACAddr(SCJsonBuilder *js, const char *key, const uint8_t *val, bool is_array)
Definition: output-json.c:694
Port
uint16_t Port
Definition: decode.h:219
File_::name
uint8_t * name
Definition: util-file.h:155
TH_ECN
#define TH_ECN
Definition: decode-tcp.h:41
HttpXFFCfg_
Definition: app-layer-htp-xff.h:41
LOGFILE_TYPE_UNIX_DGRAM
@ LOGFILE_TYPE_UNIX_DGRAM
Definition: util-logopenfile.h:40
LogFileTypeCtx_::thread_data
void * thread_data
Definition: util-logopenfile.h:68
SCLogOpenThreadedFile
bool SCLogOpenThreadedFile(const char *log_path, const char *append, LogFileCtx *parent_ctx)
Definition: util-logopenfile.c:393
util-proto-name.h
SCTPVars_::has_abort
bool has_abort
Definition: decode-sctp.h:87
OutputJsonCommonSettings_::include_ethernet
bool include_ethernet
Definition: output-json.h:65
__attribute__
typedef __attribute__
DNP3 application header.
File_::sid
uint32_t * sid
Definition: util-file.h:175
LOGFILE_TYPE_UNIX_STREAM
@ LOGFILE_TYPE_UNIX_STREAM
Definition: util-logopenfile.h:41
EvePacket
void EvePacket(const Packet *p, SCJsonBuilder *js, uint32_t max_length)
Jsonify a packet.
Definition: output-json.c:419
MemBuffer_
Definition: util-buffer.h:27
File_::sid_cnt
uint32_t sid_cnt
Definition: util-file.h:176
TH_URG
#define TH_URG
Definition: decode-tcp.h:39
SCLogInfo
#define SCLogInfo(...)
Macro used to log INFORMATIONAL messages.
Definition: util-debug.h:232
EveAddMetadata
void EveAddMetadata(const Packet *p, const Flow *f, SCJsonBuilder *js)
Definition: output-json.c:369
VAR_TYPE_FLOW_FLOAT
@ VAR_TYPE_FLOW_FLOAT
Definition: util-var.h:38
FlowVarTypeInt_::value
uint32_t value
Definition: flow-var.h:46
Flow_::src
FlowAddress src
Definition: flow.h:362
Flow_::flowvar
GenericVar * flowvar
Definition: flow.h:494
OutputJsonCommonSettings_::compress_ipv6
bool compress_ipv6
Definition: output-json.h:66
OutputJsonCommonSettings_::include_metadata
bool include_metadata
Definition: output-json.h:63
JsonAddrInfo_::proto
char proto[JSON_PROTO_LEN]
Definition: output-json.h:46
MAC_SET_SRC
@ MAC_SET_SRC
Definition: util-macset.h:28
File_::flags
uint16_t flags
Definition: util-file.h:147
SCConfNodeLookupChild
SCConfNode * SCConfNodeLookupChild(const SCConfNode *node, const char *name)
Lookup a child configuration node by name.
Definition: conf.c:849
PacketL4::L4Vars::sctp
SCTPVars sctp
Definition: decode.h:495
FILE_STATE_CLOSED
@ FILE_STATE_CLOSED
Definition: util-file.h:138
File_
Definition: util-file.h:146
TH_PUSH
#define TH_PUSH
Definition: decode-tcp.h:37
flow-storage.h
cnt
uint32_t cnt
Definition: tmqh-packetpool.h:7
Flow_::icmp_s
struct Flow_::@126::@132 icmp_s
OutputInitResult_
Definition: output.h:46
FlowVarTypeStr::value
uint8_t * value
Definition: flow-var.h:40
Packet_::flow
struct Flow_ * flow
Definition: decode.h:564
SCTPVars_::tracked_chunk_cnt
uint8_t tracked_chunk_cnt
Definition: decode-sctp.h:81
StringParseUint64
int StringParseUint64(uint64_t *res, int base, size_t len, const char *str)
Definition: util-byte.c:263
VAR_TYPE_FLOW_BIT
@ VAR_TYPE_FLOW_BIT
Definition: util-var.h:36
GET_IPV4_SRC_ADDR_PTR
#define GET_IPV4_SRC_ADDR_PTR(p)
Definition: decode.h:199
PrintBufferData
#define PrintBufferData(buf, buf_offset_ptr, buf_size,...)
Definition: util-print.h:27
TH_SYN
#define TH_SYN
Definition: decode-tcp.h:35
flags
uint8_t flags
Definition: decode-gre.h:0
OutputJSONMemBufferWrapper_::expand_by
uint32_t expand_by
Definition: output-json.h:59
SCNtohs
#define SCNtohs(x)
Definition: suricata-common.h:436
suricata-common.h
JsonAddrInfo_::sp
Port sp
Definition: output-json.h:44
FLOW_IPV6
#define FLOW_IPV6
Definition: flow.h:101
OutputCtx_::DeInit
void(* DeInit)(struct OutputCtx_ *)
Definition: tm-modules.h:94
LogFileTypeCtx_::init_data
void * init_data
Definition: util-logopenfile.h:67
VarNameStoreLookupById
const char * VarNameStoreLookupById(const uint32_t id, const enum VarTypes type)
find name for id+type at packet time. As the active store won't be modified, we don't need locks.
Definition: util-var-name.c:307
FlowVar_::data
union FlowVar_::@121 data
MacSetSize
int MacSetSize(const MacSet *ms)
Definition: util-macset.c:245
GenericVar_
Definition: util-var.h:53
JSON_ADDR_LEN
#define JSON_ADDR_LEN
Definition: output-json.h:37
FILE_STORED
#define FILE_STORED
Definition: util-file.h:123
Packet_::livedev_id
uint16_t livedev_id
Definition: decode.h:633
FLOWVAR_TYPE_FLOAT
#define FLOWVAR_TYPE_FLOAT
Definition: flow-var.h:35
FILE_MD5
#define FILE_MD5
Definition: util-file.h:115
LogFileFreeCtx
int LogFileFreeCtx(LogFileCtx *lf_ctx)
LogFileFreeCtx() Destroy a LogFileCtx (Close the file and free memory)
Definition: util-logopenfile.c:951
output-eve-syslog.h
util-classification-config.h
CreateEveHeaderWithTxId
SCJsonBuilder * CreateEveHeaderWithTxId(const Packet *p, enum SCOutputJsonLogDirection dir, const char *event_type, JsonAddrInfo *addr, uint64_t tx_id, OutputJsonCtx *eve_ctx)
Definition: output-json.c:962
SCStrdup
#define SCStrdup(s)
Definition: util-mem.h:56
FatalError
#define FatalError(...)
Definition: util-debug.h:517
Flow_::parent_id
int64_t parent_id
Definition: flow.h:435
FlowBit_::idx
uint32_t idx
Definition: flow-bit.h:33
DETECT_FLOWBITS
@ DETECT_FLOWBITS
Definition: detect-engine-register.h:68
tv
ThreadVars * tv
Definition: fuzz_decodepcapfile.c:34
File_::sha256
uint8_t sha256[SC_SHA256_LEN]
Definition: util-file.h:165
File_::start
uint64_t start
Definition: util-file.h:172
JB_SET_FALSE
#define JB_SET_FALSE(jb, key)
Definition: rust.h:38
util-validate.h
SCLogConfig
struct SCLogConfig_ SCLogConfig
Holds the config state used by the logging api.
JsonAddrInfo_::src_ip
char src_ip[JSON_ADDR_LEN]
Definition: output-json.h:42
FlowBit_
Definition: flow-bit.h:30
str
#define str(s)
Definition: suricata-common.h:313
SCConfLogOpenGeneric
int SCConfLogOpenGeneric(SCConfNode *conf, LogFileCtx *log_ctx, const char *default_filename, int rotate)
open a generic output "log file", which may be a regular file or a socket
Definition: util-logopenfile.c:498
GET_IPV6_SRC_ADDR
#define GET_IPV6_SRC_ADDR(p)
Definition: decode.h:204
SCFree
#define SCFree(p)
Definition: util-mem.h:61
Packet_::pkt_src
uint8_t pkt_src
Definition: decode.h:626
util-logopenfile.h
MacSetGetFirst
uint8_t * MacSetGetFirst(const MacSet *ms, MacSetSide side)
Definition: util-macset.c:232
MEMBUFFER_SIZE
#define MEMBUFFER_SIZE(mem_buffer)
Get the MemBuffers current size.
Definition: util-buffer.h:61
src
uint16_t src
Definition: app-layer-dnp3.h:5
util-buffer.h
TH_CWR
#define TH_CWR
Definition: decode-tcp.h:43
VAR_TYPE_FLOW_VAR
@ VAR_TYPE_FLOW_VAR
Definition: util-var.h:39
MacSetForEach
int MacSetForEach(const MacSet *ms, MacSetIteratorFunc IterFunc, void *data)
Definition: util-macset.c:219
SCTPVars_::has_data
bool has_data
Definition: decode-sctp.h:86
LogFileCtx_::prefix
char * prefix
Definition: util-logopenfile.h:137
JsonAddrInfo_::dst_ip
char dst_ip[JSON_ADDR_LEN]
Definition: output-json.h:43
VAR_TYPE_FLOW_INT
@ VAR_TYPE_FLOW_INT
Definition: util-var.h:37
LogFileCtx_::is_pcap_offline
bool is_pcap_offline
Definition: util-logopenfile.h:165
PcapFileGetFilename
const char * PcapFileGetFilename(void)
Definition: source-pcap-file-helper.c:168
GenericVar_::type
uint16_t type
Definition: util-var.h:54
PktVar_::value_len
uint16_t value_len
Definition: decode.h:320
MAX_JSON_SIZE
#define MAX_JSON_SIZE
Definition: output-json.c:66
OutputJsonCtx_::file_ctx
LogFileCtx * file_ctx
Definition: output-json.h:78
OutputJSONMemBufferCallback
int OutputJSONMemBufferCallback(const char *str, size_t size, void *data)
Definition: output-json.c:975
JSONMACAddrInfo::src
SCJsonBuilder * src
Definition: output-json.c:708
OutputJSONBuffer
int OutputJSONBuffer(json_t *js, LogFileCtx *file_ctx, MemBuffer **buffer)
Definition: output-json.c:989
FILE_SHA1
#define FILE_SHA1
Definition: util-file.h:117
PacketL4::L4Vars::igmp
IGMPVars igmp
Definition: decode.h:494
LogFileType
LogFileType
Definition: util-logopenfile.h:38
MemBufferWriteRaw
uint32_t MemBufferWriteRaw(MemBuffer *dst, const uint8_t *raw, const uint32_t raw_len)
Write a raw buffer to the MemBuffer dst.
Definition: util-buffer.c:115
SCEveFindFileType
SCEveFileType * SCEveFindFileType(const char *name)
Definition: output-eve.c:81
LOG_DIR_PACKET
@ LOG_DIR_PACKET
Definition: output-eve-bindgen.h:34
LOG_DIR_FLOW_TOCLIENT
@ LOG_DIR_FLOW_TOCLIENT
Definition: output-eve-bindgen.h:36
IGMPVars_::version
uint8_t version
Definition: decode-igmp.h:34
PktVar_
Definition: decode.h:314
Packet_::vlan_id
uint16_t vlan_id[VLAN_MAX_LAYERS]
Definition: decode.h:543
likely
#define likely(expr)
Definition: util-optimize.h:32
IPPROTO_SCTP
#define IPPROTO_SCTP
Definition: decode.h:1273
Flow_::sp
Port sp
Definition: flow.h:364
dst
uint16_t dst
Definition: app-layer-dnp3.h:4
PROG_VER
#define PROG_VER
Definition: suricata.h:76
LogFileTypeCtx_::filetype
SCEveFileType * filetype
Definition: util-logopenfile.h:66
OutputJsonCommonSettings_::community_id_seed
uint16_t community_id_seed
Definition: output-json.h:68
flow.h
MEMBUFFER_OFFSET
#define MEMBUFFER_OFFSET(mem_buffer)
Get the MemBuffers current offset.
Definition: util-buffer.h:56
Packet_::dp
Port dp
Definition: decode.h:531
PktVar_::key_len
uint16_t key_len
Definition: decode.h:319
RUNMODE_PCAP_FILE
@ RUNMODE_PCAP_FILE
Definition: runmodes.h:30
SCCalloc
#define SCCalloc(nm, sz)
Definition: util-mem.h:53
SCConfNode_
Definition: conf.h:37
flow-var.h
SCConfNode_::val
char * val
Definition: conf.h:39
FILE_STATE_ERROR
@ FILE_STATE_ERROR
Definition: util-file.h:142
FlowVar_
Definition: flow-var.h:55
DEBUG_VALIDATE_BUG_ON
#define DEBUG_VALIDATE_BUG_ON(exp)
Definition: util-validate.h:109
SCTPVars_::has_init_ack
bool has_init_ack
Definition: decode-sctp.h:85
Flow_::tenant_id
uint32_t tenant_id
Definition: flow.h:429
VAR_TYPE_PKT_VAR
@ VAR_TYPE_PKT_VAR
Definition: util-var.h:33
PacketL4::vars
union PacketL4::L4Vars vars
LOGFILE_TYPE_FILETYPE
@ LOGFILE_TYPE_FILETYPE
Definition: util-logopenfile.h:44
FlowVar_::datatype
uint8_t datatype
Definition: flow-var.h:57
FILE_HAS_GAPS
#define FILE_HAS_GAPS
Definition: util-file.h:126
output.h
PktVar_::id
uint32_t id
Definition: decode.h:315
SCEveRunCallbacks
void SCEveRunCallbacks(ThreadVars *tv, const Packet *p, Flow *f, SCJsonBuilder *jb)
Definition: output-eve.c:52
LogFileCtx_::threaded
bool threaded
Definition: util-logopenfile.h:104
MODULE_NAME
#define MODULE_NAME
Definition: output-json.c:64
SCEveFileType_
Structure used to define an EVE output file type.
Definition: output-eve-bindgen.h:110
f
Flow f
Definition: fuzz_dataset.c:32
MacSetGetFlowStorageID
SCFlowStorageId MacSetGetFlowStorageID(void)
Definition: util-macset.c:112
OutputJsonCtx_::filetype
SCEveFileType * filetype
Definition: output-json.h:82