fixed handling of incomplete char/string literals in `isPrefixStringCharLiteral()` - also optimized it a bit (#4541)
* fixed handling of incomplete char/string literals in `isPrefixStringCharLiteral()` - also optimized it a bit / added tests for `isStringLiteral()` and `isCharLiteral()` * utils.h: early out in `isStringCharLiteral()` to avoid the loop
This commit is contained in:
parent
c5a226470a
commit
d1bfae989e
22
lib/utils.h
22
lib/utils.h
|
@ -89,15 +89,31 @@ bool endsWith(const std::string& str, const char (&end)[N])
|
|||
|
||||
inline static bool isPrefixStringCharLiteral(const std::string &str, char q, const std::string& p)
|
||||
{
|
||||
// str must be at least the prefix plus the start and end quote
|
||||
if (str.length() < p.length() + 2)
|
||||
return false;
|
||||
|
||||
// check for end quote
|
||||
if (!endsWith(str, q))
|
||||
return false;
|
||||
if ((str.length() + 1) > p.length() && (str.compare(0, p.size() + 1, p + q) == 0))
|
||||
return true;
|
||||
return false;
|
||||
|
||||
// check for start quote
|
||||
if (str[p.size()] != q)
|
||||
return false;
|
||||
|
||||
// check for prefix
|
||||
if (str.compare(0, p.size(), p) != 0)
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
inline static bool isStringCharLiteral(const std::string &str, char q)
|
||||
{
|
||||
// early out to avoid the loop
|
||||
if (!endsWith(str, q))
|
||||
return false;
|
||||
|
||||
static const std::array<std::string, 5> suffixes{"", "u8", "u", "U", "L"};
|
||||
for (const std::string & p: suffixes) {
|
||||
if (isPrefixStringCharLiteral(str, q, p))
|
||||
|
|
|
@ -30,6 +30,8 @@ private:
|
|||
void run() override {
|
||||
TEST_CASE(isValidGlobPattern);
|
||||
TEST_CASE(matchglob);
|
||||
TEST_CASE(isStringLiteral);
|
||||
TEST_CASE(isCharLiteral);
|
||||
}
|
||||
|
||||
void isValidGlobPattern() const {
|
||||
|
@ -68,6 +70,114 @@ private:
|
|||
ASSERT_EQUALS(true, ::matchglob("?y?", "xyz"));
|
||||
ASSERT_EQUALS(true, ::matchglob("?/?/?", "x/y/z"));
|
||||
}
|
||||
|
||||
void isStringLiteral() const {
|
||||
// empty
|
||||
ASSERT_EQUALS(false, ::isStringLiteral(""));
|
||||
|
||||
// no literals
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u8"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("U"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("L"));
|
||||
|
||||
// incomplete string literals
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("\""));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u8\""));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u\""));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("U\""));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("L\""));
|
||||
|
||||
// valid string literals
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("\"\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("u8\"\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("u\"\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("U\"\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("L\"\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("\"t\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("u8\"t\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("u\"t\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("U\"t\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("L\"t\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("\"test\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("u8\"test\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("u\"test\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("U\"test\""));
|
||||
ASSERT_EQUALS(true, ::isStringLiteral("L\"test\""));
|
||||
|
||||
// incomplete char literals
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u8'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("U'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("L'"));
|
||||
|
||||
// valid char literals
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("'t'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u8't'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u't'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("U't'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("L't'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("'test'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u8'test'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("u'test'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("U'test'"));
|
||||
ASSERT_EQUALS(false, ::isStringLiteral("L'test'"));
|
||||
}
|
||||
|
||||
void isCharLiteral() const {
|
||||
// empty
|
||||
ASSERT_EQUALS(false, ::isCharLiteral(""));
|
||||
|
||||
// no literals
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u8"));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u"));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("U"));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("L"));
|
||||
|
||||
// incomplete string literals
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u8\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("U\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("L\""));
|
||||
|
||||
// valid string literals
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("\"\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u8\"\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u\"\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("U\"\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("L\"\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("\"t\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u8\"t\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u\"t\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("U\"t\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("L\"t\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("\"test\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u8\"test\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u\"test\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("U\"test\""));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("L\"test\""));
|
||||
|
||||
// incomplete char literals
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("'"));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u8'"));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("u'"));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("U'"));
|
||||
ASSERT_EQUALS(false, ::isCharLiteral("L'"));
|
||||
|
||||
// valid char literals
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("'t'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("u8't'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("u't'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("U't'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("L't'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("'test'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("u8'test'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("u'test'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("U'test'"));
|
||||
ASSERT_EQUALS(true, ::isCharLiteral("L'test'"));
|
||||
}
|
||||
};
|
||||
|
||||
REGISTER_TEST(TestUtils)
|
||||
|
|
Loading…
Reference in New Issue