From 3b8ea78570edcf81820f0e5e053337ecb42bf086 Mon Sep 17 00:00:00 2001 From: Oswald Buddenhagen Date: Thu, 7 Mar 2013 21:47:42 +0100 Subject: make split_value_list() mostly sane don't count parentheses, don't nest quotes, don't create empty elements. the backslash still escapes only quotes (and itself) - $$list() (one of the main users of this function) is commonly used with (windows) path lists, so letting it escape anything would make a royal mess. Change-Id: I29252fbe14fd6d28217450ec41cf8acfb2e30681 Reviewed-by: Joerg Bornemann Reviewed-by: Oswald Buddenhagen (cherry picked from qtbase/6c22b9b3e86d1617665f7b81b105c032f43c6d72) (cherry picked from qtbase/a5c2ab47867a558d6f8f62126fb8e4f2777cfe06) --- src/linguist/shared/qmakeevaluator.cpp | 69 +++++++++++++++++++--------------- 1 file changed, 38 insertions(+), 31 deletions(-) diff --git a/src/linguist/shared/qmakeevaluator.cpp b/src/linguist/shared/qmakeevaluator.cpp index ce2a5d19e..ef86f003f 100644 --- a/src/linguist/shared/qmakeevaluator.cpp +++ b/src/linguist/shared/qmakeevaluator.cpp @@ -264,48 +264,55 @@ ProStringList QMakeEvaluator::split_value_list(const QString &vals, const ProFil { QString build; ProStringList ret; - QStack quote; - - const ushort SPACE = ' '; - const ushort LPAREN = '('; - const ushort RPAREN = ')'; - const ushort SINGLEQUOTE = '\''; - const ushort DOUBLEQUOTE = '"'; - const ushort BACKSLASH = '\\'; if (!source) source = currentProFile(); - ushort unicode; const QChar *vals_data = vals.data(); const int vals_len = vals.length(); - int parens = 0; + ushort quote = 0; + bool hadWord = false; for (int x = 0; x < vals_len; x++) { - unicode = vals_data[x].unicode(); - if (x != (int)vals_len-1 && unicode == BACKSLASH && - (vals_data[x+1].unicode() == SINGLEQUOTE || vals_data[x+1].unicode() == DOUBLEQUOTE)) { - build += vals_data[x++]; //get that 'escape' - } else if (!quote.isEmpty() && unicode == quote.top()) { - quote.pop(); - } else if (unicode == SINGLEQUOTE || unicode == DOUBLEQUOTE) { - quote.push(unicode); - } else if (unicode == RPAREN) { - --parens; - } else if (unicode == LPAREN) { - ++parens; + ushort unicode = vals_data[x].unicode(); + if (unicode == quote) { + quote = 0; + continue; } - - if (!parens && quote.isEmpty() && vals_data[x] == SPACE) { - ret << ProString(build).setSource(source); - build.clear(); - } else { - build += vals_data[x]; + switch (unicode) { + case '"': + case '\'': + quote = unicode; + hadWord = true; + continue; + case ' ': + case '\t': + if (!quote) { + if (hadWord) { + ret << ProString(build).setSource(source); + build.clear(); + hadWord = false; + } + continue; + } + build += QChar(unicode); + break; + case '\\': + if (x + 1 != vals_len) { + ushort next = vals_data[++x].unicode(); + if (next == '\'' || next == '"' || next == '\\') + unicode = next; + else + --x; + } + // fallthrough + default: + hadWord = true; + build += QChar(unicode); + break; } } - if (!build.isEmpty()) + if (hadWord) ret << ProString(build).setSource(source); - if (parens) - deprecationWarning(fL1S("Unmatched parentheses are deprecated.")); return ret; } -- cgit v1.2.1