From 2e8d50a9bd3eb13c239b569c056fe5babe585638 Mon Sep 17 00:00:00 2001 From: Jeff Lucovsky Date: Sun, 16 Aug 2026 08:34:19 -0400 Subject: [PATCH] ftp: point truncated lines at the unconsumed remainder When a line exceeds the configured maximum length and contains no LF, FTPGetLineForDirection emitted a window starting at the beginning of the stream slice rather than at the unconsumed remainder. If a complete command had already been taken from the same slice, that window was shifted left by the consumed count: it began inside the previous command and stopped short of the end of the long one. The command MPM match, the per-transaction request copy and the port_line capture all ran over those stale bytes, so a long command hidden behind a short one in the same segment was classified and logged as the previous command. The response direction had the same problem. The LF-found branch already derives the line from input->buf + o_consumed; do the same here, and advance consumed so the cursor still describes the slice it was handed. Issue: 8859 --- src/app-layer-ftp.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/app-layer-ftp.c b/src/app-layer-ftp.c index cd59f348e8..e41f6ec75d 100644 --- a/src/app-layer-ftp.c +++ b/src/app-layer-ftp.c @@ -290,9 +290,12 @@ static AppLayerResult FTPGetLineForDirection( if (lf_idx == NULL) { if (!(*current_line_truncated) && (uint32_t)input->len >= ftp_max_line_len) { *current_line_truncated = true; - line->buf = input->buf; + line->buf = input->buf + input->consumed; line->len = ftp_max_line_len; line->delim_len = 0; + /* No caller reads consumed after this; advance it so the cursor + * still describes the slice it was handed. */ + input->consumed += input->len; input->len = 0; SCReturnStruct(APP_LAYER_OK); }