From: Eric Leblond Date: Sun, 15 Oct 2023 13:39:40 +0000 (+0200) Subject: eve: revert ethernet addresses when needed X-Git-Tag: suricata-7.0.6~33 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=e58f3185c5b14fec93cf85e439fa15a2526ea0b0;p=thirdparty%2Fsuricata.git eve: revert ethernet addresses when needed EVE logging has a direction parameter that can cause the logging of an application layer to be done in a direction that is not linked to the packet. As a result the source IP addres could be assigned the MAC address of the destination IP and reverse. This patch addresses this by propagating the direction to the ethernet logging function and using it there to define the correct mapping. Issue #6405 (cherry picked from commit 21916b974304998d38cfcafe543ee7b94e268daf) --- diff --git a/src/output-json-flow.c b/src/output-json-flow.c index 07bcd954f2..487185f2ed 100644 --- a/src/output-json-flow.c +++ b/src/output-json-flow.c @@ -281,7 +281,7 @@ static void EveFlowLogJSON(OutputJsonThreadCtx *aft, JsonBuilder *jb, Flow *f) /* Close flow. */ jb_close(jb); - EveAddCommonOptions(&aft->ctx->cfg, NULL, f, jb); + EveAddCommonOptions(&aft->ctx->cfg, NULL, f, jb, LOG_DIR_FLOW); /* TCP */ if (f->proto == IPPROTO_TCP) { diff --git a/src/output-json-netflow.c b/src/output-json-netflow.c index 2ac6995cfa..98873e5f06 100644 --- a/src/output-json-netflow.c +++ b/src/output-json-netflow.c @@ -275,7 +275,7 @@ static int JsonNetFlowLogger(ThreadVars *tv, void *thread_data, Flow *f) if (unlikely(jb == NULL)) return TM_ECODE_OK; NetFlowLogEveToServer(jb, f); - EveAddCommonOptions(&jhl->ctx->cfg, NULL, f, jb); + EveAddCommonOptions(&jhl->ctx->cfg, NULL, f, jb, LOG_DIR_FLOW_TOSERVER); OutputJsonBuilderBuffer(jb, jhl); jb_free(jb); @@ -285,7 +285,7 @@ static int JsonNetFlowLogger(ThreadVars *tv, void *thread_data, Flow *f) if (unlikely(jb == NULL)) return TM_ECODE_OK; NetFlowLogEveToClient(jb, f); - EveAddCommonOptions(&jhl->ctx->cfg, NULL, f, jb); + EveAddCommonOptions(&jhl->ctx->cfg, NULL, f, jb, LOG_DIR_FLOW_TOCLIENT); OutputJsonBuilderBuffer(jb, jhl); jb_free(jb); } diff --git a/src/output-json.c b/src/output-json.c index 5d4255cd28..7c3b7e2757 100644 --- a/src/output-json.c +++ b/src/output-json.c @@ -79,7 +79,8 @@ static void OutputJsonDeInitCtx(OutputCtx *); static void CreateEveCommunityFlowId(JsonBuilder *js, const Flow *f, const uint16_t seed); -static int CreateJSONEther(JsonBuilder *parent, const Packet *p, const Flow *f); +static int CreateJSONEther( + JsonBuilder *parent, const Packet *p, const Flow *f, enum OutputJsonLogDirection dir); static const char *TRAFFIC_ID_PREFIX = "traffic/id/"; static const char *TRAFFIC_LABEL_PREFIX = "traffic/label/"; @@ -412,14 +413,14 @@ void EveAddMetadata(const Packet *p, const Flow *f, JsonBuilder *js) } } -void EveAddCommonOptions(const OutputJsonCommonSettings *cfg, - const Packet *p, const Flow *f, JsonBuilder *js) +void EveAddCommonOptions(const OutputJsonCommonSettings *cfg, const Packet *p, const Flow *f, + JsonBuilder *js, enum OutputJsonLogDirection dir) { if (cfg->include_metadata) { EveAddMetadata(p, f, js); } if (cfg->include_ethernet) { - CreateJSONEther(js, p, f); + CreateJSONEther(js, p, f, dir); } if (cfg->include_community_id && f != NULL) { CreateEveCommunityFlowId(js, f, cfg->community_id_seed); @@ -742,14 +743,42 @@ static int MacSetIterateToJSON(uint8_t *val, MacSetSide side, void *data) return 0; } -static int CreateJSONEther(JsonBuilder *js, const Packet *p, const Flow *f) +static int CreateJSONEther( + JsonBuilder *js, const Packet *p, const Flow *f, enum OutputJsonLogDirection dir) { if (p != NULL) { /* this is a packet context, so we need to add scalar fields */ if (p->ethh != NULL) { jb_open_object(js, "ether"); - uint8_t *src = p->ethh->eth_src; - uint8_t *dst = p->ethh->eth_dst; + uint8_t *src; + uint8_t *dst; + switch (dir) { + case LOG_DIR_FLOW_TOSERVER: + // fallthrough + case LOG_DIR_FLOW: + if (PKT_IS_TOCLIENT(p)) { + src = p->ethh->eth_dst; + dst = p->ethh->eth_src; + } else { + src = p->ethh->eth_src; + dst = p->ethh->eth_dst; + } + break; + case LOG_DIR_FLOW_TOCLIENT: + if (PKT_IS_TOSERVER(p)) { + src = p->ethh->eth_dst; + dst = p->ethh->eth_src; + } else { + src = p->ethh->eth_src; + dst = p->ethh->eth_dst; + } + break; + case LOG_DIR_PACKET: + default: + src = p->ethh->eth_src; + dst = p->ethh->eth_dst; + break; + } JSONFormatAndAddMACAddr(js, "src_mac", src, false); JSONFormatAndAddMACAddr(js, "dest_mac", dst, false); jb_close(js); @@ -773,8 +802,15 @@ static int CreateJSONEther(JsonBuilder *js, const Packet *p, const Flow *f) } jb_close(info.dst); jb_close(info.src); - jb_set_object(js, "dest_macs", info.dst); - jb_set_object(js, "src_macs", info.src); + /* case is handling netflow too so may need to revert */ + if (dir == LOG_DIR_FLOW_TOCLIENT) { + jb_set_object(js, "dest_macs", info.src); + jb_set_object(js, "src_macs", info.dst); + } else { + DEBUG_VALIDATE_BUG_ON(dir != LOG_DIR_FLOW_TOSERVER && dir != LOG_DIR_FLOW); + jb_set_object(js, "dest_macs", info.dst); + jb_set_object(js, "src_macs", info.src); + } jb_free(info.dst); jb_free(info.src); jb_close(js); @@ -863,7 +899,7 @@ JsonBuilder *CreateEveHeader(const Packet *p, enum OutputJsonLogDirection dir, jb_set_string(js, "pkt_src", PktSrcToString(p->pkt_src)); if (eve_ctx != NULL) { - EveAddCommonOptions(&eve_ctx->cfg, p, f, js); + EveAddCommonOptions(&eve_ctx->cfg, p, f, js, dir); } return js; diff --git a/src/output-json.h b/src/output-json.h index 6fe6c5898d..74d07bb8a2 100644 --- a/src/output-json.h +++ b/src/output-json.h @@ -110,8 +110,8 @@ OutputInitResult OutputJsonLogInitSub(ConfNode *conf, OutputCtx *parent_ctx); TmEcode JsonLogThreadInit(ThreadVars *t, const void *initdata, void **data); TmEcode JsonLogThreadDeinit(ThreadVars *t, void *data); -void EveAddCommonOptions(const OutputJsonCommonSettings *cfg, - const Packet *p, const Flow *f, JsonBuilder *js); +void EveAddCommonOptions(const OutputJsonCommonSettings *cfg, const Packet *p, const Flow *f, + JsonBuilder *js, enum OutputJsonLogDirection dir); void EveAddMetadata(const Packet *p, const Flow *f, JsonBuilder *js); int OutputJSONMemBufferCallback(const char *str, size_t size, void *data);