diff options
author | Matthew Vogt <matthew.vogt@nokia.com> | 2012-01-16 11:05:23 +1000 |
---|---|---|
committer | Qt by Nokia <qt-info@nokia.com> | 2012-01-18 01:37:30 +0100 |
commit | 3aa53b8bc383ebcdf8dc922b2670170ec012949f (patch) | |
tree | 26181d69c9cdb5a2bbd61a3c99b97523352cf08c /src | |
parent | 52c1d7a994216f0b37ac04a2fea4337bc0c7550b (diff) |
Allow QML URLs to contain pre-encoded octets
Use QUrl Tolerant parsing mode to permit user-supplied URLs to contain
pre-encoded octets which are not mangled by string conversion.
Task-number: QTBUG-22756
Change-Id: I4b160b04340b95221d1eb3336bda8c0b38d2e232
Reviewed-by: Michael Brasser <michael.brasser@nokia.com>
Diffstat (limited to 'src')
-rw-r--r-- | src/declarative/qml/qdeclarativecompiler.cpp | 12 | ||||
-rw-r--r-- | src/declarative/qml/qdeclarativeproperty.cpp | 28 | ||||
-rw-r--r-- | src/declarative/qml/v4/qv4bindings.cpp | 12 | ||||
-rw-r--r-- | src/declarative/qml/v8/qv8sequencewrapper_p_p.h | 6 |
4 files changed, 44 insertions, 14 deletions
diff --git a/src/declarative/qml/qdeclarativecompiler.cpp b/src/declarative/qml/qdeclarativecompiler.cpp index 25013c9870..a855063ba5 100644 --- a/src/declarative/qml/qdeclarativecompiler.cpp +++ b/src/declarative/qml/qdeclarativecompiler.cpp @@ -404,6 +404,14 @@ bool QDeclarativeCompiler::testLiteralAssignment(QDeclarativeScript::Property *p return true; } +static QUrl urlFromUserString(const QString &data) +{ + QUrl u; + // Preserve any valid percent-encoded octets supplied by the source + u.setEncodedUrl(data.toUtf8(), QUrl::TolerantMode); + return u; +} + /*! Generate a store instruction for assigning literal \a v to property \a prop. @@ -511,7 +519,7 @@ void QDeclarativeCompiler::genLiteralAssignment(QDeclarativeScript::Property *pr { Instruction::StoreUrl instr; QString string = v->value.asString(); - QUrl u = string.isEmpty() ? QUrl() : output->url.resolved(QUrl(string)); + QUrl u = string.isEmpty() ? QUrl() : output->url.resolved(urlFromUserString(string)); instr.propertyIndex = prop->index; instr.value = output->indexForUrl(u); output->addInstruction(instr); @@ -720,7 +728,7 @@ void QDeclarativeCompiler::genLiteralAssignment(QDeclarativeScript::Property *pr } else if (type == qMetaTypeId<QList<QUrl> >()) { Instruction::StoreUrlQList instr; QString string = v->value.asString(); - QUrl u = string.isEmpty() ? QUrl() : output->url.resolved(QUrl(string)); + QUrl u = string.isEmpty() ? QUrl() : output->url.resolved(urlFromUserString(string)); instr.propertyIndex = prop->index; instr.value = output->indexForUrl(u); output->addInstruction(instr); diff --git a/src/declarative/qml/qdeclarativeproperty.cpp b/src/declarative/qml/qdeclarativeproperty.cpp index b393b77b5f..6cc55cc155 100644 --- a/src/declarative/qml/qdeclarativeproperty.cpp +++ b/src/declarative/qml/qdeclarativeproperty.cpp @@ -1052,6 +1052,22 @@ QVariant QDeclarativePropertyPrivate::readValueProperty() } } +static QUrl urlFromUserString(const QByteArray &data) +{ + QUrl u; + if (!data.isEmpty()) + { + // Preserve any valid percent-encoded octets supplied by the source + u.setEncodedUrl(data, QUrl::TolerantMode); + } + return u; +} + +static QUrl urlFromUserString(const QString &data) +{ + return urlFromUserString(data.toUtf8()); +} + // helper function to allow assignment / binding to QList<QUrl> properties. static QVariant resolvedUrlSequence(const QVariant &value, QDeclarativeContextData *context) { @@ -1059,19 +1075,19 @@ static QVariant resolvedUrlSequence(const QVariant &value, QDeclarativeContextDa if (value.userType() == qMetaTypeId<QUrl>()) { urls.append(value.toUrl()); } else if (value.userType() == qMetaTypeId<QString>()) { - urls.append(QUrl(value.toString())); + urls.append(urlFromUserString(value.toString())); } else if (value.userType() == qMetaTypeId<QByteArray>()) { - urls.append(QUrl(QString::fromUtf8(value.toByteArray()))); + urls.append(urlFromUserString(value.toByteArray())); } else if (value.userType() == qMetaTypeId<QList<QUrl> >()) { urls = value.value<QList<QUrl> >(); } else if (value.userType() == qMetaTypeId<QStringList>()) { QStringList urlStrings = value.value<QStringList>(); for (int i = 0; i < urlStrings.size(); ++i) - urls.append(QUrl(urlStrings.at(i))); + urls.append(urlFromUserString(urlStrings.at(i))); } else if (value.userType() == qMetaTypeId<QList<QString> >()) { QList<QString> urlStrings = value.value<QList<QString> >(); for (int i = 0; i < urlStrings.size(); ++i) - urls.append(QUrl(urlStrings.at(i))); + urls.append(urlFromUserString(urlStrings.at(i))); } // note: QList<QByteArray> is not currently supported. QList<QUrl> resolvedUrls; @@ -1211,10 +1227,10 @@ bool QDeclarativePropertyPrivate::write(QObject *object, u = value.toUrl(); found = true; } else if (variantType == QVariant::ByteArray) { - u = QUrl(QString::fromUtf8(value.toByteArray())); + u = urlFromUserString(value.toByteArray()); found = true; } else if (variantType == QVariant::String) { - u = QUrl(value.toString()); + u = urlFromUserString(value.toString()); found = true; } diff --git a/src/declarative/qml/v4/qv4bindings.cpp b/src/declarative/qml/v4/qv4bindings.cpp index 5255db0163..ba53a4176c 100644 --- a/src/declarative/qml/v4/qv4bindings.cpp +++ b/src/declarative/qml/v4/qv4bindings.cpp @@ -420,15 +420,16 @@ inline static QUrl toUrl(Register *reg, int type, QDeclarativeContextData *conte if (vt == QVariant::Url) { base = var->toUrl(); } else if (vt == QVariant::ByteArray) { - base = QUrl(QString::fromUtf8(var->toByteArray())); + // Preserve any valid percent-encoded octets supplied by the source + base.setEncodedUrl(var->toByteArray(), QUrl::TolerantMode); } else if (vt == QVariant::String) { - base = QUrl(var->toString()); + base.setEncodedUrl(var->toString().toUtf8(), QUrl::TolerantMode); } else { if (ok) *ok = false; return QUrl(); } } else if (type == QMetaType::QString) { - base = QUrl(*reg->getstringptr()); + base.setEncodedUrl(reg->getstringptr()->toUtf8(), QUrl::TolerantMode); } else { if (ok) *ok = false; return QUrl(); @@ -1012,7 +1013,10 @@ void QV4Bindings::run(int instrIndex, quint32 &executedBlocks, output.cleanupString(); MARK_CLEAN_REGISTER(instr->unaryop.output); } - new (output.geturlptr()) QUrl(tmp); + QUrl *urlPtr = output.geturlptr(); + new (urlPtr) QUrl(); + urlPtr->setEncodedUrl(tmp.toUtf8(), QUrl::TolerantMode); + URL_REGISTER(instr->unaryop.output); } } diff --git a/src/declarative/qml/v8/qv8sequencewrapper_p_p.h b/src/declarative/qml/v8/qv8sequencewrapper_p_p.h index c7a8ca4d8d..8dc1b117f7 100644 --- a/src/declarative/qml/v8/qv8sequencewrapper_p_p.h +++ b/src/declarative/qml/v8/qv8sequencewrapper_p_p.h @@ -180,12 +180,14 @@ static QString convertQStringToString(QV8Engine *, const QString &v) static QUrl convertV8ValueToUrl(QV8Engine *e, v8::Handle<v8::Value> v) { - return QUrl(e->toString(v->ToString())); + QUrl u; + u.setEncodedUrl(e->toString(v->ToString()).toUtf8(), QUrl::TolerantMode); + return u; } static v8::Handle<v8::Value> convertUrlToV8Value(QV8Engine *e, const QUrl &v) { - return e->toString(v.toString()); + return e->toString(v.toEncoded()); } static QString convertUrlToString(QV8Engine *, const QUrl &v) |