qmake: use even fewer magic numbers

De-unroll the loop over the "interesting" keyword ignore comments by
using the existing array of their names. Replace magic numbers by
strlen() calls. Use local starts_with() instead of strncmp() when
comparing with fixed-size constant string literals, to avoid repeating
the fixed string's lengths for the third argument of strncmp().

Task-number: QTBUG-55458
Change-Id: If458aced382948fb719d984702857fb2171c87ee
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Lars Knoll <lars.knoll@qt.io>
This commit is contained in:
Marc Mutz 2021-11-22 08:42:49 +01:00
parent ed343669f7
commit f8ab1f0576

View File

@ -932,6 +932,13 @@ bool QMakeSourceFileInfo::findMocs(SourceFile *file)
NumKeywords
};
static const char keywords[][19] = {
"Q_OBJECT",
"Q_GADGET",
"Q_NAMESPACE",
"Q_NAMESPACE_EXPORT",
};
static_assert(std::size(keywords) == NumKeywords);
bool ignore[NumKeywords] = {};
/* qmake ignore Q_GADGET */
/* qmake ignore Q_OBJECT */
@ -957,30 +964,26 @@ bool QMakeSourceFileInfo::findMocs(SourceFile *file)
x = SKIP_BSNL(y + 1);
for (; x < buffer_len; x = SKIP_BSNL(x + 1)) {
if (buffer[x] == 't' || buffer[x] == 'q') { // ignore
if(buffer_len >= (x + 20) &&
!strncmp(buffer + x + 1, "make ignore Q_OBJECT", 20)) {
debug_msg(2, "Mocgen: %s:%d Found \"qmake ignore Q_OBJECT\"",
file->file.real().toLatin1().constData(), line_count);
x += 20;
ignore[Q_OBJECT_Keyword] = true;
} else if(buffer_len >= (x + 20) &&
!strncmp(buffer + x + 1, "make ignore Q_GADGET", 20)) {
debug_msg(2, "Mocgen: %s:%d Found \"qmake ignore Q_GADGET\"",
file->file.real().toLatin1().constData(), line_count);
x += 20;
ignore[Q_GADGET_Keyword] = true;
} else if (buffer_len >= (x + 23) &&
!strncmp(buffer + x + 1, "make ignore Q_NAMESPACE", 23)) {
debug_msg(2, "Mocgen: %s:%d Found \"qmake ignore Q_NAMESPACE\"",
file->file.real().toLatin1().constData(), line_count);
x += 23;
ignore[Q_NAMESPACE_Keyword] = true;
} else if (buffer_len >= (x + 30) &&
!strncmp(buffer + x + 1, "make ignore Q_NAMESPACE_EXPORT", 30)) {
debug_msg(2, "Mocgen: %s:%d Found \"qmake ignore Q_NAMESPACE_EXPORT\"",
file->file.real().toLatin1().constData(), line_count);
x += 30;
ignore[Q_NAMESPACE_EXPORT_Keyword] = true;
const char tag[] = "make ignore ";
const auto starts_with = [](const char *haystack, const char *needle) {
return strncmp(haystack, needle, strlen(needle)) == 0;
};
const auto is_ignore = [&](const char *keyword) {
return buffer_len >= int(x + strlen(tag) + strlen(keyword)) &&
starts_with(buffer + x + 1, tag) &&
starts_with(buffer + x + 1 + strlen(tag), keyword);
};
int interest = 0;
for (const char *keyword : keywords) {
if (is_ignore(keyword)){
debug_msg(2, "Mocgen: %s:%d Found \"q%s%s\"",
file->file.real().toLatin1().constData(), line_count,
tag, keyword);
x += strlen(tag);
x += strlen(keyword);
ignore[interest] = true;
}
++interest;
}
} else if (buffer[x] == '*') {
extralines = 0;
@ -1008,17 +1011,15 @@ bool QMakeSourceFileInfo::findMocs(SourceFile *file)
int morelines = 0;
int y = skipEscapedLineEnds(buffer, buffer_len, x + 1, &morelines);
if (buffer[y] == 'Q') {
static const char interesting[][19] = { "Q_OBJECT", "Q_GADGET", "Q_NAMESPACE", "Q_NAMESPACE_EXPORT" };
static_assert(std::size(interesting) == NumKeywords);
for (int interest = 0; interest < NumKeywords; ++interest) {
if (ignore[interest])
continue;
int matchlen = 0, extralines = 0;
size_t needle_len = strlen(interesting[interest]);
size_t needle_len = strlen(keywords[interest]);
Q_ASSERT(needle_len <= INT_MAX);
if (matchWhileUnsplitting(buffer, buffer_len, y,
interesting[interest],
keywords[interest],
static_cast<int>(needle_len),
&matchlen, &extralines)
&& y + matchlen < buffer_len