[PATCH] gpg-interface: trim only CR characters that precede LF
- From
- Okhuomon Ajayi <okhuomonajayi54@gmail.com>
- Date
- Oct 16, 2025, 18:44 UTC
- Message-ID
- <20251016184420.78268-1-okhuomonajayi54@gmail.com>
The current implementation of remove_cr_after() drops every carriage return (CR) it finds, even when the CR is not part of a CRLF sequence. This can damage data that legitimately contains standalone CR bytes, such as binary payloads or text formatted for older systems.
Update remove_cr_after() to remove a CR only when it is immediately followed by an LF. This keeps Windows-style CRLF normalization intact while preserving lone CR characters that are part of the data itself.
Signed-off-by: Okhuomon Ajayi <okhuomonajayi54@gmail.com> --- gpg-interface.c | 25 ++++++++++++++++--------- 1 file changed, 16 insertions(+), 9 deletions(-)
diff --git a/gpg-interface.c b/gpg-interface.c index 2f4f0e32cb..c961607444 100644 --- a/gpg-interface.c +++ b/gpg-interface.c @@ -965,19 +965,22 @@ int sign_buffer(struct strbuf *buffer, struct strbuf *signature, const char *sig } /* - * Strip CR from the line endings, in case we are on Windows. - * NEEDSWORK: make it trim only CRs before LFs and rename + * Trim CR characters only when they appear before LF (\r\n) line endings. + * This avoids removing legitimate lone CRs from teh content. */ -static void remove_cr_after(struct strbuf *buffer, size_t offset) +static void trim_cr_before_lf(struct strbuf *buffer, size_t offset) { size_t i, j; for (i = j = offset; i < buffer->len; i++) { - if (buffer->buf[i] != '\r') { + /* skip CR only if it comes right before LF */ + if (buffer->buf[i] == '\r' && i + 1 < buffer->len && buffer->buf[i+1] == '\n') + continue; + if (i != j) buffer->buf[j] = buffer->buf[i]; j++; - } + } strbuf_setlen(buffer, j); } @@ -1023,8 +1026,10 @@ static int sign_buffer_gpg(struct strbuf *buffer, struct strbuf *signature, } strbuf_release(&gpg_status); - /* Strip CR from the line endings, in case we are on Windows. */ - remove_cr_after(signature, bottom); + /* Trim carriage returns (CR) only when they appear before line feeds (LF),. + * mainly for handling Windows-style line endings + */ + trim_cr_before_lf(signature, bottom); return 0; } @@ -1110,8 +1115,10 @@ static int sign_buffer_ssh(struct strbuf *buffer, struct strbuf *signature, ssh_signature_filename.buf); goto out; } - /* Strip CR from the line endings, in case we are on Windows. */ - remove_cr_after(signature, bottom); + /* Trim carriage returns (CR) only when they appear before line feeds (LF), + * mainly for handling Windows-style line endings. + */ + trim_cr_before_lf(signature, bottom); out: if (key_file)
-- 2.43.0