diff options
author | Lionel Elie Mamane <lionel@mamane.lu> | 2012-08-21 19:27:30 +0200 |
---|---|---|
committer | Lionel Elie Mamane <lionel@mamane.lu> | 2012-08-21 19:30:20 +0200 |
commit | e8409cbd7227849fe446661011c8bc73acdca319 (patch) | |
tree | 94cccc59932d73fb95909bdb3393c18017cd1496 /connectivity/source/parse | |
parent | cc430308c38d106618189357364454230ff574d6 (diff) |
fdo#53887 ConvertLikeToken(): make escape character properly escape itself
Change-Id: Ic2b79e78f95e298a08794fa11f227d76152244f5
Diffstat (limited to 'connectivity/source/parse')
-rw-r--r-- | connectivity/source/parse/sqlbison.y | 34 |
1 files changed, 25 insertions, 9 deletions
diff --git a/connectivity/source/parse/sqlbison.y b/connectivity/source/parse/sqlbison.y index a93b7998d5f7..ce2d0e778e99 100644 --- a/connectivity/source/parse/sqlbison.y +++ b/connectivity/source/parse/sqlbison.y @@ -4511,7 +4511,7 @@ const double fMilliSecondsPerDay = 86400000.0; //------------------------------------------------------------------ ::rtl::OUString ConvertLikeToken(const OSQLParseNode* pTokenNode, const OSQLParseNode* pEscapeNode, sal_Bool bInternational) { - ::rtl::OUStringBuffer aMatchStr; + ::rtl::OUStringBuffer aMatchStr(0); if (pTokenNode->isToken()) { sal_Unicode cEscape = 0; @@ -4533,18 +4533,34 @@ const double fMilliSecondsPerDay = 86400000.0; sReplace.appendAscii("%_",2); } + bool wasEscape = false; for (sal_Int32 i = 0; i < nLen; i++) { const sal_Unicode c = aMatchStr[i]; - if (c == sSearch[0] || c == sSearch[1]) + // SQL standard requires the escape to be followed + // by a meta-character ('%', '_' or itself), else error + // We are more lenient here and let it escape anything. + // Especially since some databases (e.g. Microsoft SQL Server) + // have more meta-characters than the standard, such as e.g. '[' and ']' + if (wasEscape) { - if (i > 0 && aMatchStr[i - 1] == cEscape) - continue; - else - { - const sal_Unicode cCharacter = sReplace[(c == sSearch[0] ? 0 : 1)]; - aMatchStr[i] = cCharacter; - } + wasEscape=false; + continue; + } + if (c == cEscape) + { + wasEscape=true; + continue; + } + int match = -1; + if (c == sSearch[0]) + match=0; + else if (c == sSearch[1]) + match=1; + + if (match != -1) + { + aMatchStr[i] = sReplace[match]; } } } |