Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Pcap conditional v2.2.6 #6389

Closed

Conversation

scottfgjordan
Copy link
Contributor

Make sure these boxes are signed before submitting your Pull Request -- thank you.

Link to redmine ticket:

Describe changes:

suricata-verify-pr: 542

regit and others added 23 commits September 17, 2021 13:43
Add an option to only write to pcap packets with alerts and flow
that have alerted.
It will be used later when multiple writing operations will be
necessary.
We add a flag to packet to be able to know if this packet was the
first one to get alerts on the flow.
This patch optionally adds packet header to the TCP segment
and update the for each segment function by changing the
callback.

This patch is based on the work by Scott Jordan <scottfgjordan@gmail.com>
This patch update the alert mode of pcap logging.

It uses the packet header data added to the TCP segments
to build packets corresponding to the acked data that did trigger
the alert. It then write it to the pcap file before starting to
dump all packet for the flow that did alert.
In alert mode, we need to write the root packet to the pcap
file instead of the packet that did trigger the alert.
This patch adds the tag as logging condition. If this option is
used all tagged packets are written to the pcap.
TCP memory cap was not taking into account the memory that can
be used by realloc of Packet headers in TCP segments.
This patch adds a function to get the current pcap file name that
will be used to current packet.
This patch updates EVE alerts to add pcap output filename when pcap
capture is done in multi mode. In other mode, the pcap file can be
determined by checking the timestamps.
This patch updates tcp segment dumping to dump segments
from both sides of the session in order when capturing
alerts and tags.
We may need to know that a packet has been tagged but is the
first one (and thus is not tagged).
We were missing the first packet when using condition pcap logging
in tag mode as it was not tagged. As a result we were not getting
the stream data triggering the alert in the pcap file.
As Suricata is not supporting pcap-ng we have to stick with one single
datalink type for the capture if ever we want to do pcap logging.
Assuming this, this patch introduces a function to set the link
type globally. This will be used with pcap conditional logging
to get the logging of TCP segments with the correct link type.
Set pseudo packet datalink to the global one. This fixes the case
where the pcap handle is open with information coming from a
pseudo packet. Without this, we did end up in most cases with
an Ethernet packet being written in a Raw pcap.
@scottfgjordan scottfgjordan requested review from norg and a team as code owners September 17, 2021 20:46
@victorjulien victorjulien mentioned this pull request Sep 18, 2021
3 tasks
@codecov
Copy link

codecov bot commented Sep 18, 2021

Codecov Report

Merging #6389 (44b7040) into master (b3f447a) will decrease coverage by 0.03%.
The diff coverage is 62.00%.

@@            Coverage Diff             @@
##           master    #6389      +/-   ##
==========================================
- Coverage   76.96%   76.92%   -0.04%     
==========================================
  Files         611      612       +1     
  Lines      186077   186338     +261     
==========================================
+ Hits       143214   143344     +130     
- Misses      42863    42994     +131     
Flag Coverage Δ
fuzzcorpus 52.58% <10.54%> (-0.13%) ⬇️
suricata-verify 51.74% <69.08%> (+0.09%) ⬆️
unittests 63.03% <6.20%> (-0.08%) ⬇️

Flags with carried forward coverage won't be shown. Click here to find out more.

"Pcap logging with multiple link type is not supported.");
} else {
/* In multi mode, only pcap conditional is not supported as a flow timeout
* will trigger packet logging with potentially invalid with. In regular
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The first sensor is missing something after with or should be reworded.

/* Log alerted flow or tagged flow */
switch (ptd->pcap_log->conditional) {
case LOGMODE_COND_ALERTS:
if (p->alerts.cnt || (p->flow && FlowHasAlerts(p->flow))) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Could (should?) PKT_FIRST_ALERTS be used here?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It could be, but isn't necessary. The PKT_FIRST_ALERTS flag is used to determine when the data held in the tcp segments should be dumped (i.e. before the first alerted packet is dumped, otherwise will be out of order). The FlowSetHasAlertsFlag is set in the same block as p->flags |= PKT_FIRST_ALERTS.

SCLogError(SC_ERR_FSEEK, "fseek failed: %s", strerror(errno));
return TM_ECODE_FAILED;
}
if (fwrite(comp->buffer, 1, out_size, comp->file) < out_size) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can out_size be zero? See conditional at L528.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes it can be zero. out_size is equal to the return of the LZ4F_compressUpdate which is the number of bytes written in to the compression buffer. From the function documentation "@return: number of bytes written into 'dstBuffer' (it can be zero, meaning input data was just buffered) or an error code if it fails".

I don't believe any functionality in this block has actually changed from the original log-pcap.c file, it has just been moved to be within the PcapWrite function rather than the PcapLog function.

MemBufferWriteRaw(pctx->buf, buf, buflen);

PcapWrite(pctx->pl, pctx->connp, (uint8_t *)pctx->buf->buffer,
seg->pcap_hdr_storage->pktlen + buflen);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggst using pctx->pl->h->len instead

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Agreed.

#endif
}
if (ret != TM_ECODE_OK)
return ret;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Leaving the pcap log lock held ... need PcapLogUnlock(pl)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also ... missing call (i think?) to PCAPLOG_PROFILE_END() when returning

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good catch, thanks!

@@ -950,6 +1111,12 @@ static TmEcode PcapLogDataInit(ThreadVars *t, const void *initdata, void **data)

*data = (void *)td;

if (IsTcpSessionDumpingEnabled()) {
td->buf = MemBufferCreateNew(65537);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggest a comment for why this is the proper value? Should it be configurable? should it be a #define?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Moved to a define in log-pcap.h, as for the particular value, would need to ask @regit as I am not sure why that was selected versus 65535 which appears to be the common OUTPUT_BUFFER_SIZE defined value in other log- files that call MemBufferCreateNew. Will leave as 65537 for now.

} else if (strcasecmp(s_conditional, "all") != 0) {
SCLogError(SC_ERR_INVALID_ARGUMENT,
"log-pcap: invalid conditional \"%s\". Valid options: \"all\", "
"or \"alerts\" mode ",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

tag is valid too

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good catch.

pl->conditional = LOGMODE_COND_TAG;
EnableTcpSessionDumping();
} else if (strcasecmp(s_conditional, "all") != 0) {
SCLogError(SC_ERR_INVALID_ARGUMENT,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggest FatalError here.

* need to check that this is sufficient and allocate more memory if
* not.
*/
if (GET_PKT_LEN(rp) - p->payload_len > seg->pcap_hdr_storage->alloclen) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggest using seg->pcap_hdr_storage->pktlen here instead.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

and also on L592

@scottfgjordan
Copy link
Contributor Author

Working on addressing feedback ASAP, do you know if there were any QA issues similar to the test ran from the previous PR #6154 (comment) @jlucovsky? I will need to setup a similar test locally to see If I can get to the source of the issue.

@scottfgjordan scottfgjordan mentioned this pull request Sep 24, 2021
3 tasks
@scottfgjordan
Copy link
Contributor Author

Replaced by: #6408

jufajardini added a commit to jufajardini/suricata that referenced this pull request Dec 15, 2023
The ConsolidatedDataRow struct had a length field that wasn't truly
used.

Related to
Bug OISF#6389
jufajardini added a commit to jufajardini/suricata that referenced this pull request Dec 15, 2023
The `ConsolidatedDataRow` struct had a `length` field that wasn't truly
used.

Related to
Bug OISF#6389
victorjulien pushed a commit to victorjulien/suricata that referenced this pull request Dec 19, 2023
The `ConsolidatedDataRow` struct had a `length` field that wasn't truly
used.

Related to
Bug OISF#6389
jufajardini added a commit to jufajardini/suricata that referenced this pull request Dec 19, 2023
The `ConsolidatedDataRow` struct had a `length` field that wasn't truly
used.

Related to
Bug OISF#6389

(cherry picked from commit 1afb485)
victorjulien pushed a commit to victorjulien/suricata that referenced this pull request Dec 21, 2023
The `ConsolidatedDataRow` struct had a `length` field that wasn't truly
used.

Related to
Bug OISF#6389

(cherry picked from commit 1afb485)
jufajardini added a commit to jufajardini/suricata that referenced this pull request Jan 4, 2024
Found by oss-fuzz with quadfuzz.

Cf https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=63113

According to PostgreSQL documentation the maximum number of rows can be
the maximum of tuples that can fit onto max u32 pages - 4,294,967,295 (cf
https://www.postgresql.org/docs/current/limits.html). Some rough
calculations for that indicate that this could go over max u32, so
updating the data_row data type to u64.

Bug OISF#6389
jufajardini added a commit to jufajardini/suricata that referenced this pull request Jan 4, 2024
Found by oss-fuzz with quadfuzz.

Cf https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=63113

According to PostgreSQL documentation the maximum number of rows can be
the maximum of tuples that can fit onto max u32 pages - 4,294,967,295 (cf
https://www.postgresql.org/docs/current/limits.html). Some rough
calculations for that indicate that this could go over max u32, so
updating the data_row data type to u64.

Bug OISF#6389
victorjulien pushed a commit to victorjulien/suricata that referenced this pull request Jan 8, 2024
Found by oss-fuzz with quadfuzz.

Cf https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=63113

According to PostgreSQL documentation the maximum number of rows can be
the maximum of tuples that can fit onto max u32 pages - 4,294,967,295 (cf
https://www.postgresql.org/docs/current/limits.html). Some rough
calculations for that indicate that this could go over max u32, so
updating the data_row data type to u64.

Bug OISF#6389
victorjulien pushed a commit to victorjulien/suricata that referenced this pull request Jan 9, 2024
Found by oss-fuzz with quadfuzz.

Cf https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=63113

According to PostgreSQL documentation the maximum number of rows can be
the maximum of tuples that can fit onto max u32 pages - 4,294,967,295 (cf
https://www.postgresql.org/docs/current/limits.html). Some rough
calculations for that indicate that this could go over max u32, so
updating the data_row data type to u64.

Bug OISF#6389

(cherry picked from commit 8d3de85)
jufajardini added a commit to jufajardini/suricata that referenced this pull request Jan 9, 2024
Found by oss-fuzz with quadfuzz.

Cf https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=63113

According to PostgreSQL documentation the maximum number of rows can be
the maximum of tuples that can fit onto max u32 pages - 4,294,967,295 (cf
https://www.postgresql.org/docs/current/limits.html). Some rough
calculations for that indicate that this could go over max u32, so
updating the data_row data type to u64.

Bug OISF#6389

(cherry picked from commit 8d3de85)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Development

Successfully merging this pull request may close these issues.

3 participants