Experimental change. Cache pages with unload event
for back/forward. This will improve the history
navigation. But it may break some sites. See discussion
in https://bugs.webkit.org/show_bug.cgi?id=29021.
diff --git a/WebCore/config.h b/WebCore/config.h
index 02958bc..127d1cb 100644
--- a/WebCore/config.h
+++ b/WebCore/config.h
@@ -189,6 +189,15 @@
 // or if javascript tried to change the location.
 #define ANDROID_USER_GESTURE
 
+// Enable pages with unloadEvent for page cache. See the blog in
+// http://webkit.org/blog/427/webkit-page-cache-i-the-basics/ about this issue.
+// And see the bug, https://bugs.webkit.org/show_bug.cgi?id=29021, for details.
+// Currently WebKit doesn't cache pages with unloadEvent. This means that we
+// won't cache a lot of common sites like cnn.com. Experimenting caching pages
+// with unloadEvent for better back/forward navigation. Invoke unloadEvent when
+// a page is cached. Invoke loadEvent when a page is restored.
+#define ANDROID_PAGE_CACHE_UNLOAD
+
 #endif /* PLATFORM(ANDROID) */
 
 #ifdef __cplusplus
diff --git a/WebCore/history/CachedFrame.cpp b/WebCore/history/CachedFrame.cpp
index 16c7087..fe6c31f 100644
--- a/WebCore/history/CachedFrame.cpp
+++ b/WebCore/history/CachedFrame.cpp
@@ -99,6 +99,10 @@
     for (unsigned i = 0; i < m_childFrames.size(); ++i)
         m_childFrames[i]->open();
 
+#ifdef ANDROID_PAGE_CACHE_UNLOAD
+    // matches pageshowEvent as in Document::implicitClose()
+    m_document->dispatchWindowLoadEvent();
+#endif
     m_document->dispatchWindowEvent(PageTransitionEvent::create(EventNames().pageshowEvent, true), m_document);
 }
 
diff --git a/WebCore/loader/FrameLoader.cpp b/WebCore/loader/FrameLoader.cpp
index f9dc2bf..93ada45 100644
--- a/WebCore/loader/FrameLoader.cpp
+++ b/WebCore/loader/FrameLoader.cpp
@@ -530,7 +530,9 @@
                 if (m_frame->domWindow()) {
                     if (unloadEventPolicy == UnloadEventPolicyUnloadAndPageHide)
                         m_frame->domWindow()->dispatchEvent(PageTransitionEvent::create(EventNames().pagehideEvent, m_frame->document()->inPageCache()), m_frame->document());
+#ifndef ANDROID_PAGE_CACHE_UNLOAD
                     if (!m_frame->document()->inPageCache())
+#endif
                         m_frame->domWindow()->dispatchEvent(Event::create(eventNames().unloadEvent, false, false), m_frame->domWindow()->document());
                 }
                 m_unloadEventBeingDispatched = false;
@@ -1523,7 +1525,9 @@
         // the right NPObjects. See <rdar://problem/5197041> for more information.
         && !m_containsPlugIns
         && !m_URL.protocolIs("https")
+#ifndef ANDROID_PAGE_CACHE_UNLOAD
         && (!m_frame->domWindow() || !m_frame->domWindow()->hasEventListeners(eventNames().unloadEvent))
+#endif
 #if ENABLE(DATABASE)
         && !m_frame->document()->hasOpenDatabases()
 #endif
@@ -1668,8 +1672,10 @@
             { PCLOG("   -Frame contains plugins"); cannotCache = true; }
         if (m_URL.protocolIs("https"))
             { PCLOG("   -Frame is HTTPS"); cannotCache = true; }
+#ifndef ANDROID_PAGE_CACHE_UNLOAD
         if (m_frame->domWindow() && m_frame->domWindow()->hasEventListeners(eventNames().unloadEvent))
             { PCLOG("   -Frame has an unload event listener"); cannotCache = true; }
+#endif
 #if ENABLE(DATABASE)
         if (m_frame->document()->hasOpenDatabases())
             { PCLOG("   -Frame has open database handles"); cannotCache = true; }