From ad70a5c682076fdf693370e4c7444df53c60ef49 Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Thu, 16 Feb 2023 23:09:47 +0100 Subject: [PATCH] QMessagePattern: don't use strncpy() When Qt is configured to return nullptr from isNull() QStrings (QT5_NULL_STRINGS != 1), then we'd be feeding a nullptr src into strncpy(), which is UB. I couldn't rule the case of a null QString lexeme out with local reasoning, seeing as the code is in the else branch of an if (lexeme.startsWith(~~~) && lexeme.endsWith(~~~)), so it might be null. Instead of porting to qstrncpy(), which can deal with a nullptr src (albeit up to recently, badly), note that the strncpy + the char[] allocation is a qstrdup(), so use that instead. This also does away with the queasiness of taking the size() of a UTF-16 string to limit strncpy() for the L1-recoded version (which, in this instance is safe, as toLatin1().constData() is NUL-terminated, but in some other instances was not). As a drive-by, make sure we don't leak the strdup()'ed string if the emplace_back() fails. Amends be98fa32c7d56ea91359b647a329356fa44eca04. Qt 5 is not affected, as constData() never returns nullptr there. Change-Id: I178d356e560d2749cd6ce0b9364c710a2d117304 Reviewed-by: Volker Hilsheimer (cherry picked from commit 4a9e918d4ebdd9f7ea641e2b0f12a48c5f619acb) Reviewed-by: Qt Cherry-pick Bot --- src/corelib/global/qlogging.cpp | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/src/corelib/global/qlogging.cpp b/src/corelib/global/qlogging.cpp index cf38a90151b..a0b8432b5b3 100644 --- a/src/corelib/global/qlogging.cpp +++ b/src/corelib/global/qlogging.cpp @@ -1338,11 +1338,8 @@ void QMessagePattern::setPattern(const QString &pattern) .arg(lexeme); } } else { - char *literal = new char[lexeme.size() + 1]; - strncpy(literal, lexeme.toLatin1().constData(), lexeme.size()); - literal[lexeme.size()] = '\0'; - literalsVar.emplace_back(literal); - tokens[i] = literal; + using UP = std::unique_ptr; + tokens[i] = literalsVar.emplace_back(UP(qstrdup(lexeme.toLatin1().constData()))).get(); } } if (nestedIfError)