IMAP protocol parser, logger and sticky buffers v2#14822
Conversation
This introduces a parser for IMAP protocol. Ticket OISF#8276
This introduces a logger for IMAP protocol. Ticket OISF#8276
This implement the following sticky buffers for IMAP protocol: - imap.request - imap.response - imap.email.direction - imap.email.header - imap.email.header.name - imap.email.header.value - imap.email.body Ticket OISF#8276
|
NOTE: This PR may contain new authors. |
| Email headers are normalized before matching: | ||
|
|
||
| - **Header names** are converted to lowercase with hyphens replaced by underscores | ||
| (e.g. ``Content-Type`` becomes ``content_type``). |
There was a problem hiding this comment.
Because we do that for smtp.
There was a problem hiding this comment.
How so ? Where do you see this in the code ?
There was a problem hiding this comment.
See output-json-email-common.c:
struct {
const char *config_field;
const char *email_field;
uint32_t flags;
} email_fields[] = {
{ "reply_to", "reply-to", LOG_EMAIL_DEFAULT },
{ "bcc", "bcc", LOG_EMAIL_COMMA|LOG_EMAIL_EXTENDED },
{ "message_id", "message-id", LOG_EMAIL_EXTENDED },
{ "subject", "subject", LOG_EMAIL_EXTENDED },
{ "x_mailer", "x-mailer", LOG_EMAIL_EXTENDED },
{ "user_agent", "user-agent", LOG_EMAIL_EXTENDED },
{ "received", "received", LOG_EMAIL_ARRAY },
{ "x_originating_ip", "x-originating-ip", LOG_EMAIL_DEFAULT },
{ "in_reply_to", "in-reply-to", LOG_EMAIL_DEFAULT },
{ "references", "references", LOG_EMAIL_DEFAULT },
{ "importance", "importance", LOG_EMAIL_DEFAULT },
{ "priority", "priority", LOG_EMAIL_DEFAULT },
{ "sensitivity", "sensitivity", LOG_EMAIL_DEFAULT },
{ "organization", "organization", LOG_EMAIL_DEFAULT },
{ "content_md5", "content-md5", LOG_EMAIL_DEFAULT },
{ "date", "date", LOG_EMAIL_DEFAULT },
{ NULL, NULL, LOG_EMAIL_DEFAULT},
};
Also, @jasonish asked me to do this for compatibility with elasticsearch.
There was a problem hiding this comment.
This is for output, not for detection, right ?
There was a problem hiding this comment.
I think Philippe is correct in this interpretation.
| quic-keywords | ||
| nfs-keywords | ||
| smtp-keywords | ||
| imap-keywords |
There was a problem hiding this comment.
I think there is more doc than keywords, there is a section where we show an example json output of an imap event
There was a problem hiding this comment.
So, the idea would be to also add an output examplo to the https://docs.suricata.io/en/latest/output/eve/index.html chapter.
| JsonArpLogRegister(); | ||
| /* IMAP JSON logger. */ | ||
| OutputRegisterTxSubModule(LOGGER_JSON_TX, "eve-log", "JsonImapLog", "eve-log.imap", | ||
| OutputJsonLogInitSub, ALPROTO_IMAP, JsonGenericDirFlowLogger, JsonLogThreadInit, |
There was a problem hiding this comment.
I wonder if JsonGenericDirFlowLogger is the best for the cases where we see files/emails in both directions...
There was a problem hiding this comment.
I've added a direction field to the email object that indicates whether it's to_server or to_client.
There was a problem hiding this comment.
Yes, I am not sure I like it
There was a problem hiding this comment.
Can you elaborate on what you don't like, exactly?
There was a problem hiding this comment.
| } | ||
|
|
||
| fn parse_command_keyword(i: &[u8]) -> IResult<&[u8], ImapCommand> { | ||
| alt(( |
There was a problem hiding this comment.
why alt of alt ?
This looks inefficient compared to a switch over strings with rust being clever
There was a problem hiding this comment.
Bcause alt accepts a maximum of 21 parsers.
There was a problem hiding this comment.
Yes, that means alt is not the right way to do this
| fn parse_quoted_string(i: &[u8]) -> IResult<&[u8], &[u8]> { | ||
| delimited( | ||
| char('"'), | ||
| take_while(|c| c != b'"' && c != b'\r' && c != b'\n'), |
There was a problem hiding this comment.
Can we not escape quotes in a quoted string ?
| "type": "array", | ||
| "description": "Array of IMAP response lines in this transaction", | ||
| "items": { | ||
| "type": "string" |
There was a problem hiding this comment.
you can add the suricata section with the keywords ;-)
| pub requests: Vec<ImapMessage>, | ||
| pub responses: Vec<ImapMessage>, | ||
| pub request_lines: Vec<Vec<u8>>, | ||
| pub response_lines: Vec<Vec<u8>>, |
There was a problem hiding this comment.
Do you bound the number of response lines somehow ?
There was a problem hiding this comment.
You should :-p https://redmine.openinfosecfoundation.org/issues/8212
| if SCAppLayerParserConfParserEnabled(ip_proto_str.as_ptr(), parser.name) != 0 { | ||
| let _ = AppLayerRegisterParser(&parser, alproto); | ||
| } | ||
| if let Some(val) = conf_get("app-layer.protocols.imap.max-tx") { |
There was a problem hiding this comment.
Can we have pipelined transactions or such ?
| if SCAppLayerProtoDetectConfProtoDetectionEnabled(ip_proto_str.as_ptr(), parser.name) != 0 { | ||
| let alproto = applayer_register_protocol_detection(&parser, 1); | ||
| ALPROTO_IMAP = alproto; | ||
| if SCAppLayerParserConfParserEnabled(ip_proto_str.as_ptr(), parser.name) != 0 { |
There was a problem hiding this comment.
We do not have port-indpendent detection with CAPABILITY pattern anymore ?
There was a problem hiding this comment.
Yes we do now and you are removing it... Was this intended ?
catenacyber
left a comment
There was a problem hiding this comment.
Awesome big work
I think there are quite some things to complete
My main remarks would be
- how much verbose/configurable do we want the logs to be ?
- can we have the existing keywords like
email.fromwork also with IMAP ?
|
Information: QA ran without warnings. Pipeline = 29614 |
jufajardini
left a comment
There was a problem hiding this comment.
Left some inline comments, sharing review now to allow for the new iteration to happen!
| content-inspect-window: 4096 | ||
| imap: | ||
| enabled: detection-only | ||
| enabled: yes |
There was a problem hiding this comment.
minor, but: is the plan to have it enabled by default? If so, then I agree that output verbosity is something to consider carefully.
| - Encrypted quic traffic bypass is now independently controlled through | ||
| ``app-layer.protocols.quic.encryption-handling`` setting. The setting can either | ||
| be ``bypass``, ``track-only`` or ``full``. | ||
| - IMAP parser, logger and sticky buffers have been introduced. |
There was a problem hiding this comment.
If it will be enabled by default, I think it is worth it mentioning that here.
There was a problem hiding this comment.
In general this is not a changelog, so it should only mention breaking changes or other things ppl should really be aware of.
| JsonArpLogRegister(); | ||
| /* IMAP JSON logger. */ | ||
| OutputRegisterTxSubModule(LOGGER_JSON_TX, "eve-log", "JsonImapLog", "eve-log.imap", | ||
| OutputJsonLogInitSub, ALPROTO_IMAP, JsonGenericDirFlowLogger, JsonLogThreadInit, |
There was a problem hiding this comment.
Can you elaborate on what you don't like, exactly?
| .. table:: **Direction values for imap.email.direction** | ||
|
|
||
| ===== =========== | ||
| Value Name | ||
| ===== =========== | ||
| 0 to_server | ||
| 1 to_client | ||
| ===== =========== | ||
|
|
There was a problem hiding this comment.
If we want users to use to_server and to_client, wouldn't it be simpler to remove this table?
| Email headers are normalized before matching: | ||
|
|
||
| - **Header names** are converted to lowercase with hyphens replaced by underscores | ||
| (e.g. ``Content-Type`` becomes ``content_type``). |
There was a problem hiding this comment.
I think Philippe is correct in this interpretation.
| JsonArpLogRegister(); | ||
| /* IMAP JSON logger. */ | ||
| OutputRegisterTxSubModule(LOGGER_JSON_TX, "eve-log", "JsonImapLog", "eve-log.imap", | ||
| OutputJsonLogInitSub, ALPROTO_IMAP, JsonGenericDirFlowLogger, JsonLogThreadInit, |
There was a problem hiding this comment.
| quic-keywords | ||
| nfs-keywords | ||
| smtp-keywords | ||
| imap-keywords |
There was a problem hiding this comment.
So, the idea would be to also add an output examplo to the https://docs.suricata.io/en/latest/output/eve/index.html chapter.
|
Replaced with #14995 |
Link to ticket: https://redmine.openinfosecfoundation.org/issues/8276
Previous PR: #14792
Describe changes:
Content-DispositionheaderSV_BRANCH=OISF/suricata-verify#2908