wasm: avoid LocalStorage past-the-end access on clear()
We were looping over all keys and removing the Qt keys using an integer index. However, removing one key shifts all other keys at higher indexes down one step such that the loop eventually indexes past the end. Fix this by getting the keys first in a separate step, and then remove keys without relying on a stable iteration order (which is also not guaranteed by the standard). Change-Id: I8bc577d1831d6931ebca2b2e04faf65c9affb429 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Morten Johan Sørvig <morten.sorvig@qt.io> (cherry picked from commit 8a20a278fa5f1e2890f88a69d8b5f96873a67ac9) Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
This commit is contained in:
parent
28dd79dc49
commit
4b736cb7ad
@ -122,13 +122,21 @@ QStringList QWasmLocalStorageSettingsPrivate::children(const QString &prefix, Ch
|
|||||||
|
|
||||||
void QWasmLocalStorageSettingsPrivate::clear()
|
void QWasmLocalStorageSettingsPrivate::clear()
|
||||||
{
|
{
|
||||||
// Remove all Qt keys from window.localStorage
|
// Get all Qt keys from window.localStorage
|
||||||
const int length = m_localStorage["length"].as<int>();
|
const int length = m_localStorage["length"].as<int>();
|
||||||
|
std::vector<std::string> keys;
|
||||||
|
keys.reserve(length);
|
||||||
for (int i = 0; i < length; ++i) {
|
for (int i = 0; i < length; ++i) {
|
||||||
std::string fullKey = (m_localStorage.call<val>("key", i).as<std::string>());
|
std::string key = (m_localStorage.call<val>("key", i).as<std::string>());
|
||||||
QString key = QString::fromStdString(fullKey);
|
keys.push_back(std::move(key));
|
||||||
if (removeStoragePrefix(QStringView(key)).isEmpty() == false)
|
}
|
||||||
m_localStorage.call<val>("removeItem", fullKey);
|
|
||||||
|
// Remove all Qt keys. Note that localStorage does not guarantee a stable
|
||||||
|
// iteration order when the storage is mutated, which is why removal is done
|
||||||
|
// in a second step after getting all keys.
|
||||||
|
for (std::string key: keys) {
|
||||||
|
if (removeStoragePrefix(QString::fromStdString(key)).isEmpty() == false)
|
||||||
|
m_localStorage.call<val>("removeItem", key);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user