Title: [139878] trunk/Source
Revision
139878
Author
[email protected]
Date
2013-01-16 07:06:46 -0800 (Wed, 16 Jan 2013)

Log Message

[Qt] Use the shared HistoryItem serialization for QWebHistory
https://bugs.webkit.org/show_bug.cgi?id=106671

Reviewed by Allan Sandfeld Jensen.

Source/WebCore:

This allows a few things missing from the previous serialization code
to function while using commonly maintained code:
- The itemSequenceNumber and documentSequenceNumber that were needed
  to properly restore same-document navigations
- The form data
- The navigation hierarchy mapping the frame tree

* history/HistoryItem.h:
(HistoryItem):
* history/qt/HistoryItemQt.cpp:
(QDataStreamCoder):
(WebCore):
(WebCore::QDataStreamCoder::QDataStreamCoder):
(WebCore::QDataStreamCoder::encodeBytes):
(WebCore::QDataStreamCoder::encodeBool):
(WebCore::QDataStreamCoder::encodeUInt32):
(WebCore::QDataStreamCoder::encodeUInt64):
(WebCore::QDataStreamCoder::encodeInt32):
(WebCore::QDataStreamCoder::encodeInt64):
(WebCore::QDataStreamCoder::encodeFloat):
(WebCore::QDataStreamCoder::encodeDouble):
(WebCore::QDataStreamCoder::encodeString):
(WebCore::QDataStreamCoder::decodeBytes):
(WebCore::QDataStreamCoder::decodeBool):
(WebCore::QDataStreamCoder::decodeUInt32):
(WebCore::QDataStreamCoder::decodeUInt64):
(WebCore::QDataStreamCoder::decodeInt32):
(WebCore::QDataStreamCoder::decodeInt64):
(WebCore::QDataStreamCoder::decodeFloat):
(WebCore::QDataStreamCoder::decodeDouble):
(WebCore::QDataStreamCoder::decodeString):
(WebCore::HistoryItem::restoreState):
(WebCore::WebCore::HistoryItem::saveState):

Source/WebKit/qt:

Bump the serialization version and change the code to abort the
restore of a previous stream version rather than trying to keep the
support of restoring previous versions. This is mainly to simplify
things given that HistoryItem itself aborts in that case.

* Api/qwebhistory.cpp:
(operator<<):
(operator>>):
* tests/qwebhistory/tst_qwebhistory.cpp:
(tst_QWebHistory::serialize_2): Modify the test to cover same-document navigations.
(tst_QWebHistory::restoreIncompatibleVersion1): Add a previous version
hard-coded stream to verify that the deserialization doesn't hang or
crash.

Modified Paths

Diff

Modified: trunk/Source/WebCore/ChangeLog (139877 => 139878)


--- trunk/Source/WebCore/ChangeLog	2013-01-16 14:15:58 UTC (rev 139877)
+++ trunk/Source/WebCore/ChangeLog	2013-01-16 15:06:46 UTC (rev 139878)
@@ -1,3 +1,44 @@
+2013-01-16  Jocelyn Turcotte  <[email protected]>
+
+        [Qt] Use the shared HistoryItem serialization for QWebHistory
+        https://bugs.webkit.org/show_bug.cgi?id=106671
+
+        Reviewed by Allan Sandfeld Jensen.
+
+        This allows a few things missing from the previous serialization code
+        to function while using commonly maintained code:
+        - The itemSequenceNumber and documentSequenceNumber that were needed
+          to properly restore same-document navigations
+        - The form data
+        - The navigation hierarchy mapping the frame tree
+
+        * history/HistoryItem.h:
+        (HistoryItem):
+        * history/qt/HistoryItemQt.cpp:
+        (QDataStreamCoder):
+        (WebCore):
+        (WebCore::QDataStreamCoder::QDataStreamCoder):
+        (WebCore::QDataStreamCoder::encodeBytes):
+        (WebCore::QDataStreamCoder::encodeBool):
+        (WebCore::QDataStreamCoder::encodeUInt32):
+        (WebCore::QDataStreamCoder::encodeUInt64):
+        (WebCore::QDataStreamCoder::encodeInt32):
+        (WebCore::QDataStreamCoder::encodeInt64):
+        (WebCore::QDataStreamCoder::encodeFloat):
+        (WebCore::QDataStreamCoder::encodeDouble):
+        (WebCore::QDataStreamCoder::encodeString):
+        (WebCore::QDataStreamCoder::decodeBytes):
+        (WebCore::QDataStreamCoder::decodeBool):
+        (WebCore::QDataStreamCoder::decodeUInt32):
+        (WebCore::QDataStreamCoder::decodeUInt64):
+        (WebCore::QDataStreamCoder::decodeInt32):
+        (WebCore::QDataStreamCoder::decodeInt64):
+        (WebCore::QDataStreamCoder::decodeFloat):
+        (WebCore::QDataStreamCoder::decodeDouble):
+        (WebCore::QDataStreamCoder::decodeString):
+        (WebCore::HistoryItem::restoreState):
+        (WebCore::WebCore::HistoryItem::saveState):
+
 2013-01-15  Gustavo Noronha Silva  <[email protected]>
 
         [GStreamer][Soup] Let GStreamer provide the buffer data is downloaded to, to avoid copying

Modified: trunk/Source/WebCore/history/HistoryItem.h (139877 => 139878)


--- trunk/Source/WebCore/history/HistoryItem.h	2013-01-16 14:15:58 UTC (rev 139877)
+++ trunk/Source/WebCore/history/HistoryItem.h	2013-01-16 15:06:46 UTC (rev 139878)
@@ -201,7 +201,7 @@
     QVariant userData() const { return m_userData; }
     void setUserData(const QVariant& userData) { m_userData = userData; }
 
-    bool restoreState(QDataStream& buffer, int version);
+    static PassRefPtr<HistoryItem> restoreState(QDataStream& buffer, int version);
     QDataStream& saveState(QDataStream& out, int version) const;
 #endif
 

Modified: trunk/Source/WebCore/history/qt/HistoryItemQt.cpp (139877 => 139878)


--- trunk/Source/WebCore/history/qt/HistoryItemQt.cpp	2013-01-16 14:15:58 UTC (rev 139877)
+++ trunk/Source/WebCore/history/qt/HistoryItemQt.cpp	2013-01-16 15:06:46 UTC (rev 139878)
@@ -21,22 +21,13 @@
 #include "HistoryItem.h"
 
 #include "FormData.h"
+#include <wtf/Decoder.h>
+#include <wtf/Encoder.h>
 #include <wtf/text/CString.h>
 
-static QDataStream& operator<<(QDataStream& stream, const WebCore::IntPoint& point)
-{
-    stream << point.x() << point.y();
-    return stream;
-}
+using namespace WTF;
 
-static QDataStream& operator>>(QDataStream& stream, WebCore::IntPoint& point)
-{
-    int x, y;
-    stream >> x >> y;
-    point.setX(x);
-    point.setY(y);
-    return stream;
-}
+namespace WebCore {
 
 static QDataStream& operator<<(QDataStream& stream, const String& str)
 {
@@ -54,117 +45,190 @@
     return stream;
 }
 
-template<typename T>
-QDataStream& operator<<(QDataStream& stream, const Vector<T>& data)
+class QDataStreamCoder : public WTF::Encoder, public WTF::Decoder {
+public:
+    QDataStreamCoder(QDataStream&);
+
+private:
+    virtual void encodeBytes(const uint8_t*, size_t);
+    virtual void encodeBool(bool);
+    virtual void encodeUInt32(uint32_t);
+    virtual void encodeUInt64(uint64_t);
+    virtual void encodeInt32(int32_t);
+    virtual void encodeInt64(int64_t);
+    virtual void encodeFloat(float);
+    virtual void encodeDouble(double);
+    virtual void encodeString(const String&);
+
+    virtual bool decodeBytes(Vector<uint8_t>&);
+    virtual bool decodeBool(bool&);
+    virtual bool decodeUInt32(uint32_t&);
+    virtual bool decodeUInt64(uint64_t&);
+    virtual bool decodeInt32(int32_t&);
+    virtual bool decodeInt64(int64_t&);
+    virtual bool decodeFloat(float&);
+    virtual bool decodeDouble(double&);
+    virtual bool decodeString(String&);
+
+    QDataStream& m_stream;
+};
+
+QDataStreamCoder::QDataStreamCoder(QDataStream& stream)
+    : m_stream(stream)
 {
-    stream << qint64(data.size());
-    foreach (const T& i, data)
-        stream << i;
-    return stream;
 }
 
-template<typename T>
-QDataStream& operator>>(QDataStream& stream, Vector<T>& data)
+void QDataStreamCoder::encodeBytes(const uint8_t* bytes, size_t size)
 {
-    data.clear();
+    m_stream << qint64(size);
+    for (; size > 0; --size)
+        m_stream << bytes++;
+}
+
+void QDataStreamCoder::encodeBool(bool value)
+{
+    m_stream << value;
+}
+
+void QDataStreamCoder::encodeUInt32(uint32_t value)
+{
+    m_stream << value;
+}
+
+void QDataStreamCoder::encodeUInt64(uint64_t value)
+{
+    m_stream << static_cast<quint64>(value);
+}
+
+void QDataStreamCoder::encodeInt32(int32_t value)
+{
+    m_stream << value;
+}
+
+void QDataStreamCoder::encodeInt64(int64_t value)
+{
+    m_stream << static_cast<qint64>(value);
+}
+
+void QDataStreamCoder::encodeFloat(float value)
+{
+    m_stream << value;
+}
+
+void QDataStreamCoder::encodeDouble(double value)
+{
+    m_stream << value;
+}
+
+void QDataStreamCoder::encodeString(const String& value)
+{
+    m_stream << value;
+}
+
+bool QDataStreamCoder::decodeBytes(Vector<uint8_t>& out)
+{
+    out.clear();
     qint64 count;
-    T item;
-    stream >> count;
-    data.reserveCapacity(count);
+    uint8_t byte;
+    m_stream >> count;
+    out.reserveCapacity(count);
     for (qint64 i = 0; i < count; ++i) {
-        stream >> item;
-        data.append(item);
+        m_stream >> byte;
+        out.append(byte);
     }
-    return stream;
+    return m_stream.status() == QDataStream::Ok;
 }
 
-bool WebCore::HistoryItem::restoreState(QDataStream& in, int version)
+bool QDataStreamCoder::decodeBool(bool& out)
 {
-    // we only support version 1 for now
+    m_stream >> out;
+    return m_stream.status() == QDataStream::Ok;
+}
 
-    if (version != 1)
-        return false;
+bool QDataStreamCoder::decodeUInt32(uint32_t& out)
+{
+    m_stream >> out;
+    return m_stream.status() == QDataStream::Ok;
+}
 
-    WTF::String url;
-    WTF::String title;
-    WTF::String altTitle;
-    WTF::String orginalUrl;
-    WTF::String referrer;
-    WTF::String target;
-    WTF::String parrent;
-    double lastVisitedTime;
-    bool validUserData;
-    WTF::String parent;
-    bool lastVisitWasHTTPNonGet;
-    bool lastVisitWasFailure;
-    bool isTargetItem;
-    int visitCount;
-    WTF::Vector<WTF::String> documentState;
-    WebCore::IntPoint scrollPoint;
-    qreal pageScaleFactor;
-    WTF::Vector<int> weeklyVisitCounts;
-    WTF::Vector<int> dailyVisitCounts;
-    // bool loadFormdata;
-    // WTF::String formContentType;
-    // WTF::Vector<char> formData;
+bool QDataStreamCoder::decodeUInt64(uint64_t& out)
+{
+    quint64 tmp;
+    m_stream >> tmp;
+    // quint64 is defined to "long long unsigned", incompatible with uint64_t defined as "long unsigned" on 64bits archs.
+    out = tmp;
+    return m_stream.status() == QDataStream::Ok;
+}
 
-    in >> url >> title >> altTitle >> lastVisitedTime >> orginalUrl >> referrer >> target >> parent;
-    in >> lastVisitWasHTTPNonGet >> lastVisitWasFailure >> isTargetItem >> visitCount >> documentState;
-    in >> scrollPoint >> pageScaleFactor >> dailyVisitCounts >> weeklyVisitCounts;
-    /*in >> loadFormdata;
-    if (loadFormdata) {
-        in >> formContentType >> formData;
-        // direct assigned (!)
-        m_formContentType = formContentType;
-        m_formData = FormData::create(CString(formData));
-    }*/
-    // use setters
-    adoptVisitCounts(dailyVisitCounts, weeklyVisitCounts);
-    setScrollPoint(scrollPoint);
-    setPageScaleFactor(pageScaleFactor);
-    setDocumentState(documentState);
-    setVisitCount(visitCount);
-    setIsTargetItem(isTargetItem);
-    setLastVisitWasFailure(lastVisitWasFailure);
-    setLastVisitWasHTTPNonGet(lastVisitWasHTTPNonGet);
-    setParent(parent);
-    setTarget(target);
-    setReferrer(referrer);
-    setOriginalURLString(orginalUrl);
-    setURLString(url);
-    setLastVisitedTime(lastVisitedTime);
-    setTitle(title);
-    setAlternateTitle(altTitle);
+bool QDataStreamCoder::decodeInt32(int32_t& out)
+{
+    m_stream >> out;
+    return m_stream.status() == QDataStream::Ok;
+}
 
+bool QDataStreamCoder::decodeInt64(int64_t& out)
+{
+    qint64 tmp;
+    m_stream >> tmp;
+    // qint64 is defined to "long long", incompatible with int64_t defined as "long" on 64bits archs.
+    out = tmp;
+    return m_stream.status() == QDataStream::Ok;
+}
+
+bool QDataStreamCoder::decodeFloat(float& out)
+{
+    m_stream >> out;
+    return m_stream.status() == QDataStream::Ok;
+}
+
+bool QDataStreamCoder::decodeDouble(double& out)
+{
+    m_stream >> out;
+    return m_stream.status() == QDataStream::Ok;
+}
+
+bool QDataStreamCoder::decodeString(String& out)
+{
+    m_stream >> out;
+    return m_stream.status() == QDataStream::Ok;
+}
+
+PassRefPtr<HistoryItem> HistoryItem::restoreState(QDataStream& in, int version)
+{
+    ASSERT(version == 2);
+
+    String url;
+    String title;
+    String originalURL;
+    in >> url >> title >> originalURL;
+
+    QDataStreamCoder decoder(in);
+    RefPtr<HistoryItem> item = decodeBackForwardTree(url, title, originalURL, decoder);
+    // decodeBackForwardTree has its own stream version. An incompatible input stream version will return null here.
+    if (!item)
+        return 0;
+
     // at the end load userData
+    bool validUserData;
     in >> validUserData;
     if (validUserData) {
         QVariant tmp;
         in >> tmp;
-        setUserData(tmp);
+        item->setUserData(tmp);
     }
 
-    return in.status() == QDataStream::Ok;
+    return item;
 }
 
 QDataStream& WebCore::HistoryItem::saveState(QDataStream& out, int version) const
 {
-    // we only support version 1 for now.
-    if (version != 1)
-        return out;
+    ASSERT(version == 2);
 
-    out << urlString() << title() << alternateTitle() << lastVisitedTime();
-    out << originalURLString() << referrer() << target() << parent();
-    out << lastVisitWasHTTPNonGet() << lastVisitWasFailure() << isTargetItem();
-    out << visitCount() << documentState() << scrollPoint();
-    out << qreal(pageScaleFactor()) << dailyVisitCounts() << weeklyVisitCounts();
-    /*if (m_formData) {
-        out << true;
-        out << formContentType();
-        out << m_formData->flatten();
-    } else {
-        out << false;
-    }*/
+    out << urlString() << title() << originalURLString();
+
+    QDataStreamCoder encoder(out);
+    encodeBackForwardTree(encoder);
+
     // save user data
     if (userData().isValid())
         out << true << userData();
@@ -174,3 +238,4 @@
     return out;
 }
 
+} // namespace WebCore

Modified: trunk/Source/WebKit/qt/Api/qwebhistory.cpp (139877 => 139878)


--- trunk/Source/WebKit/qt/Api/qwebhistory.cpp	2013-01-16 14:15:58 UTC (rev 139877)
+++ trunk/Source/WebKit/qt/Api/qwebhistory.cpp	2013-01-16 15:06:46 UTC (rev 139878)
@@ -35,10 +35,7 @@
 #include <QSharedData>
 #include <QDebug>
 
-enum {
-    InitialHistoryVersion = 1,
-    DefaultHistoryVersion = InitialHistoryVersion
-};
+static const int HistoryStreamVersion = 2;
 
 /*!
   \class QWebHistoryItem
@@ -496,7 +493,7 @@
 {
     QWebHistoryPrivate* d = history.d;
 
-    int version = DefaultHistoryVersion;
+    int version = HistoryStreamVersion;
 
     target << version;
     target << history.count() << history.currentItemIndex();
@@ -521,29 +518,42 @@
 QDataStream& operator>>(QDataStream& source, QWebHistory& history)
 {
     QWebHistoryPrivate* d = history.d;
+    // Clear first, to have the same behavior if our version doesn't match and if the HistoryItem's version doesn't.
+    history.clear();
 
+    // This version covers every field we serialize in qwebhistory.cpp and HistoryItemQt.cpp (like the HistoryItem::userData()).
+    // HistoryItem has its own version in the stream covering the work done in encodeBackForwardTree.
+    // If any of those two stream version changes, the effect should be the same and the QWebHistory should fail to restore.
     int version;
-
     source >> version;
+    if (version != HistoryStreamVersion) {
+        // We do not try to decode previous history stream versions.
+        // Make sure that our history is cleared and mark the rest of the stream as invalid.
+        ASSERT(history.count() == 1);
+        source.setStatus(QDataStream::ReadCorruptData);
+        return source;
+    }
 
-    if (version == 1) {
-        int count;
-        int currentIndex;
-        source >> count >> currentIndex;
+    int count;
+    int currentIndex;
+    source >> count >> currentIndex;
 
-        history.clear();
-        // only if there are elements
-        if (count) {
-            // after clear() is new clear HistoryItem (at the end we had to remove it)
-            WebCore::HistoryItem* nullItem = d->lst->currentItem();
-            for (int i = 0; i < count; i++) {
-                WTF::PassRefPtr<WebCore::HistoryItem> item = WebCore::HistoryItem::create();
-                item->restoreState(source, version);
-                d->lst->addItem(item);
+    // only if there are elements
+    if (count) {
+        // after clear() is new clear HistoryItem (at the end we had to remove it)
+        WebCore::HistoryItem* nullItem = d->lst->currentItem();
+        for (int i = 0; i < count; i++) {
+            WTF::RefPtr<WebCore::HistoryItem> item = WebCore::HistoryItem::restoreState(source, version);
+            if (!item) {
+                // The HistoryItem internal version might have changed, do the same as when our own version change.
+                history.clear();
+                source.setStatus(QDataStream::ReadCorruptData);
+                return source;
             }
-            d->lst->removeItem(nullItem);
-            history.goToItem(history.itemAt(currentIndex));
+            d->lst->addItem(item);
         }
+        d->lst->removeItem(nullItem);
+        history.goToItem(history.itemAt(currentIndex));
     }
 
     d->page()->updateNavigationActions();

Modified: trunk/Source/WebKit/qt/ChangeLog (139877 => 139878)


--- trunk/Source/WebKit/qt/ChangeLog	2013-01-16 14:15:58 UTC (rev 139877)
+++ trunk/Source/WebKit/qt/ChangeLog	2013-01-16 15:06:46 UTC (rev 139878)
@@ -1,5 +1,26 @@
 2013-01-16  Jocelyn Turcotte  <[email protected]>
 
+        [Qt] Use the shared HistoryItem serialization for QWebHistory
+        https://bugs.webkit.org/show_bug.cgi?id=106671
+
+        Reviewed by Allan Sandfeld Jensen.
+
+        Bump the serialization version and change the code to abort the
+        restore of a previous stream version rather than trying to keep the
+        support of restoring previous versions. This is mainly to simplify
+        things given that HistoryItem itself aborts in that case.
+ 
+        * Api/qwebhistory.cpp:
+        (operator<<):
+        (operator>>):
+        * tests/qwebhistory/tst_qwebhistory.cpp:
+        (tst_QWebHistory::serialize_2): Modify the test to cover same-document navigations.
+        (tst_QWebHistory::restoreIncompatibleVersion1): Add a previous version
+        hard-coded stream to verify that the deserialization doesn't hang or
+        crash.
+
+2013-01-16  Jocelyn Turcotte  <[email protected]>
+
         [Qt] Crash in WebCore::CachedFrame::destroy
         https://bugs.webkit.org/show_bug.cgi?id=104525
 

Modified: trunk/Source/WebKit/qt/tests/qwebhistory/tst_qwebhistory.cpp (139877 => 139878)


--- trunk/Source/WebKit/qt/tests/qwebhistory/tst_qwebhistory.cpp	2013-01-16 14:15:58 UTC (rev 139877)
+++ trunk/Source/WebKit/qt/tests/qwebhistory/tst_qwebhistory.cpp	2013-01-16 15:06:46 UTC (rev 139878)
@@ -65,6 +65,7 @@
     void popPushState_data();
     void popPushState();
     void clear();
+    void restoreIncompatibleVersion1();
 
 
 private:
@@ -237,16 +238,20 @@
     QDataStream save(&tmp, QIODevice::WriteOnly); //here data will be saved
     QDataStream load(&tmp, QIODevice::ReadOnly); //from here data will be loaded
 
-    int oldCurrentIndex = hist->currentItemIndex();
+    // Force a "same document" navigation.
+    frame->load(frame->url().toString() + QLatin1String("#dummyAnchor"));
 
+    int initialCurrentIndex = hist->currentItemIndex();
+
     hist->back();
+    hist->back();
     waitForLoadFinished.exec();
     hist->back();
     waitForLoadFinished.exec();
     //check if current index was changed (make sure that it is not last item)
-    QVERIFY(hist->currentItemIndex() != oldCurrentIndex);
+    QVERIFY(hist->currentItemIndex() != initialCurrentIndex);
     //save current index
-    oldCurrentIndex = hist->currentItemIndex();
+    int oldCurrentIndex = hist->currentItemIndex();
 
     save << *hist;
     QVERIFY(save.status() == QDataStream::Ok);
@@ -255,6 +260,13 @@
 
     //check current index
     QCOMPARE(hist->currentItemIndex(), oldCurrentIndex);
+
+    hist->forward();
+    waitForLoadFinished.exec();
+    hist->forward();
+    waitForLoadFinished.exec();
+    hist->forward();
+    QCOMPARE(hist->currentItemIndex(), initialCurrentIndex);
 }
 
 /**
@@ -414,5 +426,99 @@
     delete page2;
 }
 
+// static void dumpCurrentVersion(QWebHistory* history)
+// {
+//     QByteArray buffer;
+//     saveHistory(history, &buffer);
+//     printf("    static const char version1Dump[] = {");
+//     for (int i = 0; i < buffer.size(); ++i) {
+//         bool newLine = !(i % 15);
+//         bool last = i == buffer.size() - 1;
+//         printf("%s0x%.2x%s", newLine ? "\n        " : "", (unsigned char)buffer[i], last ? "" : ", ");
+//     }
+//     printf("};\n");
+// }
+
+void tst_QWebHistory::restoreIncompatibleVersion1()
+{
+    // Uncomment this code to generate a dump similar to the one below with the current stream version.
+    // dumpCurrentVersion(hist);
+    static const char version1Dump[] = {
+        0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00,
+        0x32, 0x00, 0x71, 0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f, 0x00, 0x72, 0x00, 0x65,
+        0x00, 0x73, 0x00, 0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00, 0x65, 0x00, 0x73, 0x00,
+        0x2f, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x31, 0x00, 0x2e, 0x00, 0x68,
+        0x00, 0x74, 0x00, 0x6d, 0x00, 0x6c, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x70, 0x00, 0x61, 0x00,
+        0x67, 0x00, 0x65, 0x00, 0x31, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x32, 0x00, 0x71, 0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00,
+        0x2f, 0x00, 0x72, 0x00, 0x65, 0x00, 0x73, 0x00, 0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63,
+        0x00, 0x65, 0x00, 0x73, 0x00, 0x2f, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00,
+        0x31, 0x00, 0x2e, 0x00, 0x68, 0x00, 0x74, 0x00, 0x6d, 0x00, 0x6c, 0xff, 0xff, 0xff, 0xff,
+        0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x3f, 0xf0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x32,
+        0x00, 0x71, 0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f, 0x00, 0x72, 0x00, 0x65, 0x00,
+        0x73, 0x00, 0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00, 0x65, 0x00, 0x73, 0x00, 0x2f,
+        0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x32, 0x00, 0x2e, 0x00, 0x68, 0x00,
+        0x74, 0x00, 0x6d, 0x00, 0x6c, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67,
+        0x00, 0x65, 0x00, 0x32, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x32, 0x00, 0x71, 0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f,
+        0x00, 0x72, 0x00, 0x65, 0x00, 0x73, 0x00, 0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00,
+        0x65, 0x00, 0x73, 0x00, 0x2f, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x32,
+        0x00, 0x2e, 0x00, 0x68, 0x00, 0x74, 0x00, 0x6d, 0x00, 0x6c, 0xff, 0xff, 0xff, 0xff, 0xff,
+        0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x3f, 0xf0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x32, 0x00,
+        0x71, 0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f, 0x00, 0x72, 0x00, 0x65, 0x00, 0x73,
+        0x00, 0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00, 0x65, 0x00, 0x73, 0x00, 0x2f, 0x00,
+        0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x33, 0x00, 0x2e, 0x00, 0x68, 0x00, 0x74,
+        0x00, 0x6d, 0x00, 0x6c, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00,
+        0x65, 0x00, 0x33, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x32, 0x00, 0x71, 0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f, 0x00,
+        0x72, 0x00, 0x65, 0x00, 0x73, 0x00, 0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00, 0x65,
+        0x00, 0x73, 0x00, 0x2f, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x33, 0x00,
+        0x2e, 0x00, 0x68, 0x00, 0x74, 0x00, 0x6d, 0x00, 0x6c, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+        0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3f,
+        0xf0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x32, 0x00, 0x71,
+        0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f, 0x00, 0x72, 0x00, 0x65, 0x00, 0x73, 0x00,
+        0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00, 0x65, 0x00, 0x73, 0x00, 0x2f, 0x00, 0x70,
+        0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x34, 0x00, 0x2e, 0x00, 0x68, 0x00, 0x74, 0x00,
+        0x6d, 0x00, 0x6c, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65,
+        0x00, 0x34, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x32, 0x00, 0x71, 0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f, 0x00, 0x72,
+        0x00, 0x65, 0x00, 0x73, 0x00, 0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00, 0x65, 0x00,
+        0x73, 0x00, 0x2f, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x34, 0x00, 0x2e,
+        0x00, 0x68, 0x00, 0x74, 0x00, 0x6d, 0x00, 0x6c, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+        0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x3f, 0xf0,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x32, 0x00, 0x71, 0x00,
+        0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f, 0x00, 0x72, 0x00, 0x65, 0x00, 0x73, 0x00, 0x6f,
+        0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00, 0x65, 0x00, 0x73, 0x00, 0x2f, 0x00, 0x70, 0x00,
+        0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x35, 0x00, 0x2e, 0x00, 0x68, 0x00, 0x74, 0x00, 0x6d,
+        0x00, 0x6c, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00,
+        0x35, 0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x32, 0x00, 0x71, 0x00, 0x72, 0x00, 0x63, 0x00, 0x3a, 0x00, 0x2f, 0x00, 0x72, 0x00,
+        0x65, 0x00, 0x73, 0x00, 0x6f, 0x00, 0x75, 0x00, 0x72, 0x00, 0x63, 0x00, 0x65, 0x00, 0x73,
+        0x00, 0x2f, 0x00, 0x70, 0x00, 0x61, 0x00, 0x67, 0x00, 0x65, 0x00, 0x35, 0x00, 0x2e, 0x00,
+        0x68, 0x00, 0x74, 0x00, 0x6d, 0x00, 0x6c, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
+    QByteArray version1(version1Dump, sizeof(version1Dump));
+    QDataStream stream(&version1, QIODevice::ReadOnly);
+
+    // This should fail to load, the history should be cleared and the stream should be broken.
+    stream >> *hist;
+    QVERIFY(!hist->canGoBack());
+    QVERIFY(!hist->canGoForward());
+    QVERIFY(stream.status() == QDataStream::ReadCorruptData);
+}
+
 QTEST_MAIN(tst_QWebHistory)
 #include "tst_qwebhistory.moc"
_______________________________________________
webkit-changes mailing list
[email protected]
http://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to