desktop/source/deployment/dp_persmap.cxx | 43 +++++++++++++++---------------- 1 file changed, 21 insertions(+), 22 deletions(-)
New commits: commit fd7facf439be9e0f0e464205343c13cb5a68268f Author: Mike Kaganski <[email protected]> AuthorDate: Mon Nov 10 18:11:23 2025 +0500 Commit: Xisco Fauli <[email protected]> CommitDate: Thu Nov 27 16:36:02 2025 +0100 tdf#80959: fix percent character escaping in dp_misc::(en|de)codeString The intention that these functions, that use % as a special character, escape existing % with another %, was documented in comments at both functions. But it had never been implemented properly. In encodeString, the code did wrong calculations, and wrote first special character (either %, or 0x00-0x0F) verbatim; and only then processed following characters according to the algorithm. That meant that an input with percent-encoded space, like Foo%20Bar was checked until the percent; then first four characters "Foo%" were copied to the resulting buffer; and then the rest of characters were sequentially checked for % or 0x00-0x0F (and none of them were). The result was unchanged "Foo%20Bar", instead of expected "Foo%%20Bar". In decodeString, despite the idea that %% must convert to %, the code didn't expect anything except 0-9 and A-F after the first %. As the result, an input string of "Foo%%20Bar" would become "Foo\EEBar", and "Foo%20Bar" would become "FooBar". This was that way since introduction of this code in AOO in commit 65415c716863d17196eae2a4a7f86f2e0ba5c1b6 (#i118662# remove usage of BerkeleyDB in desktop module, 2011-12-12), ported to LO in commit daeed90f4586eb9533041fb89bee163a5193596c (re-base on ALv2 code. Includes:, 2012-11-19). This change fixes and unifies the logic of both of the functions. Change-Id: Ice5d078b007dbffacea247daaf81bde9c6386963 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/194066 Reviewed-by: Mike Kaganski <[email protected]> Tested-by: Jenkins (cherry picked from commit 5028a5f7564b8a2d8df626feb1a6a85ee8a65db3) Reviewed-on: https://gerrit.libreoffice.org/c/core/+/194095 Reviewed-by: Xisco Fauli <[email protected]> Code-Style: Xisco Fauli <[email protected]> diff --git a/desktop/source/deployment/dp_persmap.cxx b/desktop/source/deployment/dp_persmap.cxx index 9cc74b0c79a8..c2d7eb4a11b8 100644 --- a/desktop/source/deployment/dp_persmap.cxx +++ b/desktop/source/deployment/dp_persmap.cxx @@ -72,27 +72,25 @@ PersistentMap::~PersistentMap() // replace "%" with "%%" static OString encodeString( const OString& rStr) { - const char* pChar = rStr.getStr(); - const sal_Int32 nLen = rStr.getLength(); - sal_Int32 i = nLen; + const char *pChar = rStr.getStr(), *const pEnd = pChar + rStr.getLength(); // short circuit for the simple non-encoded case - while( --i >= 0) + for (; pChar != pEnd; ++pChar) { - const unsigned char c = static_cast<unsigned char>(*(pChar++)); + const unsigned char c = static_cast<unsigned char>(*pChar); if( c <= 0x0F ) break; if( c == '%') break; } - if( i < 0) + if (pChar == pEnd) return rStr; // escape chars 0x00..0x0F with "%0".."%F" - OStringBuffer aEncStr( nLen + 32); - aEncStr.append( pChar - (nLen-i), nLen - i); - while( --i >= 0) + OStringBuffer aEncStr(rStr.getLength() + 32); + aEncStr.append(rStr.getStr(), pChar - rStr.getStr()); + for (; pChar != pEnd; ++pChar) { - unsigned char c = static_cast<unsigned char>(*(pChar++)); + unsigned char c = static_cast<unsigned char>(*pChar); if( c <= 0x0F ) { aEncStr.append( '%'); @@ -109,30 +107,31 @@ static OString encodeString( const OString& rStr) // replace "%%" with "%" static OString decodeString( const char* pEncChars, int nLen) { - const char* pChar = pEncChars; - sal_Int32 i = nLen; + const char *pChar = pEncChars, *const pEnd = pChar + nLen; // short circuit for the simple non-encoded case - while( --i >= 0) - if( *(pChar++) == '%') + for (; pChar != pEnd; ++pChar) + if (*pChar == '%') break; - if( i < 0) + if (pChar == pEnd) return OString( pEncChars, nLen); // replace escaped chars with their decoded counterparts OStringBuffer aDecStr( nLen); - pChar = pEncChars; - for( i = nLen; --i >= 0;) + aDecStr.append(pEncChars, pChar - pEncChars); + for (; pChar != pEnd; ++pChar) { - char c = *(pChar++); + char c = *pChar; // handle escaped character if( c == '%') { - --i; - OSL_ASSERT( i >= 0); - c = *(pChar++); + ++pChar; + OSL_ASSERT(pChar != pEnd); + if (pChar == pEnd) + break; + c = *pChar; if( ('0' <= c) && (c <= '9')) c -= '0'; - else + else if (c != '%') { OSL_ASSERT( ('A' <= c) && (c <= 'F')); c -= ('A'-10);
