am 64c3e551: (-s ours) am 8187c15d: Merge "Cursor leak in share_link_context_menu."

* commit '64c3e551ae13c9c4fa2b42e47c123620ddaef581':
  Cursor leak in share_link_context_menu.
diff --git a/Android.mk b/Android.mk
index e015dda..2abde9b 100644
--- a/Android.mk
+++ b/Android.mk
@@ -12,6 +12,8 @@
 
 LOCAL_PACKAGE_NAME := Browser
 
+LOCAL_PROGUARD_FLAG_FILES := proguard.flags
+
 LOCAL_EMMA_COVERAGE_FILTER := *,-com.android.common.*
 
 include $(BUILD_PACKAGE)
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index dc8f599..89e93dc 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -25,20 +25,23 @@
     <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
     <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
     <uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
-    <uses-permission android:name="com.android.launcher.permission.INSTALL_SHORTCUT"/>
+    <uses-permission android:name="android.permission.GET_ACCOUNTS"/>
     <uses-permission android:name="android.permission.INTERNET" />
+    <uses-permission android:name="android.permission.SEND_DOWNLOAD_COMPLETED_INTENTS" />
     <uses-permission android:name="android.permission.SET_WALLPAPER" />
     <uses-permission android:name="android.permission.WAKE_LOCK"/>
     <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
     <uses-permission android:name="android.permission.WRITE_SETTINGS" />
+    <uses-permission android:name="android.permission.WRITE_SYNC_SETTINGS" />
     <uses-permission android:name="com.android.browser.permission.READ_HISTORY_BOOKMARKS"/>
     <uses-permission android:name="com.android.browser.permission.WRITE_HISTORY_BOOKMARKS"/>
-    <uses-permission android:name="android.permission.SEND_DOWNLOAD_COMPLETED_INTENTS" />
+    <uses-permission android:name="com.android.launcher.permission.INSTALL_SHORTCUT"/>
 
     <application   android:name="Browser"
                    android:label="@string/application_name"
                    android:icon="@drawable/ic_launcher_browser"
                    android:backupAgent=".BrowserBackupAgent"
+                   android:hardwareAccelerated="false"
                    android:taskAffinity="android.task.browser" >
 
         <provider android:name="BrowserProvider"
@@ -49,6 +52,14 @@
             <path-permission android:path="/bookmarks/search_suggest_query"
                     android:readPermission="android.permission.GLOBAL_SEARCH" />
         </provider>
+        <provider android:name=".provider.BrowserProvider2"
+                  android:authorities="com.android.browser"
+                  android:multiprocess="true"
+                  android:readPermission="com.android.browser.permission.READ_HISTORY_BOOKMARKS"
+                  android:writePermission="com.android.browser.permission.WRITE_HISTORY_BOOKMARKS">
+            <path-permission android:path="/bookmarks/search_suggest_query"
+                    android:readPermission="android.permission.GLOBAL_SEARCH" />
+        </provider>
         <activity android:name="BrowserActivity"
                   android:label="@string/application_name"
                   android:launchMode="singleTask"
@@ -85,6 +96,16 @@
                 <data android:mimeType="application/xhtml+xml"/>
                 <data android:mimeType="application/vnd.wap.xhtml+xml"/>
             </intent-filter>
+            <!-- For viewing saved web archives. -->
+            <intent-filter>
+                <action android:name="android.intent.action.VIEW" />
+                <category android:name="android.intent.category.BROWSABLE" />
+                <category android:name="android.intent.category.DEFAULT" />
+                <data android:scheme="http" />
+                <data android:scheme="https" />
+                <data android:scheme="file" />
+                <data android:mimeType="application/x-webarchive-xml"/>
+            </intent-filter>
             <!-- We are also the main entry point of the browser. -->
             <intent-filter>
                 <action android:name="android.intent.action.MAIN" />
@@ -119,24 +140,12 @@
             <meta-data android:name="android.app.searchable"
                     android:resource="@xml/searchable" />
         </activity>
-
-        <activity android:name="CombinedBookmarkHistoryActivity" android:label="@string/bookmarks"
-                  android:excludeFromRecents="true"
-                  android:launchMode="singleTop" android:configChanges="orientation|keyboardHidden"
-                  android:theme="@style/BookmarkTheme" >
-            <meta-data android:name="android.app.default_searchable"
-                    android:value=".BrowserActivity" />
-            <intent-filter>
-                <action android:name="android.intent.action.MAIN" />
-            </intent-filter>
-        </activity>
-
         <activity android:name="BrowserBookmarksPage" android:label="@string/bookmarks"
                   android:launchMode="singleTop" android:configChanges="orientation|keyboardHidden">
         </activity>
 
-        <activity-alias android:name="ShortcutBookmarksPage"
-            android:targetActivity="BrowserBookmarksPage"
+        <activity android:name="ShortcutActivity"
+            android:theme="@style/ShortcutTheme"
             android:label="@string/shortcut_bookmark"
             android:icon="@drawable/ic_launcher_shortcut_browser_bookmark">
 
@@ -145,7 +154,7 @@
                 <category android:name="android.intent.category.DEFAULT" />
             </intent-filter>
 
-        </activity-alias>
+        </activity>
 
         <activity android:name="BrowserDownloadPage" android:label=""
                   android:configChanges="orientation|keyboardHidden">
@@ -176,8 +185,10 @@
                     android:resource="@xml/bookmarks_searchable" />
         </activity>
 
-        <activity android:name="AddBookmarkPage" android:label="Save bookmark" android:theme="@android:style/Theme.Dialog"
-                  android:configChanges="orientation|keyboardHidden" android:windowSoftInputMode="stateHidden">
+        <activity android:name="AddBookmarkPage" android:label="Save bookmark"
+                  android:theme="@style/Dialog"
+                  android:configChanges="orientation|keyboardHidden"
+                  android:windowSoftInputMode="stateHidden">
             <intent-filter>
                 <action android:name="android.intent.action.INSERT" />
                 <category android:name="android.intent.category.DEFAULT" />
@@ -185,18 +196,36 @@
             </intent-filter>
         </activity>
 
-        <!--receiver android:name=".widget.BookmarkWidgetProvider" android:label="@string/bookmarks">
-            <intent-filter>
-                <action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
-            </intent-filter>
-            <meta-data android:name="android.appwidget.provider" android:resource="@xml/bookmarkwidget"/>
-        </receiver>
+        <activity android:name="SaveToHomescreenDialog" android:label="Save to homescreen" android:theme="@android:style/Theme.Dialog"
+                  android:configChanges="orientation|keyboardHidden" android:windowSoftInputMode="stateHidden">
+        </activity>
 
-        <service android:name=".widget.BookmarkWidgetService" /-->
+        <receiver
+            android:name=".widget.BookmarkStackWidgetProvider"
+            android:label="@string/bookmarks">
+            <intent-filter>
+                <action
+                    android:name="android.appwidget.action.APPWIDGET_UPDATE" />
+            </intent-filter>
+            <meta-data
+                android:name="android.appwidget.provider"
+                android:resource="@xml/bookmarkstackwidget" />
+        </receiver>
+        <service
+            android:name=".widget.BookmarkStackWidgetService"
+            android:exported="true" />
 
         <!-- Makes .BrowserActivity the search target for any activity in Browser -->
         <meta-data android:name="android.app.default_searchable" android:value=".BrowserActivity" />
 
+        <!-- Application code for RLZ tracking.  RLZ assigns non-unique, non-personally identifiable
+             tracking labels to client products; these labels sometimes appear in Google search
+             queries.  See http://code.google.com/p/rlz for more info.
+
+             This value signifies to the RLZ client that this application uses RLZ tracking. -->
+        <meta-data android:name="com.google.android.partnersetup.RLZ_ACCESS_POINT"
+                   android:value="@string/rlz_access_point" />
+
         <receiver android:name=".OpenDownloadReceiver">
             <intent-filter>
                 <action android:name="android.intent.action.DOWNLOAD_NOTIFICATION_CLICKED"/>
diff --git a/CleanSpec.mk b/CleanSpec.mk
index b84e1b6..722b4a4 100644
--- a/CleanSpec.mk
+++ b/CleanSpec.mk
@@ -43,6 +43,7 @@
 #$(call add-clean-step, rm -rf $(OUT_DIR)/target/common/obj/JAVA_LIBRARIES/core_intermediates)
 #$(call add-clean-step, find $(OUT_DIR) -type f -name "IGTalkSession*" -print0 | xargs -0 rm -f)
 #$(call add-clean-step, rm -rf $(PRODUCT_OUT)/data/*)
+$(call add-clean-step, rm -rf $(OUT_DIR)/target/common/obj/APPS/Browser_intermediates)
 
 # ************************************************
 # NEWER CLEAN STEPS MUST BE AT THE END OF THE LIST
diff --git a/proguard.flags b/proguard.flags
new file mode 100644
index 0000000..888c238
--- /dev/null
+++ b/proguard.flags
@@ -0,0 +1,2 @@
+# Most of the classes in this package are fragments only referenced from XML
+-keep class com.android.browser.preferences.*
diff --git a/res/anim/dialog_enter.xml b/res/anim/dialog_enter.xml
deleted file mode 100644
index f98d845..0000000
--- a/res/anim/dialog_enter.xml
+++ /dev/null
@@ -1,21 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2007 The Android Open Source Project
-
-     Licensed under the Apache License, Version 2.0 (the "License");
-     you may not use this file except in compliance with the License.
-     You may obtain a copy of the License at
-
-          http://www.apache.org/licenses/LICENSE-2.0
-
-     Unless required by applicable law or agreed to in writing, software
-     distributed under the License is distributed on an "AS IS" BASIS,
-     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-     See the License for the specific language governing permissions and
-     limitations under the License.
--->
-
-<set xmlns:android="http://schemas.android.com/apk/res/android"
-        android:interpolator="@android:anim/decelerate_interpolator">
-    <translate android:fromYDelta="25%" android:toYDelta="0" android:duration="75"/>
-    <alpha android:fromAlpha="0.0" android:toAlpha="1.0" android:duration="75" />
-</set>
diff --git a/res/drawable-hdpi/button_selected.png b/res/drawable-hdpi/button_selected.png
new file mode 100644
index 0000000..752deda
--- /dev/null
+++ b/res/drawable-hdpi/button_selected.png
Binary files differ
diff --git a/res/drawable-hdpi/default_video_poster.png b/res/drawable-hdpi/default_video_poster.png
new file mode 100644
index 0000000..9bbaf9c
--- /dev/null
+++ b/res/drawable-hdpi/default_video_poster.png
Binary files differ
diff --git a/res/drawable-hdpi/divider_vert.9.png b/res/drawable-hdpi/divider_vert.9.png
new file mode 100644
index 0000000..2c5646e
--- /dev/null
+++ b/res/drawable-hdpi/divider_vert.9.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_arrow_left.png b/res/drawable-hdpi/ic_arrow_left.png
new file mode 100644
index 0000000..bcbe3f6
--- /dev/null
+++ b/res/drawable-hdpi/ic_arrow_left.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_arrow_right.png b/res/drawable-hdpi/ic_arrow_right.png
new file mode 100644
index 0000000..6095533
--- /dev/null
+++ b/res/drawable-hdpi/ic_arrow_right.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_find_next.png b/res/drawable-hdpi/ic_btn_find_next.png
deleted file mode 100644
index b696a6b..0000000
--- a/res/drawable-hdpi/ic_btn_find_next.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_find_prev.png b/res/drawable-hdpi/ic_btn_find_prev.png
deleted file mode 100644
index 5550c5a..0000000
--- a/res/drawable-hdpi/ic_btn_find_prev.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_clear_search.png b/res/drawable-hdpi/ic_clear_search.png
new file mode 100644
index 0000000..e8e67b4
--- /dev/null
+++ b/res/drawable-hdpi/ic_clear_search.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_favorite_off_normal.png b/res/drawable-hdpi/ic_favorite_off_normal.png
new file mode 100644
index 0000000..4741464
--- /dev/null
+++ b/res/drawable-hdpi/ic_favorite_off_normal.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_go_normal_white.png b/res/drawable-hdpi/ic_go_normal_white.png
new file mode 100644
index 0000000..1ae9ed9
--- /dev/null
+++ b/res/drawable-hdpi/ic_go_normal_white.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_launcher_browser.png b/res/drawable-hdpi/ic_launcher_browser.png
index f11581f..2ca92c8 100644
--- a/res/drawable-hdpi/ic_launcher_browser.png
+++ b/res/drawable-hdpi/ic_launcher_browser.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu.png b/res/drawable-hdpi/ic_menu.png
new file mode 100644
index 0000000..00f784f
--- /dev/null
+++ b/res/drawable-hdpi/ic_menu.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_add_bookmark.png b/res/drawable-hdpi/ic_menu_add_bookmark.png
index c54eb7e..28beaaa 100644
--- a/res/drawable-hdpi/ic_menu_add_bookmark.png
+++ b/res/drawable-hdpi/ic_menu_add_bookmark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_bookmarks.png b/res/drawable-hdpi/ic_menu_bookmarks.png
index fd63499..3644acf 100755
--- a/res/drawable-hdpi/ic_menu_bookmarks.png
+++ b/res/drawable-hdpi/ic_menu_bookmarks.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_downloads.png b/res/drawable-hdpi/ic_menu_downloads.png
new file mode 100644
index 0000000..c85f6a2
--- /dev/null
+++ b/res/drawable-hdpi/ic_menu_downloads.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_list.png b/res/drawable-hdpi/ic_menu_list.png
index 2b921b3..cf95f2f 100644
--- a/res/drawable-hdpi/ic_menu_list.png
+++ b/res/drawable-hdpi/ic_menu_list.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_new_window.png b/res/drawable-hdpi/ic_menu_new_window.png
index 36aee01..fa544fc 100644
--- a/res/drawable-hdpi/ic_menu_new_window.png
+++ b/res/drawable-hdpi/ic_menu_new_window.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_pageinfo.png b/res/drawable-hdpi/ic_menu_pageinfo.png
new file mode 100644
index 0000000..293a021
--- /dev/null
+++ b/res/drawable-hdpi/ic_menu_pageinfo.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_settings.png b/res/drawable-hdpi/ic_menu_settings.png
new file mode 100644
index 0000000..46be101
--- /dev/null
+++ b/res/drawable-hdpi/ic_menu_settings.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_share.png b/res/drawable-hdpi/ic_menu_share.png
new file mode 100644
index 0000000..4b69736
--- /dev/null
+++ b/res/drawable-hdpi/ic_menu_share.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_thumbnail.png b/res/drawable-hdpi/ic_menu_thumbnail.png
index 705b02b..bfc99aa 100644
--- a/res/drawable-hdpi/ic_menu_thumbnail.png
+++ b/res/drawable-hdpi/ic_menu_thumbnail.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_windows.png b/res/drawable-hdpi/ic_menu_windows.png
index 0e80009..0a27b95 100644
--- a/res/drawable-hdpi/ic_menu_windows.png
+++ b/res/drawable-hdpi/ic_menu_windows.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pages.png b/res/drawable-hdpi/ic_pages.png
new file mode 100644
index 0000000..3fc2e46
--- /dev/null
+++ b/res/drawable-hdpi/ic_pages.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_partial_secure.png b/res/drawable-hdpi/ic_partial_secure.png
new file mode 100644
index 0000000..76ba96a
--- /dev/null
+++ b/res/drawable-hdpi/ic_partial_secure.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pressed.png b/res/drawable-hdpi/ic_pressed.png
new file mode 100644
index 0000000..fd1c7d9
--- /dev/null
+++ b/res/drawable-hdpi/ic_pressed.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_reload.png b/res/drawable-hdpi/ic_reload.png
new file mode 100644
index 0000000..ebad6da
--- /dev/null
+++ b/res/drawable-hdpi/ic_reload.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_secure.png b/res/drawable-hdpi/ic_secure.png
new file mode 100644
index 0000000..4f15fc4
--- /dev/null
+++ b/res/drawable-hdpi/ic_secure.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_star.png b/res/drawable-hdpi/ic_star.png
new file mode 100644
index 0000000..666c670
--- /dev/null
+++ b/res/drawable-hdpi/ic_star.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_stop.png b/res/drawable-hdpi/ic_stop.png
new file mode 100644
index 0000000..0f1337f
--- /dev/null
+++ b/res/drawable-hdpi/ic_stop.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_web_white.png b/res/drawable-hdpi/ic_web_white.png
new file mode 100644
index 0000000..fec99ca
--- /dev/null
+++ b/res/drawable-hdpi/ic_web_white.png
Binary files differ
diff --git a/res/drawable-hdpi/list_divider_vert.9.png b/res/drawable-hdpi/list_divider_vert.9.png
new file mode 100644
index 0000000..d99730a
--- /dev/null
+++ b/res/drawable-hdpi/list_divider_vert.9.png
Binary files differ
diff --git a/res/drawable-hdpi/pattern_carbon_fiber_dark.png b/res/drawable-hdpi/pattern_carbon_fiber_dark.png
new file mode 100644
index 0000000..cc8e0c5
--- /dev/null
+++ b/res/drawable-hdpi/pattern_carbon_fiber_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/progress_stop.png b/res/drawable-hdpi/progress_stop.png
new file mode 100644
index 0000000..aacece2
--- /dev/null
+++ b/res/drawable-hdpi/progress_stop.png
Binary files differ
diff --git a/res/drawable-hdpi/tab_selected_bg.9.png b/res/drawable-hdpi/tab_selected_bg.9.png
new file mode 100644
index 0000000..4e0f740
--- /dev/null
+++ b/res/drawable-hdpi/tab_selected_bg.9.png
Binary files differ
diff --git a/res/drawable-hdpi/tab_unselected_bg.9.png b/res/drawable-hdpi/tab_unselected_bg.9.png
new file mode 100644
index 0000000..9ab7c56
--- /dev/null
+++ b/res/drawable-hdpi/tab_unselected_bg.9.png
Binary files differ
diff --git a/res/drawable-mdpi/bookmark_dialog_bg.9.png b/res/drawable-mdpi/bookmark_dialog_bg.9.png
new file mode 100644
index 0000000..f169daa
--- /dev/null
+++ b/res/drawable-mdpi/bookmark_dialog_bg.9.png
Binary files differ
diff --git a/res/drawable-mdpi/cab_bg.9.png b/res/drawable-mdpi/cab_bg.9.png
new file mode 100644
index 0000000..caf404f
--- /dev/null
+++ b/res/drawable-mdpi/cab_bg.9.png
Binary files differ
diff --git a/res/drawable-mdpi/crumb_divider.9.png b/res/drawable-mdpi/crumb_divider.9.png
new file mode 100644
index 0000000..8c8fd43
--- /dev/null
+++ b/res/drawable-mdpi/crumb_divider.9.png
Binary files differ
diff --git a/res/drawable/default_video_poster.png b/res/drawable-mdpi/default_video_poster.png
similarity index 100%
rename from res/drawable/default_video_poster.png
rename to res/drawable-mdpi/default_video_poster.png
Binary files differ
diff --git a/res/drawable-mdpi/dialog_full.9.png b/res/drawable-mdpi/dialog_full.9.png
new file mode 100644
index 0000000..2c9027b
--- /dev/null
+++ b/res/drawable-mdpi/dialog_full.9.png
Binary files differ
diff --git a/res/drawable-mdpi/divider_vert.9.png b/res/drawable-mdpi/divider_vert.9.png
new file mode 100644
index 0000000..2c5646e
--- /dev/null
+++ b/res/drawable-mdpi/divider_vert.9.png
Binary files differ
diff --git a/res/drawable-mdpi/empty_bookmark_image.png b/res/drawable-mdpi/empty_bookmark_image.png
new file mode 100644
index 0000000..7e79f35
--- /dev/null
+++ b/res/drawable-mdpi/empty_bookmark_image.png
Binary files differ
diff --git a/res/drawable-mdpi/fav_incognito.png b/res/drawable-mdpi/fav_incognito.png
new file mode 100644
index 0000000..6a120b9
--- /dev/null
+++ b/res/drawable-mdpi/fav_incognito.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_add_string.png b/res/drawable-mdpi/ic_add_string.png
new file mode 100644
index 0000000..e3b95cb
--- /dev/null
+++ b/res/drawable-mdpi/ic_add_string.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_arrow_left.png b/res/drawable-mdpi/ic_arrow_left.png
new file mode 100644
index 0000000..58be4bd
--- /dev/null
+++ b/res/drawable-mdpi/ic_arrow_left.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_arrow_right.png b/res/drawable-mdpi/ic_arrow_right.png
new file mode 100644
index 0000000..6272038
--- /dev/null
+++ b/res/drawable-mdpi/ic_arrow_right.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_back_normal.png b/res/drawable-mdpi/ic_back_normal.png
new file mode 100644
index 0000000..7e09a94
--- /dev/null
+++ b/res/drawable-mdpi/ic_back_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_bookmarks_history_normal.png b/res/drawable-mdpi/ic_bookmarks_history_normal.png
new file mode 100644
index 0000000..60a7b4a
--- /dev/null
+++ b/res/drawable-mdpi/ic_bookmarks_history_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_copy.png b/res/drawable-mdpi/ic_btn_copy.png
new file mode 100644
index 0000000..04fda7f
--- /dev/null
+++ b/res/drawable-mdpi/ic_btn_copy.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_find.png b/res/drawable-mdpi/ic_btn_find.png
new file mode 100755
index 0000000..20e1fbc
--- /dev/null
+++ b/res/drawable-mdpi/ic_btn_find.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_find_next.png b/res/drawable-mdpi/ic_btn_find_next.png
deleted file mode 100644
index abdc247..0000000
--- a/res/drawable-mdpi/ic_btn_find_next.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_find_prev.png b/res/drawable-mdpi/ic_btn_find_prev.png
deleted file mode 100644
index 4e3da1d..0000000
--- a/res/drawable-mdpi/ic_btn_find_prev.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_select_all.png b/res/drawable-mdpi/ic_btn_select_all.png
new file mode 100644
index 0000000..839915b
--- /dev/null
+++ b/res/drawable-mdpi/ic_btn_select_all.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_share.png b/res/drawable-mdpi/ic_btn_share.png
new file mode 100644
index 0000000..44db9b1
--- /dev/null
+++ b/res/drawable-mdpi/ic_btn_share.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_clear_search.png b/res/drawable-mdpi/ic_clear_search.png
new file mode 100644
index 0000000..e8e67b4
--- /dev/null
+++ b/res/drawable-mdpi/ic_clear_search.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_favorite_off_normal.png b/res/drawable-mdpi/ic_favorite_off_normal.png
new file mode 100644
index 0000000..4741464
--- /dev/null
+++ b/res/drawable-mdpi/ic_favorite_off_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_favorite_on_dark.png b/res/drawable-mdpi/ic_favorite_on_dark.png
new file mode 100644
index 0000000..50563c1
--- /dev/null
+++ b/res/drawable-mdpi/ic_favorite_on_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_favorite_on_normal.png b/res/drawable-mdpi/ic_favorite_on_normal.png
new file mode 100644
index 0000000..bd239e8
--- /dev/null
+++ b/res/drawable-mdpi/ic_favorite_on_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_folder.png b/res/drawable-mdpi/ic_folder.png
new file mode 100644
index 0000000..ee85b28
--- /dev/null
+++ b/res/drawable-mdpi/ic_folder.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_forward_normal.png b/res/drawable-mdpi/ic_forward_normal.png
new file mode 100644
index 0000000..f306403
--- /dev/null
+++ b/res/drawable-mdpi/ic_forward_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_go_dark.png b/res/drawable-mdpi/ic_go_dark.png
new file mode 100644
index 0000000..88c0985
--- /dev/null
+++ b/res/drawable-mdpi/ic_go_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_go_normal_white.png b/res/drawable-mdpi/ic_go_normal_white.png
new file mode 100644
index 0000000..1ae9ed9
--- /dev/null
+++ b/res/drawable-mdpi/ic_go_normal_white.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_launcher_browser.png b/res/drawable-mdpi/ic_launcher_browser.png
old mode 100644
new mode 100755
index b76c169..f9d6172
--- a/res/drawable-mdpi/ic_launcher_browser.png
+++ b/res/drawable-mdpi/ic_launcher_browser.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu.png b/res/drawable-mdpi/ic_menu.png
new file mode 100644
index 0000000..520b2c3
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_add_bookmark.png b/res/drawable-mdpi/ic_menu_add_bookmark.png
index ce451b3..3e38bb9 100644
--- a/res/drawable-mdpi/ic_menu_add_bookmark.png
+++ b/res/drawable-mdpi/ic_menu_add_bookmark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_archive_normal.png b/res/drawable-mdpi/ic_menu_archive_normal.png
new file mode 100644
index 0000000..40f25a4
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_archive_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_bookmarks.png b/res/drawable-mdpi/ic_menu_bookmarks.png
old mode 100644
new mode 100755
index c6a3cdb..1ac78b6
--- a/res/drawable-mdpi/ic_menu_bookmarks.png
+++ b/res/drawable-mdpi/ic_menu_bookmarks.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_cab_close.png b/res/drawable-mdpi/ic_menu_cab_close.png
new file mode 100644
index 0000000..3451027
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_cab_close.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_cab_pencil.png b/res/drawable-mdpi/ic_menu_cab_pencil.png
new file mode 100644
index 0000000..5d6ab57
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_cab_pencil.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_downloads_normal.png b/res/drawable-mdpi/ic_menu_downloads_normal.png
new file mode 100644
index 0000000..37b6b75
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_downloads_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_findonpage_normal.png b/res/drawable-mdpi/ic_menu_findonpage_normal.png
new file mode 100644
index 0000000..bea6e44
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_findonpage_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_incognito_normal.png b/res/drawable-mdpi/ic_menu_incognito_normal.png
new file mode 100644
index 0000000..2e78dc6
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_incognito_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_list.png b/res/drawable-mdpi/ic_menu_list.png
index 36bf8d6..b2d35cc 100644
--- a/res/drawable-mdpi/ic_menu_list.png
+++ b/res/drawable-mdpi/ic_menu_list.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_new_window.png b/res/drawable-mdpi/ic_menu_new_window.png
index 4fdea6c..c767979 100644
--- a/res/drawable-mdpi/ic_menu_new_window.png
+++ b/res/drawable-mdpi/ic_menu_new_window.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_overflow.png b/res/drawable-mdpi/ic_menu_overflow.png
new file mode 100644
index 0000000..e565760
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_overflow.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_pageinfo_normal.png b/res/drawable-mdpi/ic_menu_pageinfo_normal.png
new file mode 100644
index 0000000..3422e98
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_pageinfo_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_settings_normal.png b/res/drawable-mdpi/ic_menu_settings_normal.png
new file mode 100644
index 0000000..bd2c30a
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_settings_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_share_normal.png b/res/drawable-mdpi/ic_menu_share_normal.png
new file mode 100644
index 0000000..4410baa
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_share_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_thumbnail.png b/res/drawable-mdpi/ic_menu_thumbnail.png
index be4ed5e..74a87e2 100644
--- a/res/drawable-mdpi/ic_menu_thumbnail.png
+++ b/res/drawable-mdpi/ic_menu_thumbnail.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_windows.png b/res/drawable-mdpi/ic_menu_windows.png
index c33de2b..cdc4d83 100644
--- a/res/drawable-mdpi/ic_menu_windows.png
+++ b/res/drawable-mdpi/ic_menu_windows.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pages.png b/res/drawable-mdpi/ic_pages.png
new file mode 100644
index 0000000..fba4651
--- /dev/null
+++ b/res/drawable-mdpi/ic_pages.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_partial_secure.png b/res/drawable-mdpi/ic_partial_secure.png
new file mode 100644
index 0000000..b3ca0cc
--- /dev/null
+++ b/res/drawable-mdpi/ic_partial_secure.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pressed.png b/res/drawable-mdpi/ic_pressed.png
new file mode 100644
index 0000000..fd1c7d9
--- /dev/null
+++ b/res/drawable-mdpi/ic_pressed.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_refresh_normal.png b/res/drawable-mdpi/ic_refresh_normal.png
new file mode 100644
index 0000000..f8ce51d
--- /dev/null
+++ b/res/drawable-mdpi/ic_refresh_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_category_bookmark.png b/res/drawable-mdpi/ic_search_category_bookmark.png
old mode 100755
new mode 100644
index d228408..4b3bd2d
--- a/res/drawable-mdpi/ic_search_category_bookmark.png
+++ b/res/drawable-mdpi/ic_search_category_bookmark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_category_browser.png b/res/drawable-mdpi/ic_search_category_browser.png
index da8d4e3..d721425 100644
--- a/res/drawable-mdpi/ic_search_category_browser.png
+++ b/res/drawable-mdpi/ic_search_category_browser.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_category_history.png b/res/drawable-mdpi/ic_search_category_history.png
old mode 100755
new mode 100644
index 12cd51c..1a3fc98
--- a/res/drawable-mdpi/ic_search_category_history.png
+++ b/res/drawable-mdpi/ic_search_category_history.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_category_suggest.png b/res/drawable-mdpi/ic_search_category_suggest.png
old mode 100755
new mode 100644
index a4ed7aa..0216581
--- a/res/drawable-mdpi/ic_search_category_suggest.png
+++ b/res/drawable-mdpi/ic_search_category_suggest.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_normal.png b/res/drawable-mdpi/ic_search_normal.png
new file mode 100644
index 0000000..e1fa6d3
--- /dev/null
+++ b/res/drawable-mdpi/ic_search_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_secure.png b/res/drawable-mdpi/ic_secure.png
new file mode 100644
index 0000000..70d7edd
--- /dev/null
+++ b/res/drawable-mdpi/ic_secure.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_stop_normal.png b/res/drawable-mdpi/ic_stop_normal.png
new file mode 100644
index 0000000..6bd22f9
--- /dev/null
+++ b/res/drawable-mdpi/ic_stop_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_tab_close.png b/res/drawable-mdpi/ic_tab_close.png
new file mode 100644
index 0000000..2f23842
--- /dev/null
+++ b/res/drawable-mdpi/ic_tab_close.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_web_white.png b/res/drawable-mdpi/ic_web_white.png
new file mode 100644
index 0000000..fec99ca
--- /dev/null
+++ b/res/drawable-mdpi/ic_web_white.png
Binary files differ
diff --git a/res/drawable-mdpi/list_divider_vert.9.png b/res/drawable-mdpi/list_divider_vert.9.png
new file mode 100644
index 0000000..d99730a
--- /dev/null
+++ b/res/drawable-mdpi/list_divider_vert.9.png
Binary files differ
diff --git a/res/drawable-mdpi/menu_dropdown.9.png b/res/drawable-mdpi/menu_dropdown.9.png
new file mode 100644
index 0000000..562d55b
--- /dev/null
+++ b/res/drawable-mdpi/menu_dropdown.9.png
Binary files differ
diff --git a/res/drawable/pattern_carbon_fiber_dark.png b/res/drawable-mdpi/pattern_carbon_fiber_dark.png
similarity index 100%
rename from res/drawable/pattern_carbon_fiber_dark.png
rename to res/drawable-mdpi/pattern_carbon_fiber_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/progress.9.png b/res/drawable-mdpi/progress.9.png
new file mode 100644
index 0000000..08de04c
--- /dev/null
+++ b/res/drawable-mdpi/progress.9.png
Binary files differ
diff --git a/res/drawable-mdpi/progress_stop.png b/res/drawable-mdpi/progress_stop.png
new file mode 100644
index 0000000..a85f987
--- /dev/null
+++ b/res/drawable-mdpi/progress_stop.png
Binary files differ
diff --git a/res/drawable-mdpi/tab_selected_bg.9.png b/res/drawable-mdpi/tab_selected_bg.9.png
new file mode 100644
index 0000000..261982e
--- /dev/null
+++ b/res/drawable-mdpi/tab_selected_bg.9.png
Binary files differ
diff --git a/res/drawable-mdpi/tab_unselected_bg.9.png b/res/drawable-mdpi/tab_unselected_bg.9.png
new file mode 100644
index 0000000..5d483e0
--- /dev/null
+++ b/res/drawable-mdpi/tab_unselected_bg.9.png
Binary files differ
diff --git a/res/drawable-mdpi/tabbar_bg.9.png b/res/drawable-mdpi/tabbar_bg.9.png
new file mode 100644
index 0000000..bb9928d
--- /dev/null
+++ b/res/drawable-mdpi/tabbar_bg.9.png
Binary files differ
diff --git a/res/drawable-mdpi/text_field.9.png b/res/drawable-mdpi/text_field.9.png
new file mode 100644
index 0000000..92de7c8
--- /dev/null
+++ b/res/drawable-mdpi/text_field.9.png
Binary files differ
diff --git a/res/drawable-mdpi/text_field_focused.9.png b/res/drawable-mdpi/text_field_focused.9.png
new file mode 100644
index 0000000..6e84bb3
--- /dev/null
+++ b/res/drawable-mdpi/text_field_focused.9.png
Binary files differ
diff --git a/res/drawable-mdpi/text_field_results.9.png b/res/drawable-mdpi/text_field_results.9.png
new file mode 100644
index 0000000..167c42d
--- /dev/null
+++ b/res/drawable-mdpi/text_field_results.9.png
Binary files differ
diff --git a/res/drawable-mdpi/urlbar_bg.9.png b/res/drawable-mdpi/urlbar_bg.9.png
new file mode 100644
index 0000000..18b49e7
--- /dev/null
+++ b/res/drawable-mdpi/urlbar_bg.9.png
Binary files differ
diff --git a/res/menu/bookmarks.xml b/res/drawable/browserbarbutton.xml
similarity index 63%
copy from res/menu/bookmarks.xml
copy to res/drawable/browserbarbutton.xml
index a8781c2..d3eebbe 100644
--- a/res/menu/bookmarks.xml
+++ b/res/drawable/browserbarbutton.xml
@@ -1,12 +1,12 @@
 <?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2008 The Android Open Source Project
+<!-- Copyright (C) 2010 The Android Open Source Project
 
      Licensed under the Apache License, Version 2.0 (the "License");
      you may not use this file except in compliance with the License.
      You may obtain a copy of the License at
-  
+
           http://www.apache.org/licenses/LICENSE-2.0
-  
+
      Unless required by applicable law or agreed to in writing, software
      distributed under the License is distributed on an "AS IS" BASIS,
      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@@ -14,10 +14,8 @@
      limitations under the License.
 -->
 
-<menu xmlns:android="http://schemas.android.com/apk/res/android">
-    <item android:id="@+id/new_context_menu_id"
-        android:icon="@drawable/ic_menu_add_bookmark"
-        android:title="@string/bookmark_page" />
-    <item android:id="@+id/switch_mode_menu_id"
-        />
-</menu>
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+    <item android:state_pressed="true"
+            android:drawable="@drawable/ic_pressed" />
+    <item android:state_pressed="false" android:drawable="@drawable/clear" />
+</selector>
diff --git a/res/drawable/button_bg_selected.xml b/res/drawable/button_bg_selected.xml
new file mode 100644
index 0000000..d0c677b
--- /dev/null
+++ b/res/drawable/button_bg_selected.xml
@@ -0,0 +1,18 @@
+<?xml version="1.0" encoding="utf-8"?>
+    <!--
+        Copyright (C) 2010 The Android Open Source Project Licensed under the
+        Apache License, Version 2.0 (the "License"); you may not use this file
+        except in compliance with the License. You may obtain a copy of the
+        License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+        applicable law or agreed to in writing, software distributed under the
+        License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+        CONDITIONS OF ANY KIND, either express or implied. See the License for
+        the specific language governing permissions and limitations under the
+        License.
+    -->
+<shape
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:shape="rectangle">
+    <solid
+        android:color="#ff4d83ba" />
+</shape>
\ No newline at end of file
diff --git a/res/anim/dialog_exit.xml b/res/drawable/clear.xml
similarity index 62%
rename from res/anim/dialog_exit.xml
rename to res/drawable/clear.xml
index dacb5c3..267db10 100644
--- a/res/anim/dialog_exit.xml
+++ b/res/drawable/clear.xml
@@ -1,5 +1,5 @@
 <?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2007 The Android Open Source Project
+<!-- Copyright (C) 2010 The Android Open Source Project
 
      Licensed under the Apache License, Version 2.0 (the "License");
      you may not use this file except in compliance with the License.
@@ -14,9 +14,10 @@
      limitations under the License.
 -->
 
-<set xmlns:android="http://schemas.android.com/apk/res/android"
-        android:interpolator="@android:anim/accelerate_interpolator">
-    <translate android:fromYDelta="0" android:toYDelta="50%" android:duration="50"/>
-    <alpha android:fromAlpha="1.0" android:toAlpha="0.0" android:duration="50" />
-</set>
-
+<!-- Used by browserbarbutton to show a clear background for the non pressed
+        state -->
+<shape xmlns:android="http://schemas.android.com/apk/res/android">
+    <solid android:color="#00000000"/>
+    <padding android:left="4dp" android:top="4dp"
+        android:right="4dp" android:bottom="4dp" />
+</shape>
diff --git a/res/drawable/ic_menu_incognito.png b/res/drawable/ic_menu_incognito.png
new file mode 100644
index 0000000..d5a7022
--- /dev/null
+++ b/res/drawable/ic_menu_incognito.png
Binary files differ
diff --git a/res/drawable/preview.png b/res/drawable/preview.png
new file mode 100644
index 0000000..f05710f
--- /dev/null
+++ b/res/drawable/preview.png
Binary files differ
diff --git a/res/anim/dialog_exit.xml b/res/drawable/tab_background.xml
similarity index 62%
copy from res/anim/dialog_exit.xml
copy to res/drawable/tab_background.xml
index dacb5c3..6fc3ee3 100644
--- a/res/anim/dialog_exit.xml
+++ b/res/drawable/tab_background.xml
@@ -1,5 +1,5 @@
 <?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2007 The Android Open Source Project
+<!-- Copyright (C) 2010 The Android Open Source Project
 
      Licensed under the Apache License, Version 2.0 (the "License");
      you may not use this file except in compliance with the License.
@@ -14,9 +14,13 @@
      limitations under the License.
 -->
 
-<set xmlns:android="http://schemas.android.com/apk/res/android"
-        android:interpolator="@android:anim/accelerate_interpolator">
-    <translate android:fromYDelta="0" android:toYDelta="50%" android:duration="50"/>
-    <alpha android:fromAlpha="1.0" android:toAlpha="0.0" android:duration="50" />
-</set>
-
+<selector
+    xmlns:android="http://schemas.android.com/apk/res/android">
+    <item
+        android:state_activated="true"
+        android:drawable="@drawable/tab_selected_bg" />
+    <item
+        android:state_activated="false"
+        android:drawable="@drawable/tab_unselected_bg">
+    </item>
+</selector>
diff --git a/res/layout-land/http_authentication.xml b/res/layout-land/http_authentication.xml
index c008ceb..3fa7e4f 100644
--- a/res/layout-land/http_authentication.xml
+++ b/res/layout-land/http_authentication.xml
@@ -18,7 +18,7 @@
     android:layout_width="match_parent"
     android:layout_height="wrap_content"
     android:gravity="center_horizontal"
-    android:orientation="vertical">
+    android:orientation="vertical" >
 
     <TableLayout
         android:layout_width="match_parent"
@@ -28,15 +28,11 @@
     
         <TableRow>
             <TextView android:id="@+id/username_view"
-                android:textSize="18sp"
-                android:textColor="@color/username_text"
                 android:text="@string/username"
                 android:gravity="right"
                 android:layout_marginLeft="20dip" />
 
             <EditText android:id="@+id/username_edit"
-                android:textSize="18sp"
-                android:textColor="@color/username_edit"
                 android:scrollHorizontally="true"
                 android:autoText="false"
                 android:capitalize="none"
@@ -49,15 +45,11 @@
 
         <TableRow>
             <TextView android:id="@+id/password_view"
-                android:textSize="18sp"
-                android:textColor="@color/password_text"
                 android:text="@string/password"
                 android:gravity="right"
                 android:layout_marginLeft="20dip" />
     
             <EditText android:id="@+id/password_edit"
-                android:textSize="18sp"
-                android:textColor="@color/password_edit"
                 android:scrollHorizontally="true"
                 android:autoText="false"
                 android:capitalize="none"
diff --git a/res/layout-land/ssl_certificate.xml b/res/layout-land/ssl_certificate.xml
index 44c5904..6505fe5 100644
--- a/res/layout-land/ssl_certificate.xml
+++ b/res/layout-land/ssl_certificate.xml
@@ -56,8 +56,6 @@
                 android:id="@+id/issued_to_header"
                 android:text="@string/issued_to"
                 android:textStyle="bold"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
                 android:layout_marginLeft="20dip"
@@ -69,15 +67,11 @@
                 <TextView 
                     android:id="@+id/to_common_header"
                     android:text="@string/common_name"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_label"
                     android:gravity="left"
                     android:layout_marginLeft="20dip" />
 
                 <TextView 
                     android:id="@+id/to_common"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_value"
                     android:gravity="left"
                     android:layout_marginLeft="10dip"
                     android:layout_marginRight="20dip"
@@ -89,15 +83,11 @@
                 <TextView 
                     android:id="@+id/to_org_header"
                     android:text="@string/org_name"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_label"
                     android:gravity="left"
                     android:layout_marginLeft="20dip" />
 
                 <TextView 
                     android:id="@+id/to_org"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_value"
                     android:gravity="left"
                     android:layout_marginLeft="10dip"
                     android:layout_marginRight="20dip"
@@ -109,15 +99,11 @@
                 <TextView 
                     android:id="@+id/to_org_unit_header"
                     android:text="@string/org_unit"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_label"
                     android:gravity="left"
                     android:layout_marginLeft="20dip" />
 
                 <TextView 
                     android:id="@+id/to_org_unit"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_value"
                     android:gravity="left"
                     android:layout_marginLeft="10dip"
                     android:layout_marginRight="20dip"
@@ -129,8 +115,6 @@
                 android:id="@+id/issued_to_header"
                 android:text="@string/issued_by"
                 android:textStyle="bold"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
                 android:layout_marginLeft="20dip"
@@ -142,15 +126,11 @@
                 <TextView 
                     android:id="@+id/by_common_header"
                     android:text="@string/common_name"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_label"
                     android:gravity="left"
                     android:layout_marginLeft="20dip" />
 
                 <TextView 
                     android:id="@+id/by_common"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_value"
                     android:gravity="left"
                     android:layout_marginLeft="10dip"
                     android:layout_marginRight="20dip"
@@ -162,15 +142,11 @@
                 <TextView 
                     android:id="@+id/by_org_header"
                     android:text="@string/org_name"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_label"
                     android:gravity="left"
                     android:layout_marginLeft="20dip" />
 
                 <TextView 
                     android:id="@+id/by_org"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_value"
                     android:gravity="left"
                     android:layout_marginLeft="10dip"
                     android:layout_marginRight="20dip"
@@ -182,15 +158,11 @@
                 <TextView 
                     android:id="@+id/by_org_unit_header"
                     android:text="@string/org_unit"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_label"
                     android:gravity="left"
                     android:layout_marginLeft="20dip" />
 
                 <TextView 
                     android:id="@+id/by_org_unit"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_value"
                     android:gravity="left"
                     android:layout_marginLeft="10dip"
                     android:layout_marginRight="20dip"
@@ -204,8 +176,6 @@
                 android:layout_width="wrap_content"
                 android:text="@string/validity_period"
                 android:textStyle="bold"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
                 android:layout_marginBottom="7dip" />
@@ -217,8 +187,6 @@
                     android:layout_width="wrap_content" 
                     android:layout_height="wrap_content"
                     android:text="@string/issued_on"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_label"
                     android:gravity="left"
                     android:layout_marginLeft="20dip" />
         
@@ -226,8 +194,6 @@
                     android:id="@+id/issued_on"
                     android:layout_height="wrap_content"
                     android:layout_width="wrap_content"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_value"
                     android:gravity="left"
                     android:layout_marginLeft="10dip"
                     android:layout_marginRight="20dip"
@@ -242,8 +208,6 @@
                     android:layout_width="wrap_content" 
                     android:layout_height="wrap_content"
                     android:text="@string/expires_on"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_label"
                     android:gravity="left"
                     android:layout_marginLeft="20dip" />
                 
@@ -251,8 +215,6 @@
                     android:id="@+id/expires_on"
                     android:layout_height="wrap_content"
                     android:layout_width="wrap_content"
-                    android:textSize="14sp"
-                    android:textColor="@color/ssl_text_value"
                     android:gravity="left"
                     android:layout_marginLeft="10dip"
                     android:layout_marginRight="20dip"
diff --git a/res/layout/autofill_settings_fragment.xml b/res/layout/autofill_settings_fragment.xml
new file mode 100644
index 0000000..327cbd1
--- /dev/null
+++ b/res/layout/autofill_settings_fragment.xml
@@ -0,0 +1,272 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+    android:fillViewport="true">
+
+    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+        android:layout_width="match_parent"
+        android:layout_height="match_parent"
+        android:orientation="vertical"
+        android:padding="20dip">
+
+    <TextView
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:textAppearance="?android:attr/textAppearanceLarge"
+        android:text="@string/pref_autofill_profile_editor" />
+
+    <View
+        android:layout_height="20dip"
+        android:layout_width="match_parent" />
+
+    <TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:layout_weight="1"
+        android:stretchColumns="1">
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <TextView
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:gravity="center_vertical"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:text="@string/autofill_profile_editor_name" />
+            <EditText android:id="@+id/autofill_profile_editor_name_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:inputType="textPersonName|textCapWords"
+                android:singleLine="true" />
+        </TableRow>
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <TextView
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:gravity="center_vertical"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:text="@string/autofill_profile_editor_company_name" />
+            <EditText android:id="@+id/autofill_profile_editor_company_name_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:singleLine="true" />
+        </TableRow>
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:orientation="vertical">
+                <TextView
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:gravity="center_vertical"
+                    android:textAppearance="?android:attr/textAppearanceMedium"
+                    android:text="@string/autofill_profile_editor_address_line_1" />
+                 <TextView
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:gravity="center_vertical"
+                    android:textAppearance="?android:attr/textAppearanceSmall"
+                    android:text="@string/autofill_profile_editor_address_line_1_hint" />
+            </LinearLayout>
+            <EditText android:id="@+id/autofill_profile_editor_address_line_1_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:singleLine="true" />
+        </TableRow>
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:orientation="vertical">
+                <TextView
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:gravity="center_vertical"
+                    android:textAppearance="?android:attr/textAppearanceMedium"
+                    android:text="@string/autofill_profile_editor_address_line_2" />
+                 <TextView
+                    android:layout_width="wrap_content"
+                    android:layout_height="wrap_content"
+                    android:gravity="center_vertical"
+                    android:textAppearance="?android:attr/textAppearanceSmall"
+                    android:text="@string/autofill_profile_editor_address_line_2_hint" />
+            </LinearLayout>
+            <EditText android:id="@+id/autofill_profile_editor_address_line_2_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:singleLine="true" />
+        </TableRow>
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <TextView
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:gravity="center_vertical"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:text="@string/autofill_profile_editor_city" />
+            <EditText android:id="@+id/autofill_profile_editor_city_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:singleLine="true" />
+        </TableRow>
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <TextView
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:gravity="center_vertical"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:text="@string/autofill_profile_editor_state" />
+            <EditText android:id="@+id/autofill_profile_editor_state_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:singleLine="true" />
+        </TableRow>
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <TextView
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:gravity="center_vertical"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:text="@string/autofill_profile_editor_zip_code" />
+            <EditText android:id="@+id/autofill_profile_editor_zip_code_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:singleLine="true" />
+        </TableRow>
+       <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <TextView
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:gravity="center_vertical"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:text="@string/autofill_profile_editor_country" />
+            <EditText android:id="@+id/autofill_profile_editor_country_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:singleLine="true" />
+        </TableRow>
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <TextView
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:gravity="center_vertical"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:text="@string/autofill_profile_editor_phone_number" />
+            <EditText android:id="@+id/autofill_profile_editor_phone_number_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:singleLine="true"
+                android:phoneNumber="true" />
+        </TableRow>
+        <TableRow
+            android:layout_height="match_parent"
+            android:layout_weight="1">
+            <TextView
+                android:layout_width="wrap_content"
+                android:layout_height="wrap_content"
+                android:gravity="center_vertical"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:text="@string/autofill_profile_editor_email_address" />
+            <EditText android:id="@+id/autofill_profile_editor_email_address_edit"
+                android:layout_width="match_parent"
+                android:layout_height="wrap_content"
+                android:padding="10dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:inputType="textEmailAddress"
+                android:singleLine="true" />
+        </TableRow>
+    </TableLayout>
+
+    <View
+        android:layout_height="20dip"
+        android:layout_width="match_parent" />
+
+    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:orientation="horizontal"
+        android:gravity="center">
+    <Button
+        android:id="@+id/autofill_profile_editor_save_button"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:text="@string/autofill_profile_editor_save_profile"
+        android:textAppearance="?android:attr/textAppearanceMedium" />
+
+    <Button
+        android:id="@+id/autofill_profile_editor_cancel_button"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:text="@string/cancel"
+        android:textAppearance="?android:attr/textAppearanceMedium" />
+
+    <Button
+        android:id="@+id/autofill_profile_editor_delete_button"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:text="@string/autofill_profile_editor_delete_profile"
+        android:textAppearance="?android:attr/textAppearanceMedium" />
+    </LinearLayout>
+
+    </LinearLayout>
+</ScrollView>
diff --git a/res/layout/bookmark_thumbnail.xml b/res/layout/bookmark_thumbnail.xml
index 1f017d0..91d8db7 100644
--- a/res/layout/bookmark_thumbnail.xml
+++ b/res/layout/bookmark_thumbnail.xml
@@ -23,39 +23,12 @@
 
     <ImageView android:id="@+id/thumb"
         android:src="@drawable/browser_thumbnail"
-        android:scaleType="center"
-        android:layout_height="wrap_content"
-        android:layout_width="wrap_content"
+        android:scaleType="centerCrop"
+        android:layout_height="@dimen/bookmarkThumbnailHeight"
+        android:layout_width="@dimen/bookmarkThumbnailWidth"
         android:layout_gravity="center"
         />
 
-    <!-- FIXME: Want to have a gradient over the thumb -->
-
-    <!-- This holds the star for addbookmark -->
-    <LinearLayout android:id="@+id/holder"
-        android:layout_height="match_parent"
-        android:layout_width="match_parent"
-        android:orientation="horizontal"
-        android:background="#99000000"
-        android:gravity="center"
-        android:layout_alignBottom="@+id/thumb"
-        android:layout_alignTop="@+id/thumb"
-        >
-        <ImageView
-            android:layout_height="wrap_content"
-            android:layout_width="wrap_content"
-            android:src="@drawable/ic_list_bookmark"
-            />
-        <TextView
-            android:layout_height="wrap_content"
-            android:layout_width="wrap_content"
-            android:textAppearance="?android:attr/textAppearanceSmall"
-            android:textStyle="bold"
-            android:textColor="@color/white"
-            android:text="@string/add_bookmark_short"
-            />
-    </LinearLayout>
-
     <TextView android:id="@+id/label"
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
diff --git a/res/layout/bookmarks.xml b/res/layout/bookmarks.xml
new file mode 100644
index 0000000..fa08353
--- /dev/null
+++ b/res/layout/bookmarks.xml
@@ -0,0 +1,42 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2008 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+  
+          http://www.apache.org/licenses/LICENSE-2.0
+  
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<FrameLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent">
+    <GridView
+        android:id="@+id/grid"
+        android:layout_width="match_parent"
+        android:layout_height="match_parent"
+        android:horizontalSpacing="16dip"
+        android:verticalSpacing="16dip"
+        android:stretchMode="spacingWidth"
+        android:scrollbarStyle="insideInset"
+        android:listSelector="@android:drawable/gallery_thumb"
+        android:drawSelectorOnTop="true"
+        android:focusable="true"
+        android:focusableInTouchMode="true"
+        android:numColumns="auto_fit" />
+    <TextView
+        android:id="@android:id/empty"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_gravity="center"
+        android:textAppearance="?android:attr/textAppearanceLarge"
+        android:text="@string/empty_bookmarks_folder"
+        android:visibility="gone" />
+</FrameLayout>
diff --git a/res/layout/bookmarks_history.xml b/res/layout/bookmarks_history.xml
new file mode 100644
index 0000000..a89a2b9
--- /dev/null
+++ b/res/layout/bookmarks_history.xml
@@ -0,0 +1,86 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2009 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+  
+          http://www.apache.org/licenses/LICENSE-2.0
+  
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<LinearLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+    android:paddingTop="8dip"
+    android:paddingLeft="16dip"
+    android:paddingRight="16dip"
+    android:orientation="vertical"
+    android:background="@color/black">
+    <RelativeLayout
+        android:id="@+id/bar"
+        android:layout_width="match_parent"
+        android:layout_height="48dip">
+        <LinearLayout
+            android:id="@+id/tabs"
+            android:layout_width="wrap_content"
+            android:layout_height="match_parent"
+            android:paddingLeft="16dip"
+            android:paddingRight="16dip">
+            <TextView
+                android:id="@+id/historytab"
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                android:paddingLeft="32dip"
+                android:paddingRight="32dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:gravity="center_vertical"
+                android:text="@string/tab_history"
+                android:drawableLeft="@drawable/ic_tab_history_selected"
+                android:drawablePadding="16dip" />
+            <ImageView
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                android:src="@drawable/divider_vert" />
+            <TextView
+                android:id="@+id/bmtab"
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                android:paddingLeft="32dip"
+                android:paddingRight="32dip"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:gravity="center_vertical"
+                android:text="@string/bookmarks"
+                android:drawableLeft="@drawable/ic_tab_bookmarks_selected"
+                android:drawablePadding="16dip" />
+            <com.android.browser.BreadCrumbView
+                android:id="@+id/crumbs"
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                android:paddingLeft="16dip"
+                android:paddingRight="16dip" />
+        </LinearLayout>
+        <TextView
+            android:id="@+id/addbm"
+            android:layout_width="wrap_content"
+            android:layout_height="match_parent"
+            android:text="@string/add_new_bookmark"
+            android:layout_alignParentRight="true"
+            android:textAppearance="?android:attr/textAppearanceMedium"
+            android:gravity="center_vertical"
+            android:background="@null"
+            android:drawableLeft="@drawable/ic_favorite_off_normal"
+            android:drawablePadding="16dip" />
+    </RelativeLayout>
+    <FrameLayout
+        android:id="@+id/fragment"
+        android:paddingTop="8dip"
+        android:layout_width="match_parent"
+        android:layout_height="0dip"
+        android:layout_weight="1.0" />
+</LinearLayout>
diff --git a/res/layout/bookmarkstackwidget.xml b/res/layout/bookmarkstackwidget.xml
new file mode 100644
index 0000000..c8c88c4
--- /dev/null
+++ b/res/layout/bookmarkstackwidget.xml
@@ -0,0 +1,40 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<RelativeLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent">
+    <StackView
+        android:id="@+id/stackwidget_stack"
+        android:layout_width="match_parent"
+        android:layout_height="match_parent"
+        android:layout_gravity="center"
+        android:paddingTop="16dip"
+        android:paddingBottom="8dip"
+        android:paddingLeft="8dip"
+        android:paddingRight="8dip"
+        android:background="#00000000"
+        android:cacheColorHint="#00000000"
+        android:autoStart="true" />
+    <ImageView
+        android:id="@+id/logo"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_alignParentTop="true"
+        android:layout_centerHorizontal="true"
+        android:src="@drawable/ic_launcher_shortcut_browser_bookmark" />
+</RelativeLayout>
diff --git a/res/layout/bookmarkstackwidget_item.xml b/res/layout/bookmarkstackwidget_item.xml
new file mode 100644
index 0000000..e7992f7
--- /dev/null
+++ b/res/layout/bookmarkstackwidget_item.xml
@@ -0,0 +1,47 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<RelativeLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:id="@+id/stack_item"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+    android:padding="16dip">
+    <ImageView
+        android:id="@+id/thumb"
+        android:src="@drawable/browser_thumbnail"
+        android:layout_height="match_parent"
+        android:layout_width="match_parent"
+        android:scaleType="fitXY"
+        android:layout_centerInParent="true" />
+    <TextView
+        android:id="@+id/label"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:textAppearance="?android:attr/textAppearanceSmall"
+        android:textStyle="bold"
+        android:textColor="@color/white"
+        android:maxLines="1"
+        android:paddingLeft="2dip"
+        android:paddingRight="2dip"
+        android:paddingTop="0dip"
+        android:paddingBottom="0dip"
+        android:scrollHorizontally="true"
+        android:ellipsize="marquee"
+        android:layout_alignBottom="@id/thumb"
+        android:layout_alignLeft="@id/thumb"
+        android:layout_alignRight="@id/thumb" />
+</RelativeLayout>
diff --git a/res/layout/bookmarkwidget.xml b/res/layout/bookmarkwidget.xml
index 2416e4f..c7c2a90 100644
--- a/res/layout/bookmarkwidget.xml
+++ b/res/layout/bookmarkwidget.xml
@@ -31,7 +31,7 @@
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
             android:padding="10dip"
-            android:src="@drawable/ic_btn_find_prev" />
+            android:src="@*android:drawable/ic_btn_find_prev" />
 
         <TextView
             android:id="@+id/title"
@@ -49,7 +49,7 @@
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
             android:padding="10dip"
-            android:src="@drawable/ic_btn_find_next" />
+            android:src="@*android:drawable/ic_btn_find_next" />
 
     </LinearLayout>
 
diff --git a/res/layout/browser_add_bookmark.xml b/res/layout/browser_add_bookmark.xml
index e8a08a4..7e518dd 100644
--- a/res/layout/browser_add_bookmark.xml
+++ b/res/layout/browser_add_bookmark.xml
@@ -15,25 +15,62 @@
 -->
 
 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
-    android:layout_width="match_parent"
+    android:layout_width="@dimen/add_bookmark_width"
     android:layout_height="wrap_content"
     android:orientation="vertical"
     >
+    <RelativeLayout android:id="@+id/crumb_holder"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:visibility="gone"
+        >
+        <com.android.browser.BreadCrumbView android:id="@+id/crumbs"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_alignParentLeft="true"
+            android:layout_toLeftOf="@+id/add_divider"
+            />
+        <!-- FIXME: The drawable does not line up properly. We may also want a
+            different asset in the final version. -->
+        <TextView
+            android:id="@+id/add_new_folder"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_alignParentRight="true"
+            android:layout_alignBaseline="@+id/crumbs"
+            android:drawableLeft="@drawable/ic_add_string"
+            android:text="@string/new_folder"
+            android:visibility="gone"
+            android:textAppearance="?android:attr/textAppearanceMedium" />
+        <ImageView android:id="@+id/add_divider"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:layout_toLeftOf="@+id/add_new_folder"
+            android:src="@drawable/crumb_divider"
+            />
+    </RelativeLayout>
+    <!-- FIXME: The drawable does not line up properly. We may also want a
+        different asset in the final version. -->
+    <TextView android:id="@+id/fake_title"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:drawableLeft="@drawable/ic_list_bookmark"
+        android:text="@string/bookmark_this_page"
+        android:layout_gravity="left"
+        android:textAppearance="?android:attr/textAppearanceMedium" />
 
-    <ImageView android:id="@+id/titleDivider"
+    <View android:id="@+id/titleDivider"
         android:layout_width="match_parent"
         android:layout_height="1dip"
-        android:scaleType="fitXY"
         android:gravity="fill_horizontal"
-        android:src="@drawable/dialog_divider_horizontal_light"
-        android:layout_marginLeft="10dip"
-        android:layout_marginRight="10dip"/>
+        android:background="?android:attr/colorForeground"
+        />
 
-    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    <!-- XXX Use a TableLayout instead -->
+    <RelativeLayout android:id="@+id/default_view"
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
         android:layout_weight="1"
-        android:orientation="vertical"
         android:paddingTop="5dip"
         android:paddingBottom="13dip"
         android:paddingLeft="20dip"
@@ -43,6 +80,10 @@
             android:id="@+id/titleText"
             android:layout_height="wrap_content"
             android:layout_width="wrap_content"
+            android:layout_alignParentTop="true"
+            android:layout_marginRight="50dip"
+            android:layout_marginBottom="40dip"
+            android:layout_marginTop="40dip"
             android:text="@string/name"
             android:gravity="left"
             android:textAppearance="?android:attr/textAppearanceMedium" />
@@ -50,10 +91,13 @@
         <EditText
             android:id="@+id/title"
             android:layout_height="wrap_content"
-            android:layout_width="250dip"
+            android:layout_width="325dip"
             android:gravity="fill_horizontal"
+            android:layout_alignBaseline="@+id/titleText"
+            android:layout_toRightOf="@+id/titleText"
             android:inputType="textCapSentences"
             android:selectAllOnFocus="true"
+            android:ellipsize="end"
             android:textAppearance="?android:attr/textAppearanceMedium" />
                 
 
@@ -64,23 +108,85 @@
             android:layout_width="wrap_content"
             android:text="@string/location"
             android:gravity="left"
+            android:layout_below="@+id/titleText"
+            android:layout_alignLeft="@+id/titleText"
+            android:layout_marginBottom="40dip"
+            android:layout_marginRight="20dip"
             android:textAppearance="?android:attr/textAppearanceMedium" />
                 
         <EditText
             android:id="@+id/address"
             android:layout_height="wrap_content"
-            android:layout_width="250dip"
+            android:layout_width="325dip"
             android:hint="@string/http"
+            android:layout_alignBaseline="@+id/addressText"
+            android:layout_alignLeft="@+id/title"
             android:gravity="fill_horizontal"
             android:inputType="textUri"
             android:selectAllOnFocus="true"
+            android:ellipsize="end"
             android:textAppearance="?android:attr/textAppearanceMedium" />
+
+        <TextView
+            android:id="@+id/add_to"
+            android:layout_height="wrap_content"
+            android:layout_width="wrap_content"
+            android:text="@string/containing_folder"
+            android:layout_below="@+id/addressText"
+            android:layout_alignLeft="@+id/titleText"
+            android:layout_marginRight="20dip"
+            android:textAppearance="?android:attr/textAppearanceMedium" />
+
+        <TextView
+            android:id="@+id/folder"
+            android:layout_height="wrap_content"
+            android:layout_width="250dip"
+            android:layout_alignLeft="@+id/title"
+            android:layout_alignBaseline="@+id/add_to"
+            android:singleLine="true"
+            android:ellipsize="start"
+            android:text="@string/bookmarks"
+            android:textAppearance="?android:attr/textAppearanceMedium" />
+
+    </RelativeLayout>
+
+    <LinearLayout android:id="@+id/folder_selector"
+        android:layout_width="match_parent"
+        android:layout_height="@dimen/folder_selector_height"
+        android:orientation="vertical"
+        android:visibility="gone"
+        >
+
+        <ListView
+            android:id="@+id/list"
+            android:layout_marginLeft="16dip"
+            android:layout_marginRight="16dip"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            />
+        <TextView
+            android:id="@+id/empty"
+            android:layout_width="wrap_content"
+            android:layout_height="wrap_content"
+            android:visibility="gone"
+            android:layout_marginLeft="16dip"
+            android:layout_marginTop="16dip"
+            android:text="@string/no_subfolders"
+            android:textStyle="italic"
+            android:textAppearance="?android:attr/textAppearanceMedium" />
+        <EditText
+            android:id="@+id/folder_namer"
+            android:layout_marginLeft="16dip"
+            android:layout_marginRight="16dip"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:visibility="gone"
+            />
     </LinearLayout>
-        
+
     <LinearLayout 
         android:layout_width="match_parent"
         android:layout_height="wrap_content"
-        android:background="#c6c3c6"
         android:minHeight="54dip"
         android:orientation="horizontal"
         android:paddingTop="4dip"
@@ -103,4 +209,3 @@
     </LinearLayout>
 
 </LinearLayout>
-
diff --git a/res/layout/browser_find.xml b/res/layout/browser_find.xml
deleted file mode 100644
index e2f0cf6..0000000
--- a/res/layout/browser_find.xml
+++ /dev/null
@@ -1,76 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2007 The Android Open Source Project
-
-     Licensed under the Apache License, Version 2.0 (the "License");
-     you may not use this file except in compliance with the License.
-     You may obtain a copy of the License at
-  
-          http://www.apache.org/licenses/LICENSE-2.0
-  
-     Unless required by applicable law or agreed to in writing, software
-     distributed under the License is distributed on an "AS IS" BASIS,
-     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-     See the License for the specific language governing permissions and
-     limitations under the License.
--->
-
-<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
-    android:id="@+id/findControls"
-    android:layout_width="match_parent"
-    android:layout_height="wrap_content"
-    android:paddingTop="5dip"
-    android:paddingLeft="4dip"
-    android:paddingRight="4dip"
-    android:paddingBottom="1dip"
-    android:background="@android:drawable/bottom_bar">
-    <ImageButton 
-        android:src="@drawable/ic_btn_find_prev"
-        android:id="@+id/previous"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        />
-
-    <ImageButton 
-        android:src="@drawable/ic_btn_find_next"
-        android:id="@+id/next"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        />
-
-    <LinearLayout
-        android:layout_height="wrap_content"
-        android:layout_width="0dip"
-        android:layout_weight="1"
-        android:orientation="vertical"
-        android:layout_marginRight="6dip"
-        >
-        <EditText android:id="@+id/edit"
-            android:layout_width="match_parent"
-            android:layout_height="wrap_content"
-            android:scrollHorizontally="true"
-            android:inputType="text"
-            android:hint="@string/find_dot"
-            />
-        <LinearLayout android:id="@+id/matches_view"
-            android:layout_height="wrap_content"
-            android:layout_width="wrap_content"
-            android:orientation="horizontal"
-            android:layout_gravity="right"
-            android:visibility="invisible"
-            >
-            <TextView android:id="@+id/matches"
-                android:layout_width="wrap_content"
-                android:layout_height="wrap_content"
-                android:layout_gravity="right"
-                android:textAppearance="?android:attr/textAppearanceSmall"
-                android:textColor="?android:attr/textColorSecondaryInverse"
-                />
-        </LinearLayout>
-    </LinearLayout>
-    <ImageButton android:id="@+id/done"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        android:src="@drawable/ic_btn_close_panel"
-        />
-</LinearLayout>	
-
diff --git a/res/layout/browser_select.xml b/res/layout/browser_select.xml
deleted file mode 100644
index b30be8d..0000000
--- a/res/layout/browser_select.xml
+++ /dev/null
@@ -1,67 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2010 The Android Open Source Project
-
-     Licensed under the Apache License, Version 2.0 (the "License");
-     you may not use this file except in compliance with the License.
-     You may obtain a copy of the License at
-
-          http://www.apache.org/licenses/LICENSE-2.0
-
-     Unless required by applicable law or agreed to in writing, software
-     distributed under the License is distributed on an "AS IS" BASIS,
-     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-     See the License for the specific language governing permissions and
-     limitations under the License.
--->
-
-<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
-    android:id="@+id/selectControls"
-    android:layout_width="match_parent"
-    android:layout_height="wrap_content"
-    android:paddingTop="5dip"
-    android:paddingLeft="4dip"
-    android:paddingRight="4dip"
-    android:paddingBottom="1dip"
-    android:background="@android:drawable/bottom_bar">
-    <ImageButton
-        android:src="@drawable/ic_btn_copy"
-        android:id="@+id/copy"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        />
-
-    <ImageButton
-        android:src="@drawable/ic_btn_share"
-        android:id="@+id/share"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        />
-
-    <ImageButton
-        android:src="@drawable/ic_btn_select_all"
-        android:id="@+id/select_all"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        />
-
-    <ImageButton
-        android:src="@drawable/ic_btn_find"
-        android:id="@+id/find"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        />
-
-    <LinearLayout
-        android:layout_height="fill_parent"
-        android:layout_width="fill_parent"
-        android:layout_weight="1"
-        />
-
-    <ImageButton
-        android:src="@drawable/ic_btn_close_panel"
-        android:id="@+id/done"
-        android:layout_width="wrap_content"
-        android:layout_height="wrap_content"
-        />
-</LinearLayout>
-
diff --git a/res/layout/custom_screen.xml b/res/layout/custom_screen.xml
index 90dc324..525f30c 100644
--- a/res/layout/custom_screen.xml
+++ b/res/layout/custom_screen.xml
@@ -22,6 +22,7 @@
         android:layout_height="match_parent"
     />
     <LinearLayout android:orientation="vertical"
+        android:id="@+id/vertical_layout"
         android:layout_width="match_parent"
         android:layout_height="match_parent">
 
diff --git a/res/layout/empty_history.xml b/res/layout/empty_history.xml
deleted file mode 100644
index 4484a16..0000000
--- a/res/layout/empty_history.xml
+++ /dev/null
@@ -1,26 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2008 The Android Open Source Project
-
-     Licensed under the Apache License, Version 2.0 (the "License");
-     you may not use this file except in compliance with the License.
-     You may obtain a copy of the License at
-  
-          http://www.apache.org/licenses/LICENSE-2.0
-  
-     Unless required by applicable law or agreed to in writing, software
-     distributed under the License is distributed on an "AS IS" BASIS,
-     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-     See the License for the specific language governing permissions and
-     limitations under the License.
--->
-
-<TextView xmlns:android="http://schemas.android.com/apk/res/android"
-    android:id="@+id/empty_view"
-    android:layout_width="match_parent"
-    android:layout_height="match_parent"
-    android:text="@string/empty_history"
-    android:background="@color/black"
-    android:textColor="@color/white"
-    android:gravity="center"
-    android:textStyle="bold"
-    />
diff --git a/res/layout/folder_list_item.xml b/res/layout/folder_list_item.xml
new file mode 100644
index 0000000..56c597b
--- /dev/null
+++ b/res/layout/folder_list_item.xml
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+  
+          http://www.apache.org/licenses/LICENSE-2.0
+  
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<LinearLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="wrap_content"
+    android:orientation="horizontal">
+    <ImageView
+        android:id="@+id/icon1"
+        style="@style/HoloIcon"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:gravity="center_vertical"
+        android:minHeight="?android:attr/listPreferredItemHeight"
+        android:src="@drawable/ic_go_normal_white" />
+    <TextView
+        android:id="@android:id/text1"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:textAppearance="?android:attr/textAppearanceMedium"
+        android:gravity="center_vertical"
+        android:paddingLeft="6dip"
+        android:minHeight="?android:attr/listPreferredItemHeight" />
+</LinearLayout>
diff --git a/res/layout/history.xml b/res/layout/history.xml
new file mode 100644
index 0000000..f6e844a
--- /dev/null
+++ b/res/layout/history.xml
@@ -0,0 +1,38 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+  
+          http://www.apache.org/licenses/LICENSE-2.0
+  
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+>
+
+    <ExpandableListView android:id="@android:id/list"
+        android:layout_width="match_parent" 
+        android:layout_height="match_parent"
+        android:drawSelectorOnTop="false"
+    />
+
+    <TextView android:id="@android:id/empty"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_gravity="center"
+
+        android:textAppearance="?android:attr/textAppearanceLarge"
+        android:text="@string/empty_history"
+        android:visibility="gone"
+    />
+
+</FrameLayout>
\ No newline at end of file
diff --git a/res/layout/http_authentication.xml b/res/layout/http_authentication.xml
index cc785c9..cee3a42 100644
--- a/res/layout/http_authentication.xml
+++ b/res/layout/http_authentication.xml
@@ -18,14 +18,13 @@
     android:layout_width="match_parent"
     android:layout_height="wrap_content"
     android:gravity="center_horizontal"
-    android:orientation="vertical">
+    android:orientation="vertical"
+    >
 
     <TextView 
         android:id="@+id/username_view"
         android:layout_height="wrap_content"
         android:layout_width="wrap_content"
-        android:textSize="18sp"
-        android:textColor="@color/username_text"
         android:text="@string/username"
         android:gravity="left"
         android:layout_marginTop="12dip"
@@ -34,8 +33,6 @@
             
     <EditText
         android:id="@+id/username_edit"
-        android:textSize="18sp"
-        android:textColor="@color/username_edit"
         android:scrollHorizontally="true"
         android:inputType="text"
         android:gravity="fill_horizontal"
@@ -48,8 +45,6 @@
         android:id="@+id/password_view"
         android:layout_height="wrap_content"
         android:layout_width="wrap_content"
-        android:textSize="18sp"
-        android:textColor="@color/password_text"
         android:text="@string/password"
         android:gravity="left"
         android:layout_marginLeft="20dip"
@@ -57,8 +52,6 @@
             
     <EditText
         android:id="@+id/password_edit"
-        android:textSize="18sp"
-        android:textColor="@color/password_edit"
         android:scrollHorizontally="true"
         android:inputType="textPassword"
         android:gravity="fill_horizontal"
diff --git a/res/layout/import_bookmarks_dialog.xml b/res/layout/import_bookmarks_dialog.xml
new file mode 100644
index 0000000..f10f35d
--- /dev/null
+++ b/res/layout/import_bookmarks_dialog.xml
@@ -0,0 +1,47 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2008 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+  
+          http://www.apache.org/licenses/LICENSE-2.0
+  
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" 
+    android:layout_width="match_parent"
+    android:layout_height="match_parent"
+    android:orientation="vertical"
+    android:padding="8dip"
+>
+    <TextView
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:text="@string/import_bookmarks_dialog_description"
+    />
+
+    <LinearLayout android:id="@+id/accountList"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:orientation="vertical"
+    />
+    
+    <Button android:id="@+id/remove"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:text="@string/import_bookmarks_dialog_remove"
+        android:maxLines="2"
+    />
+
+    <Button android:id="@+id/cancel"
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:text="@android:string/cancel"
+    />
+</LinearLayout>
\ No newline at end of file
diff --git a/res/menu/bookmarks.xml b/res/layout/import_bookmarks_dialog_button.xml
similarity index 69%
rename from res/menu/bookmarks.xml
rename to res/layout/import_bookmarks_dialog_button.xml
index a8781c2..cf8f628 100644
--- a/res/menu/bookmarks.xml
+++ b/res/layout/import_bookmarks_dialog_button.xml
@@ -14,10 +14,9 @@
      limitations under the License.
 -->
 
-<menu xmlns:android="http://schemas.android.com/apk/res/android">
-    <item android:id="@+id/new_context_menu_id"
-        android:icon="@drawable/ic_menu_add_bookmark"
-        android:title="@string/bookmark_page" />
-    <item android:id="@+id/switch_mode_menu_id"
-        />
-</menu>
+<Button xmlns:android="http://schemas.android.com/apk/res/android" 
+    android:layout_width="match_parent"
+    android:layout_height="wrap_content"
+    android:text="@string/import_bookmarks_dialog_remove"
+    android:maxLines="2"
+/>
diff --git a/res/layout/page_info.xml b/res/layout/page_info.xml
index 275fcf4..7feb24e 100644
--- a/res/layout/page_info.xml
+++ b/res/layout/page_info.xml
@@ -31,8 +31,6 @@
             android:layout_height="wrap_content"
             android:layout_width="wrap_content"
             android:textStyle="bold"
-            android:textSize="14sp"
-            android:textColor="@color/white"
             android:layout_marginLeft="20dip"
             android:layout_marginRight="20dip"
             android:layout_marginTop="12dip"
@@ -49,8 +47,6 @@
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
                 android:text="@string/page_info_address"
-                android:textSize="14sp"
-                android:textColor="@color/white"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
@@ -60,8 +56,6 @@
                 android:id="@+id/address"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/white"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
diff --git a/res/layout/ssl_certificate.xml b/res/layout/ssl_certificate.xml
index a137d66..28f50a3 100644
--- a/res/layout/ssl_certificate.xml
+++ b/res/layout/ssl_certificate.xml
@@ -57,8 +57,6 @@
                 android:layout_width="wrap_content"
                 android:text="@string/issued_to"
                 android:textStyle="bold"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
                 android:layout_marginBottom="10dip" />
@@ -69,8 +67,6 @@
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
                 android:text="@string/common_name"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip" />
@@ -79,8 +75,6 @@
                 android:id="@+id/to_common"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_value"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
@@ -92,8 +86,6 @@
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
                 android:text="@string/org_name"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip" />
@@ -102,8 +94,6 @@
                 android:id="@+id/to_org"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_value"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
@@ -115,8 +105,6 @@
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
                 android:text="@string/org_unit"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip" />
@@ -125,8 +113,6 @@
                 android:id="@+id/to_org_unit"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_value"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
@@ -139,8 +125,6 @@
                 android:layout_width="wrap_content"
                 android:text="@string/issued_by"
                 android:textStyle="bold"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
                 android:layout_marginBottom="10dip" />
@@ -151,8 +135,6 @@
                 android:layout_width="wrap_content" 
                 android:layout_height="wrap_content"
                 android:text="@string/common_name"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip" />
@@ -161,8 +143,6 @@
                 android:id="@+id/by_common"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_value"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
@@ -174,8 +154,6 @@
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
                 android:text="@string/org_name"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip" />
@@ -184,8 +162,6 @@
                 android:id="@+id/by_org"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_value"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
@@ -197,8 +173,6 @@
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
                 android:text="@string/org_unit"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip" />
@@ -207,8 +181,6 @@
                 android:id="@+id/by_org_unit"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_value"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
@@ -221,8 +193,6 @@
                 android:layout_width="wrap_content"
                 android:text="@string/validity_period"
                 android:textStyle="bold"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
                 android:layout_marginBottom="10dip" />
@@ -233,8 +203,6 @@
                 android:layout_width="wrap_content" 
                 android:layout_height="wrap_content"
                 android:text="@string/issued_on"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip" />
@@ -243,8 +211,6 @@
                 android:id="@+id/issued_on"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_value"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
@@ -256,8 +222,6 @@
                 android:layout_width="wrap_content" 
                 android:layout_height="wrap_content"
                 android:text="@string/expires_on"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_label"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip" />
@@ -266,8 +230,6 @@
                 android:id="@+id/expires_on"
                 android:layout_height="wrap_content"
                 android:layout_width="wrap_content"
-                android:textSize="14sp"
-                android:textColor="@color/ssl_text_value"
                 android:gravity="left"
                 android:layout_marginLeft="20dip"
                 android:layout_marginRight="20dip"
diff --git a/res/layout/ssl_success.xml b/res/layout/ssl_success.xml
index e819f23..16f7f58 100644
--- a/res/layout/ssl_success.xml
+++ b/res/layout/ssl_success.xml
@@ -34,8 +34,7 @@
             android:layout_width="wrap_content"
             android:gravity="left"
             android:layout_weight="1"
-            android:textSize="18sp"
-            android:textColor="@color/ssl_text_label"
+            android:textAppearance="?android:attr/textAppearanceLarge"
             android:layout_marginLeft="10dip"
             android:layout_marginRight="20dip"
             android:layout_marginBottom="12dip" />
diff --git a/res/layout/ssl_warning.xml b/res/layout/ssl_warning.xml
index 285c189..749629d 100644
--- a/res/layout/ssl_warning.xml
+++ b/res/layout/ssl_warning.xml
@@ -31,8 +31,7 @@
             android:id="@+id/warning"
             android:gravity="left"
             android:layout_weight="1"
-            android:textSize="18sp"
-            android:textColor="@color/ssl_text_label"
+            android:textAppearance="?android:attr/textAppearanceLarge"
             android:layout_marginLeft="10dip"
             android:layout_marginRight="20dip"
             android:layout_marginBottom="12dip" />
diff --git a/res/layout/ssl_warnings.xml b/res/layout/ssl_warnings.xml
index 7e43256..3fe73d3 100644
--- a/res/layout/ssl_warnings.xml
+++ b/res/layout/ssl_warnings.xml
@@ -30,8 +30,7 @@
             android:id="@+id/warnings_header"
             android:layout_height="wrap_content"
             android:layout_width="match_parent"
-            android:textSize="18sp"
-            android:textColor="@color/ssl_text_label"
+            android:textAppearance="?android:attr/textAppearanceLarge"
             android:gravity="left"
             android:text="@string/ssl_warnings_header"
             android:layout_marginRight="20dip"
diff --git a/res/layout/suggestion_item.xml b/res/layout/suggestion_item.xml
new file mode 100644
index 0000000..45af644
--- /dev/null
+++ b/res/layout/suggestion_item.xml
@@ -0,0 +1,77 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/* //device/apps/common/assets/res/any/layout/simple_spinner_item.xml
+**
+** Copyright 2010, The Android Open Source Project
+**
+** Licensed under the Apache License, Version 2.0 (the "License");
+** you may not use this file except in compliance with the License.
+** You may obtain a copy of the License at
+**
+**     http://www.apache.org/licenses/LICENSE-2.0
+**
+** Unless required by applicable law or agreed to in writing, software
+** distributed under the License is distributed on an "AS IS" BASIS,
+** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+** See the License for the specific language governing permissions and
+** limitations under the License.
+*/
+-->
+
+<LinearLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="56dip"
+    android:orientation="horizontal"
+    android:gravity="center_vertical"
+    android:baselineAligned="false"
+    >
+    <ImageView
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:id="@+id/icon1"
+        android:scaleType="center"
+        style="@style/HoloButton" />
+    <RelativeLayout
+        android:paddingTop="8dip"
+        android:paddingBottom="8dip"
+        android:layout_width="0dip"
+        android:layout_weight="1"
+        android:layout_height="wrap_content" >
+        <TextView
+            android:id="@android:id/text1"
+            style="@style/SuggestionLineMedium"
+            android:singleLine="true"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content" />
+        <TextView
+            android:id="@android:id/text2"
+            style="@style/SuggestionLineSmall"
+            android:singleLine="true"
+            android:layout_width="match_parent"
+            android:layout_height="wrap_content"
+            android:layout_below="@android:id/text1"
+            android:layout_alignLeft="@android:id/text1" />
+    </RelativeLayout>
+    <ImageView
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:id="@+id/divider"
+        android:scaleType="center"
+        android:src="@drawable/divider_vert"
+        />
+    <ImageButton
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:id="@+id/icon2"
+        android:scaleType="center"
+        style="@style/HoloButton"
+        android:src="@drawable/ic_add_string"
+        android:background="@drawable/browserbarbutton"
+         />
+    <View
+        android:id="@+id/spacer"
+        android:layout_width="16dip"
+        android:layout_height="match_parent"
+        />
+</LinearLayout>
diff --git a/res/layout/suggestion_two_column.xml b/res/layout/suggestion_two_column.xml
new file mode 100644
index 0000000..fc74140
--- /dev/null
+++ b/res/layout/suggestion_two_column.xml
@@ -0,0 +1,44 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/* //device/apps/common/assets/res/any/layout/simple_spinner_item.xml
+**
+** Copyright 2010, The Android Open Source Project
+**
+** Licensed under the Apache License, Version 2.0 (the "License");
+** you may not use this file except in compliance with the License.
+** You may obtain a copy of the License at
+**
+**     http://www.apache.org/licenses/LICENSE-2.0
+**
+** Unless required by applicable law or agreed to in writing, software
+** distributed under the License is distributed on an "AS IS" BASIS,
+** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+** See the License for the specific language governing permissions and
+** limitations under the License.
+*/
+-->
+
+<LinearLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="match_parent"
+    android:layout_height="wrap_content"
+    android:orientation="horizontal"
+    android:gravity="center_vertical"
+    android:baselineAligned="false">
+    <include
+        android:id="@+id/suggest1"
+        layout="@layout/suggestion_item"
+        android:layout_width="0dip"
+        android:layout_weight="1"
+    />
+    <ImageView
+      android:layout_width="wrap_content"
+      android:layout_height="56dip"
+      android:background="@drawable/list_divider_vert" />
+    <include
+        android:id="@+id/suggest2"
+        layout="@layout/suggestion_item"
+        android:layout_width="0dip"
+        android:layout_weight="1"
+    />
+</LinearLayout>
diff --git a/res/layout/tab_bar.xml b/res/layout/tab_bar.xml
new file mode 100644
index 0000000..2726055
--- /dev/null
+++ b/res/layout/tab_bar.xml
@@ -0,0 +1,33 @@
+<?xml version="1.0" encoding="utf-8"?>
+    <!--
+        Copyright 2010, The Android Open Source Project Licensed under the
+        Apache License, Version 2.0 (the "License"); you may not use this file
+        except in compliance with the License. You may obtain a copy of the
+        License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+        applicable law or agreed to in writing, software distributed under the
+        License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+        CONDITIONS OF ANY KIND, either express or implied. See the License for
+        the specific language governing permissions and limitations under the
+        License.
+    -->
+<merge
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:id="@+id/tabbarcontent"
+    android:layout_width="match_parent"
+    android:layout_height="48dip"
+    android:orientation="horizontal"
+    style="@style/ActionBarStyle"
+    >
+    <com.android.browser.TabScrollView
+        android:id="@+id/tabs"
+        android:layout_width="wrap_content"
+        android:layout_height="match_parent"
+        android:orientation="horizontal" />
+    <ImageButton
+        android:id="@+id/newtab"
+        android:src="@drawable/ic_menu_new_window"
+        android:layout_width="wrap_content"
+        android:layout_height="match_parent"
+        style="@style/HoloButton"
+        android:background="@drawable/browserbarbutton" />
+</merge>
\ No newline at end of file
diff --git a/res/layout/tab_title.xml b/res/layout/tab_title.xml
new file mode 100644
index 0000000..a2da03d
--- /dev/null
+++ b/res/layout/tab_title.xml
@@ -0,0 +1,61 @@
+<?xml version="1.0" encoding="utf-8"?>
+    <!--
+        Copyright 2010, The Android Open Source Project Licensed under the
+        Apache License, Version 2.0 (the "License"); you may not use this file
+        except in compliance with the License. You may obtain a copy of the
+        License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+        applicable law or agreed to in writing, software distributed under the
+        License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+        CONDITIONS OF ANY KIND, either express or implied. See the License for
+        the specific language governing permissions and limitations under the
+        License.
+    -->
+<merge
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_width="wrap_content"
+    android:layout_height="match_parent"
+    android:gravity="center_vertical"
+    android:orientation="horizontal"
+    android:background="@drawable/tab_background">
+    <ImageView
+        android:id="@+id/incognito"
+        android:layout_width="16dip"
+        android:layout_height="16dip"
+        android:layout_marginLeft="3dip"
+        android:gravity="center_vertical"
+        android:src="@drawable/fav_incognito"
+        android:visibility="gone" />
+    <ImageView
+        android:id="@+id/favicon"
+        android:layout_width="20dip"
+        android:layout_height="20dip"
+        android:layout_marginLeft="16dip" />
+    <ImageView
+        android:id="@+id/lock"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_marginLeft="16dip"
+        android:visibility="gone" />
+    <TextView
+        android:id="@+id/title"
+        android:layout_height="match_parent"
+        android:layout_width="0dip"
+        android:layout_weight="1.0"
+        android:layout_marginLeft="16dip"
+        android:textAppearance="?android:attr/textAppearanceSmall"
+        android:textColor="@color/white"
+        android:gravity="center_vertical"
+        android:scrollHorizontally="true"
+        android:fadingEdge="horizontal"
+        android:fadingEdgeLength="24dip"
+        android:lines="1"
+        android:singleLine="true" />
+    <ImageButton
+        android:id="@+id/close"
+        android:background="@drawable/browserbarbutton"
+        android:layout_width="wrap_content"
+        android:layout_height="wrap_content"
+        android:layout_marginLeft="16dip"
+        android:layout_marginRight="16dip"
+        android:src="@drawable/ic_tab_close" />
+</merge>
diff --git a/res/layout/tab_view_add_incognito_tab.xml b/res/layout/tab_view_add_incognito_tab.xml
new file mode 100644
index 0000000..d07b4f5
--- /dev/null
+++ b/res/layout/tab_view_add_incognito_tab.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2009 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+    android:layout_height="wrap_content"
+    android:minHeight="?android:attr/listPreferredItemHeight"
+    android:layout_width="match_parent"
+    android:orientation="horizontal"
+    android:gravity="center_vertical"
+    >
+    <ImageView
+        android:layout_width="40dip"
+        android:layout_height="40dip"
+        android:layout_marginLeft="8dip"
+        android:layout_marginRight="8dip"
+        android:src="@drawable/ic_list_new_window"/>
+    <TextView
+        android:layout_width="match_parent"
+        android:layout_height="wrap_content"
+        android:textAppearance="?android:attr/textAppearanceMedium"
+        android:maxLines="1"
+        android:singleLine="true"
+        android:ellipsize="end"
+        android:text="@string/new_incognito_tab"
+        />
+</LinearLayout>
diff --git a/res/layout/tabs.xml b/res/layout/tabs.xml
deleted file mode 100644
index c212547..0000000
--- a/res/layout/tabs.xml
+++ /dev/null
@@ -1,37 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2009 The Android Open Source Project
-
-     Licensed under the Apache License, Version 2.0 (the "License");
-     you may not use this file except in compliance with the License.
-     You may obtain a copy of the License at
-  
-          http://www.apache.org/licenses/LICENSE-2.0
-  
-     Unless required by applicable law or agreed to in writing, software
-     distributed under the License is distributed on an "AS IS" BASIS,
-     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-     See the License for the specific language governing permissions and
-     limitations under the License.
--->
-<TabHost xmlns:android="http://schemas.android.com/apk/res/android"
-    android:id="@android:id/tabhost"
-    android:layout_width="match_parent"
-    android:layout_height="match_parent">
-
-    <LinearLayout
-        android:orientation="vertical"
-        android:layout_width="match_parent"
-        android:layout_height="match_parent">
-
-        <TabWidget android:id="@android:id/tabs"
-            android:layout_width="match_parent"
-            android:layout_height="wrap_content"
-        />
-
-        <FrameLayout android:id="@android:id/tabcontent"
-            android:layout_width="match_parent"
-            android:layout_height="0dip"
-            android:layout_weight="1"
-        />
-    </LinearLayout>
-</TabHost>
diff --git a/res/layout/title_bar.xml b/res/layout/title_bar.xml
index 9f0cb51..a7e50b7 100644
--- a/res/layout/title_bar.xml
+++ b/res/layout/title_bar.xml
@@ -65,8 +65,6 @@
                     android:layout_width="0dip"
                     android:layout_weight="1.0"
                     android:layout_marginLeft="3dip"
-                    android:textAppearance="?android:attr/textAppearanceMedium"
-                    android:textColor="@color/black"
                     android:gravity="center_vertical"
                     android:singleLine="true"
                     android:ellipsize="end"
@@ -90,7 +88,7 @@
             android:layout_marginRight="-5dip"
             android:scaleType="center"
             android:background="@drawable/btn_bookmark"
-            android:src="@drawable/ic_btn_bookmarks"
+            android:src="@drawable/ic_list_bookmark"
         />
     </LinearLayout>
 </LinearLayout>
diff --git a/res/layout/url_bar.xml b/res/layout/url_bar.xml
new file mode 100644
index 0000000..8b4a3c0
--- /dev/null
+++ b/res/layout/url_bar.xml
@@ -0,0 +1,161 @@
+<?xml version="1.0" encoding="utf-8"?>
+    <!--
+        Copyright 2010, The Android Open Source Project Licensed under the
+        Apache License, Version 2.0 (the "License"); you may not use this file
+        except in compliance with the License. You may obtain a copy of the
+        License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+        applicable law or agreed to in writing, software distributed under the
+        License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+        CONDITIONS OF ANY KIND, either express or implied. See the License for
+        the specific language governing permissions and limitations under the
+        License.
+    -->
+<LinearLayout
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:id="@+id/content"
+    android:layout_width="match_parent"
+    android:layout_height="wrap_content"
+    android:orientation="vertical">
+    <LinearLayout
+        android:id="@+id/taburlbar"
+        android:layout_width="match_parent"
+        android:layout_height="48dip"
+        android:orientation="horizontal"
+        android:background="@drawable/urlbar_bg">
+        <ImageButton
+            android:id="@+id/back"
+            android:src="@drawable/ic_back_normal"
+            android:layout_width="wrap_content"
+            android:layout_height="match_parent"
+            style="@style/HoloButton"
+            android:background="@drawable/browserbarbutton" />
+        <ImageButton
+            android:id="@+id/forward"
+            android:src="@drawable/ic_forward_normal"
+            android:layout_width="wrap_content"
+            android:layout_height="match_parent"
+            style="@style/HoloButton"
+            android:background="@drawable/browserbarbutton" />
+        <ImageView
+            android:id="@+id/stop"
+            android:background="@drawable/browserbarbutton"
+            android:layout_width="wrap_content"
+            android:layout_height="match_parent"
+            style="@style/HoloButton"
+            android:gravity="center_vertical"
+            android:src="@drawable/ic_stop_normal" />
+        <LinearLayout
+            android:id="@+id/urlbar_unfocused"
+            android:layout_width="0dip"
+            android:layout_height="match_parent"
+            android:layout_weight="1.0"
+            android:background="@null"
+            android:orientation="horizontal">
+            <ImageView
+                android:id="@+id/browsericon"
+                android:src="@drawable/ic_web_white"
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                style="@style/HoloButton" />
+            <ImageView
+                android:id="@+id/lock"
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                style="@style/HoloIcon"
+                android:visibility="gone" />
+            <EditText
+                android:id="@+id/url_unfocused"
+                android:layout_width="0dip"
+                android:layout_weight="1.0"
+                android:layout_height="match_parent"
+                android:background="@null"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:textColor="#ffc0c0c0"
+                android:hint="@string/search_hint"
+                android:gravity="center_vertical"
+                android:singleLine="true"
+                android:ellipsize="end"
+                android:lines="1"
+                android:scrollHorizontally="true"
+                android:inputType="textUri"
+                android:imeOptions="actionGo" />
+            <ImageButton
+                android:id="@+id/star"
+                android:src="@drawable/ic_favorite_off_normal"
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                style="@style/HoloButton"
+                android:background="@drawable/browserbarbutton" />
+        </LinearLayout>
+        <LinearLayout
+            android:id="@+id/urlbar_focused"
+            android:layout_width="0dip"
+            android:layout_height="match_parent"
+            android:layout_weight="1.0"
+            android:orientation="horizontal"
+            android:background="@drawable/text_field_results"
+            android:visibility="gone">
+            <ImageView
+                android:id="@+id/searchicon"
+                android:src="@drawable/ic_search_category_suggest"
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                style="@style/HoloButton" />
+            <com.android.browser.UrlInputView
+                android:id="@+id/url_focused"
+                android:layout_width="0dip"
+                android:layout_weight="1.0"
+                android:layout_height="match_parent"
+                android:background="@null"
+                android:textAppearance="?android:attr/textAppearanceMedium"
+                android:textColor="@color/black"
+                android:hint="@string/search_hint"
+                android:gravity="center_vertical"
+                android:singleLine="true"
+                android:ellipsize="end"
+                android:lines="1"
+                android:scrollHorizontally="true"
+                android:inputType="textUri"
+                android:imeOptions="actionGo" />
+            <ImageView
+                android:id="@+id/clear"
+                android:src="@drawable/ic_clear_search"
+                android:layout_width="wrap_content"
+                android:layout_height="match_parent"
+                style="@style/HoloButton" />
+        </LinearLayout>
+        <ImageButton
+            android:id="@+id/go"
+            android:src="@drawable/ic_go_normal_white"
+            android:layout_width="wrap_content"
+            android:layout_height="match_parent"
+            android:visibility="gone"
+            android:gravity="center_vertical"
+            style="@style/HoloButton"
+            android:background="@drawable/browserbarbutton" />
+        <ImageButton
+            android:id="@+id/search"
+            android:src="@drawable/ic_search_normal"
+            android:layout_width="wrap_content"
+            android:layout_height="match_parent"
+            android:gravity="center_vertical"
+            style="@style/HoloButton"
+            android:background="@drawable/browserbarbutton" />
+        <ImageButton
+            android:id="@+id/all_btn"
+            android:layout_width="wrap_content"
+            android:layout_height="match_parent"
+            android:scaleType="center"
+            style="@style/HoloButton"
+            android:background="@drawable/browserbarbutton"
+            android:src="@drawable/ic_bookmarks_history_normal" />
+    </LinearLayout>
+    <com.android.browser.PageProgressView
+        android:id="@+id/progress"
+        android:layout_width="match_parent"
+        android:layout_height="22dip"
+        android:background="@null"
+        android:src="@drawable/progress"
+        android:layout_marginTop="-11dip"
+        android:visibility="gone" />
+</LinearLayout>
diff --git a/res/menu-xlarge/browser.xml b/res/menu-xlarge/browser.xml
new file mode 100644
index 0000000..3b93835
--- /dev/null
+++ b/res/menu-xlarge/browser.xml
@@ -0,0 +1,98 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<menu xmlns:android="http://schemas.android.com/apk/res/android">
+    <group android:id="@+id/MAIN_MENU">
+        <item android:id="@+id/newtab"
+            android:icon="@drawable/ic_menu_new_window"
+            android:title="@string/new_tab"
+            android:showAsAction="never"
+            android:alphabeticShortcut="n" />
+        <item android:id="@+id/incognito_menu_id"
+            android:title="@string/new_incognito_tab"
+            android:icon="@drawable/ic_menu_incognito_normal" />
+        <item android:id="@+id/find_menu_id"
+            android:title="@*android:string/find_on_page"
+            android:icon="@drawable/ic_menu_findonpage_normal"
+            android:alphabeticShortcut="f" />
+        <item android:id="@+id/share_page_menu_id"
+            android:title="@string/share_page"
+            android:icon="@drawable/ic_menu_share_normal"
+            android:alphabeticShortcut="s" />
+        <item android:id="@+id/page_info_menu_id"
+            android:title="@string/page_info"
+            android:icon="@drawable/ic_menu_pageinfo_normal"
+            android:alphabeticShortcut="g" />
+        <item android:id="@+id/view_downloads_menu_id"
+            android:title="@string/menu_view_download"
+            android:icon="@drawable/ic_menu_downloads_normal"
+            android:alphabeticShortcut="d" />
+        <item android:id="@+id/preferences_menu_id"
+            android:title="@string/menu_preferences"
+            android:icon="@drawable/ic_menu_settings_normal"
+            android:alphabeticShortcut="p" />
+        <item android:id="@+id/save_webarchive_menu_id"
+            android:icon="@drawable/ic_menu_archive_normal"
+            android:title="@string/menu_save_webarchive" />
+        <!-- followings are debug only -->
+        <item android:id="@+id/dump_nav_menu_id"
+            android:title="@string/dump_nav"
+            android:visible="false" />
+        <item android:id="@+id/dump_counters_menu_id"
+            android:title="@string/dump_counters"
+            android:visible="false" />
+    </group>
+    <group android:id="@+id/MAIN_SHORTCUT_MENU" android:visible="false">
+        <item android:id="@+id/homepage_menu_id"
+            android:alphabeticShortcut="&#32;" />
+        <item android:id="@+id/classic_history_menu_id"
+            android:alphabeticShortcut="h" />
+        <item android:id="@+id/zoom_in_menu_id"
+            android:alphabeticShortcut="i" />
+        <item android:id="@+id/zoom_out_menu_id"
+            android:alphabeticShortcut="o" />
+        <item android:id="@+id/window_one_menu_id"
+            android:alphabeticShortcut="1" />
+        <item android:id="@+id/window_two_menu_id"
+            android:alphabeticShortcut="2" />
+        <item android:id="@+id/window_three_menu_id"
+            android:alphabeticShortcut="3" />
+        <item android:id="@+id/window_four_menu_id"
+            android:alphabeticShortcut="4" />
+        <item android:id="@+id/window_five_menu_id"
+            android:alphabeticShortcut="5" />
+        <item android:id="@+id/window_six_menu_id"
+            android:alphabeticShortcut="6" />
+        <item android:id="@+id/window_seven_menu_id"
+            android:alphabeticShortcut="7" />
+        <item android:id="@+id/window_eight_menu_id"
+            android:alphabeticShortcut="8" />
+        <item android:id="@+id/back_menu_id"
+            android:alphabeticShortcut="j" />
+        <item android:id="@+id/forward_menu_id"
+            android:alphabeticShortcut="k" />
+        <item android:id="@+id/bookmarks_menu_id"
+            android:alphabeticShortcut="b" />
+        <item android:id="@+id/add_bookmark_menu_id"
+            android:alphabeticShortcut="a" />
+        <item android:id="@+id/stop_reload_menu_id"
+            android:alphabeticShortcut="r" />
+        <item android:id="@+id/goto_menu_id"
+            android:alphabeticShortcut="l" />
+        <item android:id="@+id/close_menu_id"
+            android:alphabeticShortcut="w" />
+    </group>
+</menu>
diff --git a/res/menu/bookmarkscontext.xml b/res/menu/bookmarkscontext.xml
index badbb00..c58d459 100644
--- a/res/menu/bookmarkscontext.xml
+++ b/res/menu/bookmarkscontext.xml
@@ -15,10 +15,6 @@
 -->
 
 <menu xmlns:android="http://schemas.android.com/apk/res/android">
-  <group android:id="@+id/ADD_MENU">
-    <item android:id="@+id/new_context_menu_id"
-      android:title="@string/save_to_bookmarks"/>
-  </group>
   <group android:id="@+id/CONTEXT_MENU">
     <item android:id="@+id/open_context_menu_id"
       android:title="@string/open_bookmark"/>
diff --git a/res/menu/browser.xml b/res/menu/browser.xml
index 4793c21..b5d56c8 100644
--- a/res/menu/browser.xml
+++ b/res/menu/browser.xml
@@ -40,23 +40,28 @@
             android:icon="@drawable/ic_menu_add_bookmark"
             android:alphabeticShortcut="a" />
         <item android:id="@+id/find_menu_id"
-            android:title="@string/find_dot"
+            android:title="@*android:string/find_on_page"
+            android:icon="@*android:drawable/ic_menu_find"
             android:alphabeticShortcut="f" />
-        <item android:id="@+id/select_text_id"
-            android:title="@string/select_dot"
-            android:alphabeticShortcut="e" />
-        <item android:id="@+id/page_info_menu_id"
-            android:title="@string/page_info"
-            android:alphabeticShortcut="g" />
         <item android:id="@+id/share_page_menu_id"
             android:title="@string/share_page"
+            android:icon="@drawable/ic_menu_share"
             android:alphabeticShortcut="s" />
+        <item android:id="@+id/page_info_menu_id"
+            android:title="@string/page_info"
+            android:icon="@drawable/ic_menu_pageinfo"
+            android:alphabeticShortcut="g" />
         <item android:id="@+id/view_downloads_menu_id"
             android:title="@string/menu_view_download"
+            android:icon="@drawable/ic_menu_downloads"
             android:alphabeticShortcut="d" />
         <item android:id="@+id/preferences_menu_id"
             android:title="@string/menu_preferences"
+            android:icon="@drawable/ic_menu_settings"
             android:alphabeticShortcut="p" />
+        <item android:id="@+id/save_webarchive_menu_id"
+            android:title="@string/menu_save_webarchive"
+             />
         <!-- followings are debug only -->
         <item android:id="@+id/dump_nav_menu_id"
             android:title="@string/dump_nav"
@@ -91,16 +96,10 @@
         <item android:id="@+id/window_eight_menu_id"
             android:alphabeticShortcut="8" />
         <item android:id="@+id/back_menu_id"
-            android:title="@string/back"
-            android:drawable="@*android:drawable/ic_menu_back"
             android:alphabeticShortcut="j" />
         <item android:id="@+id/goto_menu_id"
-            android:title="@string/goto_dot"
-            android:alphabeticShortcut="l"
-            android:icon="@android:drawable/ic_menu_search"/>
+            android:alphabeticShortcut="l" />
         <item android:id="@+id/close_menu_id"
-            android:icon="@drawable/ic_btn_close_panel"
-            android:title="@string/tab_picker_remove_tab"
             android:alphabeticShortcut="w" />
     </group>
     <!-- these items are toggled in and out of @+id/stop_reload_menu_id -->
diff --git a/res/menu/bookmarks.xml b/res/menu/folder_choice.xml
similarity index 65%
copy from res/menu/bookmarks.xml
copy to res/menu/folder_choice.xml
index a8781c2..068b170 100644
--- a/res/menu/bookmarks.xml
+++ b/res/menu/folder_choice.xml
@@ -1,12 +1,12 @@
 <?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2008 The Android Open Source Project
+<!-- Copyright (C) 2010 The Android Open Source Project
 
      Licensed under the Apache License, Version 2.0 (the "License");
      you may not use this file except in compliance with the License.
      You may obtain a copy of the License at
-  
+
           http://www.apache.org/licenses/LICENSE-2.0
-  
+
      Unless required by applicable law or agreed to in writing, software
      distributed under the License is distributed on an "AS IS" BASIS,
      WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@@ -15,9 +15,10 @@
 -->
 
 <menu xmlns:android="http://schemas.android.com/apk/res/android">
-    <item android:id="@+id/new_context_menu_id"
-        android:icon="@drawable/ic_menu_add_bookmark"
-        android:title="@string/bookmark_page" />
-    <item android:id="@+id/switch_mode_menu_id"
-        />
+    <item android:id="@+id/home_screen"
+        android:title="@string/add_to_homescreen_menu_option"/>
+    <item android:id="@+id/bookmarks"
+        android:title="@string/add_to_bookmarks_menu_option"/>
+    <item android:id="@+id/other"
+        android:title="@string/add_to_other_folder_menu_option"/>
 </menu>
diff --git a/res/values-cs-xlarge/strings.xml b/res/values-cs-xlarge/strings.xml
new file mode 100644
index 0000000..092d6c7
--- /dev/null
+++ b/res/values-cs-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Nová karta"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Nová anonymní karta"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Karty"</string>
+</resources>
diff --git a/res/values-cs/strings.xml b/res/values-cs/strings.xml
index c2b1fa2..78cd2d6 100644
--- a/res/values-cs/strings.xml
+++ b/res/values-cs/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Prohlížeč"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Zvolit soubor, který chcete nahrát."</string>
     <string name="new_tab" msgid="4505722538297295141">"Nové okno"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nové anonymní okno"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Okna"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Záložky"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Nejnavštěvovanější"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Prohlížeč"</string>
     <string name="cancel" msgid="3017274947407233702">"Zrušit"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Žádné shody"</item>
-    <item quantity="one" msgid="4352019729062956802">"Shoda"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> shod"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> shod"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Načítání..."</string>
     <string name="page_info" msgid="4048529256302257195">"Informace o stránce"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Zobrazit informace o stránce"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Předat dál"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Zrušit"</string>
-    <string name="location" msgid="969988560160364559">"Místo"</string>
-    <string name="name" msgid="5990326151488445481">"Jméno"</string>
+    <string name="location" msgid="3411848697912600125">"Adresa"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Přidat do složky"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Nová složka"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Štítek"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Přidat záložku"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Přidat k záložkám"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Přidat stránku do záložek"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Upravit záložku"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Přidat odkaz na plochu"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Přidat na plochu"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Otevřít"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Smazat záložku"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Zrušit přístup k poloze"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Záložka <xliff:g id="BOOKMARK">%s</xliff:g> bude smazána."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Otevřít v novém okně"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Přejít"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Vyhledat na stránce"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Otevřít novou anonymní kartu"</string>
     <string name="select_dot" msgid="6299170761900561967">"Vybrat text"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Aktuální okna"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Zavřít"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Stažené"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Kopírovat adresu URL stránky"</string>
     <string name="share_page" msgid="593756995297268343">"Sdílet stránku"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Uložit jako webový archiv"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Webový archiv byl uložen."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Uložení webového archivu se nezdařilo."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Otevřít"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Otevřít v novém okně"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Přidat odkaz do záložek"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Přizpůsobit velikost webových stránek obrazovce"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Zobrazení pouze na šířku"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Zobrazit stránky pouze s displejem otočeným na šířku"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Osobní nastavení"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchronizovat s prohlížečem Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Sdílet záložky a jiná data mezi Prohlížečem systému Android a aplikací Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Účet Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synchronizovat záložky"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synchronizovat záložky mezi Prohlížečem systému Android a aplikací Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchronizovat"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Vyberte účet Google pro sdílení"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Nastavení ochrany osobních údajů"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Vymazat mezipaměť"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Vymazat všechen obsah a databáze uložené do místní mezipaměti"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japonština (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japonština (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japonština (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Korejština (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Kódování textu"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problémy s datovým připojením"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Vymazat všechna data"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Zrušit"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Nastavení tapety..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Záložky"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Žádné záložky k zobrazení"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchronizovat s účtem Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Vaše záložky v systému Android nejsou přidruženy k účtu Google."</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Odebrat záložky systému Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Přidat všechny záložky systému Android do záložek účtu <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-da-xlarge/strings.xml b/res/values-da-xlarge/strings.xml
new file mode 100644
index 0000000..6505d89
--- /dev/null
+++ b/res/values-da-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Ny fane"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Ny inkognitofane"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Faner"</string>
+</resources>
diff --git a/res/values-da/strings.xml b/res/values-da/strings.xml
index 7b6e542..dfbbad5 100644
--- a/res/values-da/strings.xml
+++ b/res/values-da/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Browser"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Vælg fil til upload"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nyt vindue"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nyt inkognitovindue"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Vinduer"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Bogmærker"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Mest besøgte"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
     <string name="cancel" msgid="3017274947407233702">"Annuller"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Der er ingen matches"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 match"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> matches"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> matches"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Indlæser ..."</string>
     <string name="page_info" msgid="4048529256302257195">"Sideoplysninger"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Vis sideoplysninger"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Fremad"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Annuller"</string>
-    <string name="location" msgid="969988560160364559">"Placering"</string>
-    <string name="name" msgid="5990326151488445481">"Navn"</string>
+    <string name="location" msgid="3411848697912600125">"Adresse"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Føj til"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Ny mappe"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Etiket"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Tilføj bogmærke"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Føj til bogmærker"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Tilføj side som bogmærke"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Rediger bogmærke"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Føj genvej til Start"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Føj til Startskærm"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Åbn"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Slet bogmærke"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Fjern fra bogmærker"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Bogmærket \"<xliff:g id="BOOKMARK">%s</xliff:g>\" slettes."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Åbn i et nyt vindue"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Gå"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Find på side"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Åbn ny inkognitofane"</string>
     <string name="select_dot" msgid="6299170761900561967">"Vælg tekst"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Aktuelle vinduer"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Luk"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Kopier sidens webadresse"</string>
     <string name="share_page" msgid="593756995297268343">"Del side"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Gem som webarkiv"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Webarkivet blev gemt."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Webarkivet blev ikke gemt."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Åbn"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Åbn i et nyt vindue"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Opret et bogmærke for linket"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Tilpas websider, så de passer til skærmen"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Kun liggende visning"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Vis kun sider i den brede liggende retning"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Personlige indstillinger"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synkroniser med Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Del bogmærker og andre data mellem Android-browser og Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google-konto"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synkroniser bogmærker"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synkroniser bogmærker mellem Android-browser og Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Start synkronisering"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Vælg Google-konto at dele med"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Indstillinger for fortrolighed"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Ryd cache"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Ryd lokalt cachelagret indhold og databaser"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japansk (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japansk (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japansk (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Koreansk (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Tekstkodning"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Dataforbindelsesproblem"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Slet alle data"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Annuller"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Indstiller tapet ..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bogmærker"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Der er ingen bogmærker"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synkroniser med Google-konto"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Dine Android-bogmærker er ikke tilknyttet en Google-konto"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Fjern dine Android-bogmærker"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Føj dine Android-bogmærker til bogmærker for <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-de-xlarge/strings.xml b/res/values-de-xlarge/strings.xml
new file mode 100644
index 0000000..b263de1
--- /dev/null
+++ b/res/values-de-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Neuer Tab"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Neuer Inkognito-Tab"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Tabs"</string>
+</resources>
diff --git a/res/values-de/strings.xml b/res/values-de/strings.xml
index 51d1f4c..e21f1dd 100644
--- a/res/values-de/strings.xml
+++ b/res/values-de/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Browser"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Datei zum Hochladen auswählen"</string>
     <string name="new_tab" msgid="4505722538297295141">"Neues Fenster"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Neues Inkognito-Fenster"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Fenster"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Lesezeichen"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Meistbesucht"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
     <string name="cancel" msgid="3017274947407233702">"Abbrechen"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Keine Treffer"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 Treffer"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> Treffer"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> Treffer"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Wird geladen..."</string>
     <string name="page_info" msgid="4048529256302257195">"Seiteninfo"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Seiteninfo anzeigen"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Vorwärts"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Abbrechen"</string>
-    <string name="location" msgid="969988560160364559">"URL"</string>
-    <string name="name" msgid="5990326151488445481">"Name"</string>
+    <string name="location" msgid="3411848697912600125">"Adresse"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Hinzufügen zu"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Neuer Ordner"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Label"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Lesezeichen hinzufügen"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Zu Lesezeichen hinzufügen"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Diese Seite als Lesezeichen speichern"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Lesezeichen bearbeiten"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Verknüpfung auf dem Startbildschirm erstellen"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Zur Startseite hinzufügen"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Öffnen"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Lesezeichen löschen"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Aus Lesezeichen entfernen"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Lesezeichen \"<xliff:g id="BOOKMARK">%s</xliff:g>\" wird gelöscht."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"In neuem Fenster öffnen"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Los"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Auf Seite suchen"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Neuen Inkognito-Tab öffnen"</string>
     <string name="select_dot" msgid="6299170761900561967">"Text auswählen"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Aktuelle Fenster"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Schließen"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Seiten-URL kopieren"</string>
     <string name="share_page" msgid="593756995297268343">"Seitenlink weiterleiten"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Als Webarchiv speichern"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Webarchiv gespeichert."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Das Webarchiv wurde nicht gespeichert."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Öffnen"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"In neuem Fenster öffnen"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Link zu Lesezeichen hinzufügen"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Webseiten an den Bildschirm anpassen"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Anzeige nur im Querformat"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Seiten nur im Querformat anzeigen"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Persönliche Einstellungen"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Mit Google Chrome synchronisieren"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Lesezeichen und andere Daten zwischen Android-Browser und Google Chrome austauschen"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google-Konto"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Lesezeichen synchronisieren"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Lesezeichen zwischen Android-Browser und Google Chrome synchronisieren"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchronis. starten"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Google-Konto wählen"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Datenschutzeinstellungen"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Cache löschen"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Content und Datenbanken aus dem lokalen Cache löschen"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japanisch (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japanisch (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japanisch (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Koreanisch (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Textcodierung"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Datenverbindungsproblem"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Alle Daten löschen"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Abbrechen"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Hintergrund wird eingestellt..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Lesezeichen"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Es sind keine Lesezeichen vorhanden."</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Mit Google-Konto synchronisieren"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Ihre Android-Lesezeichen sind mit keinem Google-Konto verknüpft."</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Android-Lesezeichen entfernen"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Ihre Android-Lesezeichen den Lesezeichen für <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> hinzufügen"</string>
 </resources>
diff --git a/res/values-el-xlarge/strings.xml b/res/values-el-xlarge/strings.xml
new file mode 100644
index 0000000..b13b54e
--- /dev/null
+++ b/res/values-el-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Νέα καρτέλα"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Νέα καρτέλα ανών. περιήγησης"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Καρτέλες"</string>
+</resources>
diff --git a/res/values-el/strings.xml b/res/values-el/strings.xml
index 90d116e..8da0309 100644
--- a/res/values-el/strings.xml
+++ b/res/values-el/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Internet"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Επιλογή αρχείου για μεταφόρτωση"</string>
     <string name="new_tab" msgid="4505722538297295141">"Νέο παράθυρο"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Νέο παράθυρο για ανώνυμη περιήγηση"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Παράθυρα"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Σελιδοδείκτες"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Οι πιο δημοφιλείς"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Internet"</string>
     <string name="cancel" msgid="3017274947407233702">"Ακύρωση"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Δεν υπάρχουν αποτελέσματα"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 αποτέλεσμα"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> αποτελέσματα"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> αποτελέσματα"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Φόρτωση..."</string>
     <string name="page_info" msgid="4048529256302257195">"Πληροφορίες σελίδας"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Προβολή πληροφοριών σελίδας"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Εμπρός"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Ακύρωση"</string>
-    <string name="location" msgid="969988560160364559">"Τοποθεσία"</string>
-    <string name="name" msgid="5990326151488445481">"Όνομα"</string>
+    <string name="location" msgid="3411848697912600125">"Διεύθυνση"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Προσθήκη σε"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Νέος φάκελος"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Ετικέτα"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Προσθήκη σελιδοδείκτη"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Προσθήκη στους σελιδοδείκτες"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Προσθήκη στους σελιδοδείκτες"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Επεξεργασία σελιδοδείκτη"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Προσθήκη συντόμευσης στην αρχική οθόνη"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Προσθήκη στην αρχική οθόνη"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Άνοιγμα"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Διαγραφή σελιδοδείκτη"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Κατάργηση από τους σελιδοδείκτες"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Ο σελιδοδείκτης \"<xliff:g id="BOOKMARK">%s</xliff:g>\" θα διαγραφεί."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Άνοιγμα σε νέο παράθυρο"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Μετάβαση"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Εύρεση στη σελίδα"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Άνοιγμα νέας καρτέλας ανώνυμης περιήγησης"</string>
     <string name="select_dot" msgid="6299170761900561967">"Επιλογή κειμένου"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Τρέχοντα παράθυρα"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Κλείσιμο"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Λήψεις"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Αντιγραφή διεύθυνσης url της σελίδας"</string>
     <string name="share_page" msgid="593756995297268343">"Κοινή χρήση σελίδας"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Αποθήκευση ως αρχείου ιστού"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Το αρχείο ιστού αποθηκεύθηκε."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Η αποθήκευση του αρχείου ιστού απέτυχε."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Άνοιγμα"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Άνοιγμα σε νέο παράθυρο"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Πρόσθεση συνδέσμου στους σελιδοδείκτες"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Μορφοποίηση ιστοσελίδων για την προσαρμογή τους στο μέγεθος της οθόνης"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Προβολή μόνο σε τοπίο"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Προβολή σελίδων μόνο στον ευρύτερο προσανατολισμό τοπίου στην οθόνη"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Προσωπικές ρυθμίσεις"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Συγχρονισμός με Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Κάντε κοινή χρήση σελιδοδεικτών και άλλων δεδομένων μεταξύ του Προγράμματος περιήγησης του Android και του Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Λογαριασμός Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Συγχρονισμός σελιδοδεικτών"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Συγχρονισμός σελιδοδεικτών μεταξύ του Προγράμματος περιήγησης του Android και του Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Έναρξη συγχρονισμού"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Επιλογή λογαριασμού"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Ρυθμίσεις απορρήτου"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Εκκαθάριση προσωρινής μνήμης"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Εκκαθάριση τοπικά αποθηκευμένου στη μνήμη cache περιεχομένου και βάσεων δεδομένων"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Ιαπωνικά (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Ιαπωνικά (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Ιαπωνικά (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Κορεατικά (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Κωδικοποίηση κειμένου"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Πρόβλημα σύνδεσης δεδομένων"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Διαγραφή όλων των δεδομένων"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Ακύρωση"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Ρύθμιση ταπετσαρίας..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Σελιδοδείκτες"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Δεν υπάρχουν σελιδοδείκτες"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Συγχρον. με Λογαριασμό Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Οι σελιδοδείκτες σας Android δεν σχετίζονται με κάποιον Λογαριασμό Google"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Καταργήστε τους σελιδοδείκτες σας Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Προσθ. τους σελιδοδείκτες Android στους σελιδοδείκτες του <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-es-rUS-xlarge/strings.xml b/res/values-es-rUS-xlarge/strings.xml
new file mode 100644
index 0000000..f52826a
--- /dev/null
+++ b/res/values-es-rUS-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Pestaña nueva"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Nueva pestaña de incógnito"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Pestañas"</string>
+</resources>
diff --git a/res/values-es-rUS/strings.xml b/res/values-es-rUS/strings.xml
index 563e9ee..6615ed4 100644
--- a/res/values-es-rUS/strings.xml
+++ b/res/values-es-rUS/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Navegador"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Elegir el archivo para cargar"</string>
     <string name="new_tab" msgid="4505722538297295141">"Ventana nueva"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nueva ventana de incógnito"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Marcadores"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Más visitados"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Navegador"</string>
     <string name="cancel" msgid="3017274947407233702">"Cancelar"</string>
     <string name="ok" msgid="1509280796718850364">"Aceptar"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Sin coincidencias"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 coincidencia"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> coincide"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> coincide"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Cargando…"</string>
     <string name="page_info" msgid="4048529256302257195">"Información de la página"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Ver información de la página"</string>
@@ -67,12 +62,19 @@
     <string name="forward" msgid="4288210890526641577">"Reenviar"</string>
     <string name="save" msgid="5922311934992468496">"Aceptar"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Cancelar"</string>
-    <string name="location" msgid="969988560160364559">"Ubicación"</string>
-    <string name="name" msgid="5990326151488445481">"Nombre"</string>
+    <string name="location" msgid="3411848697912600125">"Dirección"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Agregar a"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Carpeta nueva"</string>
+    <string name="no_subfolders" msgid="5880411440592452802">"No hay subcarpetas"</string>
+    <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Marcadores"</string>
+    <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Pantalla principal"</string>
+    <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Otra carpeta…"</string>
+    <string name="name" msgid="5462672162695365387">"Etiqueta"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Agregar marcador"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Agregar a Favoritos"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Agregar esta página a Favoritos"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Editar marcador"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Agregar acceso directo a la página de inicio"</string>
+    <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Agregar acceso directo a la página de inicio"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Abrir"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Eliminar marcador"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Eliminar de marcadores"</string>
@@ -93,7 +95,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"El marcador \"<xliff:g id="BOOKMARK">%s</xliff:g>\" se eliminará."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Abrir en una ventana nueva"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Ir"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Buscar en la página"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Abrir nueva pestaña de incógnito"</string>
     <string name="select_dot" msgid="6299170761900561967">"Seleccionar texto"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Ventana actual"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Cerrar"</string>
@@ -103,6 +105,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Descargas"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Copiar la url de la página"</string>
     <string name="share_page" msgid="593756995297268343">"Compartir página"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Guardar como Archivo web"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Archivo web guardado."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Error al guardar el archivo web."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Abrir"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Abrir en una ventana nueva"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Enlace del marcador"</string>
@@ -143,6 +148,33 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatea las páginas web para que se ajusten a la pantalla"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Visualización horizontal solamente"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Mostrar páginas sólo en la orientación de pantalla horizontal más ancha"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Configuración personal"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronización con Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Compartir favoritos &amp; otros datos entre el navegador Android y Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Cuenta de Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizar favoritos"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizar favoritos entre el navegador Android y Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Iniciar la sincr."</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Selec cta Google p/comp"</string>
+    <string name="pref_autofill_enabled" msgid="1174197447388234595">"Formulario de autollenado"</string>
+    <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Completa formularios web con un sólo clic"</string>
+    <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Configuración de autollenado"</string>
+    <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Configurar y administrar datos para los formularios de autollenado"</string>
+    <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nombre completo:"</string>
+    <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Correo electrónico:"</string>
+    <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nombre de la empresa:"</string>
+    <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Dirección línea 1:"</string>
+    <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Dirección postal, código postal, A/A"</string>
+    <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Dirección línea 2:"</string>
+    <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartamento, suite, unidad, edificio, suelo, etc."</string>
+    <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Ciudad/Pueblo:"</string>
+    <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Estado / Provincia / Región:"</string>
+    <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Código postal:"</string>
+    <string name="autofill_profile_editor_country" msgid="7234470301239156656">"País:"</string>
+    <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Teléfono:"</string>
+    <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Guardar perfil"</string>
+    <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Perfil guardado"</string>
+    <string name="autofill_profile_editor_delete_profile" msgid="7112035941146003753">"Eliminar datos de perfil"</string>
     <string name="pref_privacy_title" msgid="1052470980370846151">"Configuración de privacidad"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Borrar memoria caché"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Borrar el contenido y las bases de datos de la memoria caché local"</string>
@@ -208,6 +240,7 @@
     <item msgid="891615911084608570">"Japonés (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japonés (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japonés (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificación de texto"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de conectividad de datos"</string>
@@ -296,4 +329,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Eliminar todos los datos"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancelar"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Estableciendo fondo de pantalla..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Marcadores"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"No hay ningún marcador"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronización con cta de Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Tus favoritos de Android no están asociados con una cuenta de Google."</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Eliminar tus favoritos de Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Agrega tus favoritos de Android a tus favoritos para <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>."</string>
 </resources>
diff --git a/res/values-es-xlarge/strings.xml b/res/values-es-xlarge/strings.xml
new file mode 100644
index 0000000..1a05099
--- /dev/null
+++ b/res/values-es-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Nueva pestaña"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Nueva pestaña de incógnito"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Pestañas"</string>
+</resources>
diff --git a/res/values-es/strings.xml b/res/values-es/strings.xml
index 7f7d856..6984428 100644
--- a/res/values-es/strings.xml
+++ b/res/values-es/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Navegador"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Seleccionar archivo para subir"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nueva ventana"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nueva ventana de incógnito"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Ventanas"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Marcadores"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Más visitados"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Navegador"</string>
     <string name="cancel" msgid="3017274947407233702">"Cancelar"</string>
     <string name="ok" msgid="1509280796718850364">"Aceptar"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"No hay coincidencias"</item>
-    <item quantity="one" msgid="4352019729062956802">"Una coincidencia"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> coincidencias"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> coincidencias"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Cargando..."</string>
     <string name="page_info" msgid="4048529256302257195">"Información de página"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Ver información de página"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Siguiente"</string>
     <string name="save" msgid="5922311934992468496">"Aceptar"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Cancelar"</string>
-    <string name="location" msgid="969988560160364559">"Ubicación"</string>
-    <string name="name" msgid="5990326151488445481">"Nombre"</string>
+    <string name="location" msgid="3411848697912600125">"Dirección"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Añadir a"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Nueva carpeta"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Etiqueta"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Añadir marcador"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Añadir a marcadores"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Añadir esta página a marcadores"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Editar marcador"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Añadir acceso directo al escritorio"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Añadir al escritorio"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Abrir"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Eliminar marcador"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Eliminar de marcadores"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Se eliminará el marcador \"<xliff:g id="BOOKMARK">%s</xliff:g>\"."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Abrir en ventana nueva"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Ir"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Buscar en la página"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Abrir nueva pestaña de incógnito"</string>
     <string name="select_dot" msgid="6299170761900561967">"Seleccionar texto"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Ventanas actuales"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Cerrar"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Descargas"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Copiar URL de página"</string>
     <string name="share_page" msgid="593756995297268343">"Compartir página"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Guardar como archivo web"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Archivo web guardado"</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Error al guardar archivo web"</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Abrir"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Abrir en ventana nueva"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Marcar enlace"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Configurar las páginas web para ajustarlas a la pantalla"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Vista solo horizontal"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Mostrar solo las páginas con la orientación de pantalla horizontal"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Configuración personal"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizar con Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Compartir marcadores y otros datos entre el navegador de Android y Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Cuenta de Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizar marcadores"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizar marcadores entre el navegador de Android y Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Iniciar sincronización"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Elegir cuenta para compartir"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Ajustes de privacidad"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Borrar caché"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Borrar bases de datos y contenido de la memoria caché local"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japonés (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japonés (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japonés (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificación de texto"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de conectividad de datos"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Eliminar todos los datos"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancelar"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Estableciendo fondo de pantalla..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Marcadores"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"No hay ningún marcador."</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizar con cuenta de Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Tus marcadores de Android no se han asociado a una cuenta de Google."</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Eliminar los marcadores de Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Añadir tus marcadores de Android a marcadores de <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-fr-xlarge/strings.xml b/res/values-fr-xlarge/strings.xml
new file mode 100644
index 0000000..8af3e52
--- /dev/null
+++ b/res/values-fr-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Nouvel onglet"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Nouvel onglet Navigation privée"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Onglets"</string>
+</resources>
diff --git a/res/values-fr/strings.xml b/res/values-fr/strings.xml
index 094dc29..98ba3df 100644
--- a/res/values-fr/strings.xml
+++ b/res/values-fr/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Navigateur"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Choisir le fichier à importer"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nouvelle fenêtre"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Fenêtre de navigation privée"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Fenêtres"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Favoris"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Les + visités"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Navigateur"</string>
     <string name="cancel" msgid="3017274947407233702">"Annuler"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Aucune correspondance"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 correspondance"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> correspondances"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> correspondances"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Chargement…"</string>
     <string name="page_info" msgid="4048529256302257195">"Infos sur la page"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Afficher les infos sur la page"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Suivant"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Annuler"</string>
-    <string name="location" msgid="969988560160364559">"Emplacement"</string>
-    <string name="name" msgid="5990326151488445481">"Nom"</string>
+    <string name="location" msgid="3411848697912600125">"Adresse"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Ajouter à"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Nouveau dossier"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Libellé"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Ajouter un favori"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Ajouter aux favoris"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Ajouter cette page aux favoris"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Modifier le favori"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Raccourci (page d\'accueil)"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Ajouter sur la page d\'accueil"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Ouverture"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Supprimer le favori"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Supprimer des favoris"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Le favori \"<xliff:g id="BOOKMARK">%s</xliff:g>\" sera supprimé."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Nouvelle fenêtre"</string>
     <string name="goto_dot" msgid="3895839050522602723">"OK"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Rechercher sur la page"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Ouvrir un onglet de navigation privée"</string>
     <string name="select_dot" msgid="6299170761900561967">"Sélectionner le texte"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Fenêtres actuelles"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Fermer"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Téléchargements"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Copier l\'URL de la page"</string>
     <string name="share_page" msgid="593756995297268343">"Partager la page"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Enregistrer comme archive Web"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Archive Web enregistrée"</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Échec de l\'enregistrement de l\'archive Web"</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Ouvrir"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Nouvelle fenêtre"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Lien du favori"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Configurer les pages Web pour qu\'elles s\'ajustent à l\'écran"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Mode Paysage"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Toujours afficher les pages dans le sens de la largeur (orientation paysage)"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Paramètres personnels"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchroniser avec Google Voice"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Partager les favoris et d\'autres données entre le navigateur Android et Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Compte Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synchroniser les favoris"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synchroniser les favoris entre le navigateur Android et Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Démarrer la synchro"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Sélection du compte Google"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Paramètres de confidentialité"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Effacer le cache"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Supprimer les bases de données et le contenu localement en cache"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japonais (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japonais (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japonais (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Coréen (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codage du texte"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problème de connectivité des données"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Supprimer toutes les données"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Annuler"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Définition du fond d\'écran..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Favoris"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Aucun favori"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchronisation avec un compte Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Vos favoris Android ne sont associés à aucun compte Google."</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Supprimer vos favoris Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Ajouter vos favoris Android à ceux de <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-it-xlarge/strings.xml b/res/values-it-xlarge/strings.xml
new file mode 100644
index 0000000..c626430
--- /dev/null
+++ b/res/values-it-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Nuova scheda"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Nuova scheda in incognito"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Schede"</string>
+</resources>
diff --git a/res/values-it/strings.xml b/res/values-it/strings.xml
index a84dfa3..138aba2 100644
--- a/res/values-it/strings.xml
+++ b/res/values-it/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Browser"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Scegli il file per il caricamento"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nuova finestra"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nuova finestra in incognito"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Finestre"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Segnalibri"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"I più visitati"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
     <string name="cancel" msgid="3017274947407233702">"Annulla"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Nessuna corrispondenza"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 corrispondenza"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> corrispondenze"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> corrispondenze"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Caricamento..."</string>
     <string name="page_info" msgid="4048529256302257195">"Info pagina"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Visualizza info pagina"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Avanti"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Annulla"</string>
-    <string name="location" msgid="969988560160364559">"URL"</string>
-    <string name="name" msgid="5990326151488445481">"Nome"</string>
+    <string name="location" msgid="3411848697912600125">"Indirizzo"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Aggiungi a"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Nuova cartella"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Etichetta"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Aggiungi segnalibro"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Aggiungi ai segnalibri"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Aggiungi pagina ai segnalibri"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Modifica segnalibro"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Aggiungi scorciatoia su Home"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Aggiungi a schermata Home"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Apri"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Elimina segnalibro"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Rimuovi dai segnalibri"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Il segnalibro \"<xliff:g id="BOOKMARK">%s</xliff:g>\" verrà eliminato."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Apri in nuova finestra"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Vai"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Trova nella pagina"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Apri nuova scheda in incognito"</string>
     <string name="select_dot" msgid="6299170761900561967">"Seleziona testo"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Finestre correnti"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Chiudi"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Download"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Copia URL della pagina"</string>
     <string name="share_page" msgid="593756995297268343">"Condividi pagina"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Salva come archivio web"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Archivio web salvato"</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Salvataggio archivio web non riuscito."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Apri"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Apri in nuova finestra"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Aggiungi link in segnalibri"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Adatta le pagine web allo schermo"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Visual. solo orizzontale"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Visualizza le pagine solo con l\'orientamento dello schermo orizzontale più largo"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Impostazioni personali"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizza con Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Condividi Segnalibri e altri dati tra il Browser di Android e Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Account Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizza Segnalibri"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizza Segnalibri tra il Browser di Android e Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Avvia sincronizzazione"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Seleziona account Google"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Impostazioni privacy"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Cancella cache"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Cancella i contenuti e i database memorizzati localmente nella cache"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Giapponese (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Giapponese (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Giapponese (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codifica testo"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema di connettività dati"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Elimina tutti i dati"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Annulla"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Impostazione sfondo in corso..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Segnalibri"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Nessun segnalibro disponibile"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizza con l\'account Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"I tuoi Segnalibri Android non sono associati a un account Google"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Rimuovi i tuoi Segnalibri Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Aggiungi i tuoi Segnalibri Android a quelli per <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-ja-xlarge/strings.xml b/res/values-ja-xlarge/strings.xml
new file mode 100644
index 0000000..6786c84
--- /dev/null
+++ b/res/values-ja-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"新しいタブ"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"新しいシークレットタブ"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"タブ"</string>
+</resources>
diff --git a/res/values-ja/donottranslate_strings.xml b/res/values-ja/donottranslate_strings.xml
index cbda8f2..026d57a 100644
--- a/res/values-ja/donottranslate_strings.xml
+++ b/res/values-ja/donottranslate_strings.xml
@@ -17,5 +17,5 @@
 <resources xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
 
-    <string name="pref_default_text_encoding_default">SHIFT_JIS</string>
+    <string name="pref_default_text_encoding_default" translatable="false">SHIFT_JIS</string>
 </resources>
diff --git a/res/values-ja/strings.xml b/res/values-ja/strings.xml
index 07beb3b..de0af1f 100644
--- a/res/values-ja/strings.xml
+++ b/res/values-ja/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"ブラウザ"</string>
     <string name="choose_upload" msgid="3649366287575002063">"アップロードするファイルを選択"</string>
     <string name="new_tab" msgid="4505722538297295141">"新しいウィンドウ"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"新しいシークレットウインドウ"</string>
     <string name="active_tabs" msgid="3050623868203544623">"ウィンドウ"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"ブックマーク"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"よく使用"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"ブラウザ"</string>
     <string name="cancel" msgid="3017274947407233702">"キャンセル"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"該当なし"</item>
-    <item quantity="one" msgid="4352019729062956802">"1件一致"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g>件一致"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g>件一致"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"読み込み中..."</string>
     <string name="page_info" msgid="4048529256302257195">"ページ情報"</string>
     <string name="page_info_view" msgid="5303490449842635158">"ページ情報を表示"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"進む"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"キャンセル"</string>
-    <string name="location" msgid="969988560160364559">"場所"</string>
-    <string name="name" msgid="5990326151488445481">"名前"</string>
+    <string name="location" msgid="3411848697912600125">"アドレス"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"追加先"</string>
+    <string name="new_folder" msgid="7743540149088867917">"新しいフォルダ"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"ラベル"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"ブックマークを追加"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"ブックマークに追加"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"このページをブックマークに追加"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"編集"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"ショートカットを作成"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"ホーム画面に追加"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"開く"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"削除"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"ブックマークから削除"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"ブックマーク「<xliff:g id="BOOKMARK">%s</xliff:g>」を削除します。"</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"新しいウィンドウで開く"</string>
     <string name="goto_dot" msgid="3895839050522602723">"移動"</string>
-    <string name="find_dot" msgid="6259312434696611957">"ページ内検索"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"新しいシークレットタブを開く"</string>
     <string name="select_dot" msgid="6299170761900561967">"テキストを選択してコピー"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"現在のウィンドウ"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"閉じる"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"ダウンロード履歴"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"ページのURLをコピー"</string>
     <string name="share_page" msgid="593756995297268343">"ページを共有"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"ウェブアーカイブとして保存"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"ウェブアーカイブを保存しました。"</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"ウェブアーカイブを保存できませんでした。"</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"開く"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"新しいウィンドウで開く"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"リンクをブックマーク"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"画面に合わせてウェブページをフォーマットする"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"常に横向きに表示"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"ページを常に横向きに表示する"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"個人設定"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Google Chromeと同期する"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"AndroidブラウザとGoogle Chromeの間でブックマークなどのデータを共有する"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Googleアカウント"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"ブックマークを同期する"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"AndroidブラウザとGoogle Chromeの間でブックマークを同期"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"同期を開始"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Googleアカウントを選択"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"プライバシー設定"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"キャッシュを消去"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"ローカルにキャッシュしたコンテンツとデータベースを消去する"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"日本語(ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"日本語(SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"日本語(EUC-JP)"</item>
+    <item msgid="2193955365569270096">"韓国語(EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"テキストエンコード"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"データアクセスエラー"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"すべてのデータを削除"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"キャンセル"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"壁紙を設定中..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"ブックマーク"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"ブックマークはありません"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Googleアカウントと同期"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"AndroidのブックマークはGoogleアカウントに関連付けられていません"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Androidのブックマークを削除"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Androidのブックマークを<xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>のブックマークに追加"</string>
 </resources>
diff --git a/res/values-ko-xlarge/strings.xml b/res/values-ko-xlarge/strings.xml
new file mode 100644
index 0000000..228be47
--- /dev/null
+++ b/res/values-ko-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"새 탭"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"새 시크릿 창"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"탭"</string>
+</resources>
diff --git a/res/values-ko/strings.xml b/res/values-ko/strings.xml
index a10687f..fdf0bdf 100644
--- a/res/values-ko/strings.xml
+++ b/res/values-ko/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"인터넷"</string>
     <string name="choose_upload" msgid="3649366287575002063">"업로드할 파일 선택"</string>
     <string name="new_tab" msgid="4505722538297295141">"새 창"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"새 시크릿 창"</string>
     <string name="active_tabs" msgid="3050623868203544623">"창"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"북마크"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"자주 방문한 페이지"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"브라우저"</string>
     <string name="cancel" msgid="3017274947407233702">"취소"</string>
     <string name="ok" msgid="1509280796718850364">"확인"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"검색결과 없음"</item>
-    <item quantity="one" msgid="4352019729062956802">"검색결과 1개"</item>
-    <item quantity="few" msgid="5544267486978946555">"검색결과 <xliff:g id="NUMBER">%d</xliff:g>개"</item>
-    <item quantity="other" msgid="6616125067364315405">"검색결과 <xliff:g id="NUMBER">%d</xliff:g>개"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"로드 중..."</string>
     <string name="page_info" msgid="4048529256302257195">"페이지 정보"</string>
     <string name="page_info_view" msgid="5303490449842635158">"페이지 정보 보기"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"앞으로"</string>
     <string name="save" msgid="5922311934992468496">"확인"</string>
     <string name="do_not_save" msgid="6777633870113477714">"취소"</string>
-    <string name="location" msgid="969988560160364559">"URL"</string>
-    <string name="name" msgid="5990326151488445481">"이름"</string>
+    <string name="location" msgid="3411848697912600125">"주소"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"추가할 위치"</string>
+    <string name="new_folder" msgid="7743540149088867917">"새 폴더"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"라벨"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"북마크에 추가"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"북마크에 추가"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"페이지 북마크"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"북마크 수정"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"홈에 바로가기 추가"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"홈에 추가"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"열기"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"북마크 삭제"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"북마크에서 삭제"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"\'<xliff:g id="BOOKMARK">%s</xliff:g>\' 북마크가 삭제됩니다."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"새 창에서 열기"</string>
     <string name="goto_dot" msgid="3895839050522602723">"이동"</string>
-    <string name="find_dot" msgid="6259312434696611957">"페이지에서 찾기"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"새 시크릿 탭 열기"</string>
     <string name="select_dot" msgid="6299170761900561967">"텍스트 선택"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"현재 창"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"닫기"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"다운로드"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"페이지 URL 복사"</string>
     <string name="share_page" msgid="593756995297268343">"페이지 공유"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"웹 아카이브로 저장"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"웹 아카이브를 저장했습니다."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"웹 아카이브를 저장하지 못했습니다."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"열기"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"새 창에서 열기"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"링크를 북마크에 추가"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"화면에 맞게 웹페이지 형식 지정"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"가로 표시 전용"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"넓은 가로 방향 화면으로만 페이지 표시"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"개인 설정"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Google 크롬과 동기화"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Android 브라우저와 Google 크롬 간에 북마크 및 기타 데이터 공유"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google 계정"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"북마크 동기화"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Android 브라우저와 Google 크롬 간의 북마크 동기화"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"동기화 시작"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"공유할 Google 계정 선택"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"개인정보 설정"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"캐시 지우기"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"로컬로 캐시된 콘텐츠 및 데이터베이스 삭제"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"일본어(ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"일본어(SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"일본어(EUC-JP)"</item>
+    <item msgid="2193955365569270096">"한국어(EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"텍스트 인코딩"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"데이터 연결에 문제 발생"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"모든 데이터 삭제"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"취소"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"배경화면을 설정하는 중..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"북마크"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"북마크가 없습니다."</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Google 계정과 동기화"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"사용자의 Android 북마크는 Google 계정과 연결되지 않았습니다."</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Android 북마크 삭제"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"<xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>에 대한 북마크에 Android 북마크 추가"</string>
 </resources>
diff --git a/res/values-nb-xlarge/strings.xml b/res/values-nb-xlarge/strings.xml
new file mode 100644
index 0000000..6505d89
--- /dev/null
+++ b/res/values-nb-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Ny fane"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Ny inkognitofane"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Faner"</string>
+</resources>
diff --git a/res/values-nb/strings.xml b/res/values-nb/strings.xml
index 7021af6..e356502 100644
--- a/res/values-nb/strings.xml
+++ b/res/values-nb/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Nettleser"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Velg fil for opplasting"</string>
     <string name="new_tab" msgid="4505722538297295141">"Ny fane"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nytt inkognitovindu"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Vinduer"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Bokmerker"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Mest besøkt"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Nettleser"</string>
     <string name="cancel" msgid="3017274947407233702">"Avbryt"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Ingen treff"</item>
-    <item quantity="one" msgid="4352019729062956802">"Ett treff"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> treff"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> treff"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Laster inn ..."</string>
     <string name="page_info" msgid="4048529256302257195">"Sideinfo"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Vis sideinformasjon"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Fremover"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Avbryt"</string>
-    <string name="location" msgid="969988560160364559">"Adresse"</string>
-    <string name="name" msgid="5990326151488445481">"Navn"</string>
+    <string name="location" msgid="3411848697912600125">"Adresse"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Legg til i"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Ny mappe"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Etikett"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Legg til bokmerke"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Legg til i bokmerker"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Bokmerk denne siden"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Rediger bokmerke"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Lag snarvei på skrivebordet"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Legg til på startsiden"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Åpne"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Slett bokmerke"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Fjern fra bokmerker"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Bokmerket \"<xliff:g id="BOOKMARK">%s</xliff:g>\" vil bli slettet."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Åpne i nytt vindu"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Gå til"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Finn på siden"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Åpne ny inkognitofane"</string>
     <string name="select_dot" msgid="6299170761900561967">"Velg tekst"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Gjeldende vinduer"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Lukk"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Nedlastinger"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Kopier nettstedsadresse"</string>
     <string name="share_page" msgid="593756995297268343">"Del side"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Lagre som nettarkiv"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Nettarkiv lagret."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Kunne ikke lagre nettarkivet."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Åpne"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Åpne i nytt vindu"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Bokmerk kobling"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Tilpass nettsteder til skjermen"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Bare liggende visning"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Les alltid sider i bred, liggende skjermretning"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Personlige innstillinger"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synkroniser med Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Lagre bokmerker og andre data mellom Android-nettleseren og Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google-konto"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synkroniser bokmerker"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synkroniser bokmerker mellom Android-nettleseren og Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Start synkronisering"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Velg kto. å dele med"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Personvernsinnstillinger"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Fjern hurtiglager"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Fjern lokalt bufret innhold og databaser"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japansk (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japansk (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japansk (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Koreansk (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Tekstkoding"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Datatilkoblingsproblem"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Slett alle data"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Avbryt"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Angir bakgrunn ..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bokmerker"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Det er ingen bokmerker"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synkroniser med Google-konto"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Dine Android-bokmerker er ikke tilknyttet en Google-konto"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Fjern Android-bokmerkene"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Legg til Android-bokmerker i bokmerker for <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-nl-xlarge/strings.xml b/res/values-nl-xlarge/strings.xml
new file mode 100644
index 0000000..e1b8f0b
--- /dev/null
+++ b/res/values-nl-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Nieuw tabblad"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Nieuw incognitotabblad"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Tabbladen"</string>
+</resources>
diff --git a/res/values-nl/strings.xml b/res/values-nl/strings.xml
index 686e9c0..c436d27 100644
--- a/res/values-nl/strings.xml
+++ b/res/values-nl/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Browser"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Bestand selecteren voor uploaden"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nieuw venster"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nieuw incognitovenster"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Vensters"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Bladwijzers"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Meest bezocht"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
     <string name="cancel" msgid="3017274947407233702">"Annuleren"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Geen overeenkomsten"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 overeenkomst"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> overeenkomsten"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> overeenkomsten"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Laden..."</string>
     <string name="page_info" msgid="4048529256302257195">"Pagina-informatie"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Pagina-informatie weergeven"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Volgende"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Annuleren"</string>
-    <string name="location" msgid="969988560160364559">"Locatie"</string>
-    <string name="name" msgid="5990326151488445481">"Naam"</string>
+    <string name="location" msgid="3411848697912600125">"Adres"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Toevoegen aan"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Nieuwe map"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Label"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Bladwijzer toevoegen"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Toevoegen aan bladwijzers"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Bladwijzer instellen voor deze pagina"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Bladwijzer bewerken"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Snelkoppeling naar startpagina toevoegen"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Toevoegen aan startpagina"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Openen"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Bladwijzer verwijderen"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Verwijderen uit bladwijzers"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Bladwijzer \'<xliff:g id="BOOKMARK">%s</xliff:g>\' wordt verwijderd."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Openen in een nieuw venster"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Ga"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Zoeken op pagina"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Nieuw incognitotabblad openen"</string>
     <string name="select_dot" msgid="6299170761900561967">"Tekst selecteren"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Huidige vensters"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Sluiten"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Pagina-URL kopiëren"</string>
     <string name="share_page" msgid="593756995297268343">"Pagina delen"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Opslaan als webarchief"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Webarchief opgeslagen."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Opslaan van webarchief is mislukt."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Openen"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Openen in een nieuw venster"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Bladwijzer maken van link"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Webpagina\'s zo indelen dat deze op het scherm passen"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Altijd liggende weergave"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Pagina\'s alleen liggend weergeven"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Persoonlijke instellingen"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchroniseren met Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Bladwijzers en andere gegevens delen tussen Android Browser en Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google-account"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Bladwijzers synchroniseren"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Bladwijzers synchroniseren tussen Android Browser en Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchr. starten"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Selecteer Google-account voor delen"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Privacyinstellingen"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Cache wissen"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Lokaal opgeslagen inhoud en databases wissen"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japans (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japans (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japans (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Koreaans (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Tekstcodering"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Probleem met gegevensverbinding"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Alle gegevens wissen"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Annuleren"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Achtergrond instellen..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bladwijzers"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Er zijn geen bladwijzers"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"J1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchroniseren met Google-account"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Uw Android-bladwijzers zijn niet gekoppeld aan een Google-account"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Uw Android-bladwijzers verwijderen"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Uw Android-bladwijzers toevoegen aan bladwijzers voor <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-pl-xlarge/strings.xml b/res/values-pl-xlarge/strings.xml
new file mode 100644
index 0000000..10f0199
--- /dev/null
+++ b/res/values-pl-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Nowa karta"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Nowa karta incognito"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Karty"</string>
+</resources>
diff --git a/res/values-pl/strings.xml b/res/values-pl/strings.xml
index 3e7bd59..b50fc08 100644
--- a/res/values-pl/strings.xml
+++ b/res/values-pl/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Internet"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Wybierz plik do przesłania"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nowe okno"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nowe okno incognito"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Okna"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Zakładki"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Popularne"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Przeglądarka"</string>
     <string name="cancel" msgid="3017274947407233702">"Anuluj"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Brak wyników"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 wynik"</item>
-    <item quantity="few" msgid="5544267486978946555">"Wyników: <xliff:g id="NUMBER">%d</xliff:g>"</item>
-    <item quantity="other" msgid="6616125067364315405">"Wyników: <xliff:g id="NUMBER">%d</xliff:g>"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Trwa wczytywanie..."</string>
     <string name="page_info" msgid="4048529256302257195">"Informacje o stronie"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Informacje o stronie"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Dalej"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Anuluj"</string>
-    <string name="location" msgid="969988560160364559">"Adres"</string>
-    <string name="name" msgid="5990326151488445481">"Nazwa"</string>
+    <string name="location" msgid="3411848697912600125">"Adres"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Dodaj do"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Nowy folder"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Etykieta"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Dodaj zakładkę"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Dodaj do Zakładek"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Dodaj tę stronę do zakładek"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Edytuj zakładkę"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Dodaj skrót do strony głównej"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Dodaj do ekranu głównego"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Otwórz"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Usuń zakładkę"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Usuń z zakładek"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Zakładka „<xliff:g id="BOOKMARK">%s</xliff:g>” zostanie usunięta."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Otwórz w nowym oknie"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Przejdź"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Znajdź na stronie"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Otwórz nową kartę incognito"</string>
     <string name="select_dot" msgid="6299170761900561967">"Zaznacz tekst"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Bieżące okna"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Zamknij"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Pobrane"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Kopiuj adres URL strony"</string>
     <string name="share_page" msgid="593756995297268343">"Udostępnij stronę"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Zapisz jako archiwum internetowe"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Archiwum internetowe zostało zapisane."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Nie można zapisać archiwum internetowego."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Otwórz"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Otwórz w nowym oknie"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Dodaj link do zakładek"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatuj strony internetowe w celu dopasowania do ekranu"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Zawsze w poziomie"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Wyświetlaj strony tylko w szerszej, poziomej orientacji ekranu"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Ustawienia osobiste"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchronizuj z przeglądarką Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Udostępniaj zakładki i inne dane między przeglądarką w systemie Android i przeglądarką Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Konto Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synchronizuj zakładki"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synchronizuj zakładki między przeglądarką w systemie Android i przeglądarką Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchronizuj"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Wybierz konto Google dla udostępniania"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Ustawienia prywatności"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Wyczyść pamięć podręczną"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Wyczyść zawartość lokalnej pamięci podręcznej i baz danych"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"japoński (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"japoński (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"japoński (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"koreański (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Kodowanie tekstu"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problem z łącznością danych"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Usuń wszystkie dane"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Anuluj"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Trwa ustawianie tapety..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Zakładki"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Brak zakładek"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchronizuj z kontem Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Zakładki w systemie Android nie są powiązane z kontem Google"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Usuń zakładki w systemie Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Dodaj zakładki z systemu Android do zakładek na koncie <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-pt-rPT-xlarge/strings.xml b/res/values-pt-rPT-xlarge/strings.xml
new file mode 100644
index 0000000..7db3453
--- /dev/null
+++ b/res/values-pt-rPT-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Novo separador"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Novo sep. de navegação anónima"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Separadores"</string>
+</resources>
diff --git a/res/values-pt-rPT/strings.xml b/res/values-pt-rPT/strings.xml
index 8139636..f1534bf 100644
--- a/res/values-pt-rPT/strings.xml
+++ b/res/values-pt-rPT/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Navegad."</string>
     <string name="choose_upload" msgid="3649366287575002063">"Escolher ficheiro a carregar"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nova janela"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nova janela de naveg. anónima"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Janelas"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Marcadores"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Os mais visitados"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Navegad."</string>
     <string name="cancel" msgid="3017274947407233702">"Cancelar"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Sem correspondência"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 correspondência"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> correspondências"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> correspondências"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"A carregar..."</string>
     <string name="page_info" msgid="4048529256302257195">"Informações da página"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Ver informações da página"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Avançar"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Cancelar"</string>
-    <string name="location" msgid="969988560160364559">"Local"</string>
-    <string name="name" msgid="5990326151488445481">"Nome"</string>
+    <string name="location" msgid="3411848697912600125">"Endereço"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Adicionar a"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Nova pasta"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Etiqueta"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Adicionar marcador"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Adicionar aos marcadores"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Adicionar esta página aos marcadores"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Editar marcador"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Adicionar atalho à página inicial"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Adicionar à página inicial"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Abrir"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Eliminar marcador"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Remover dos marcadores"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"O marcador \"<xliff:g id="BOOKMARK">%s</xliff:g>\" será eliminado."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Abrir numa janela nova"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Ir"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Encontrar na página"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Abrir novo separador de navegação anónima"</string>
     <string name="select_dot" msgid="6299170761900561967">"Seleccionar texto"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Janelas actuais"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Fechar"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Transferências"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Copiar URL da página"</string>
     <string name="share_page" msgid="593756995297268343">"Partilhar página"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Guardar como arquivo Web"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Arquivo Web guardado."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Não foi possível guardar o arquivo Web."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Abrir"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Abrir numa janela nova"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Adicionar link aos marcadores"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatar páginas Web para se ajustarem ao ecrã"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Apresentação apenas na horizontal"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Mostrar páginas só na orientação horizontal do ecrã (mais larga)"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Definições pessoais"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizar com o Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Partilhar marcadores e outros dados entre o navegador do Android e o Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Conta Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizar marcadores"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizar marcadores entre o navegador do Android e o Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Inic. sincronização"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Selec. conta Google p/ partilhar c/"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Definições de privacidade"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Limpar cache"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Limpar bases de dados e conteúdos colocados em cache localmente"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japonês (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japonês (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japonês (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificação do texto"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de conectividade de dados"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Eliminar todos os dados"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancelar"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"A definir imagem de fundo..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Marcadores"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Não existem marcadores"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizar com conta Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Os seus marcadores do Android não estão associados a uma conta Google"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Remover marcadores do Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Adicionar os seus marcadores do Android aos marcadores da <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-pt-xlarge/strings.xml b/res/values-pt-xlarge/strings.xml
new file mode 100644
index 0000000..4ed9cd0
--- /dev/null
+++ b/res/values-pt-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Nova guia"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Nova guia anônima"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Guias"</string>
+</resources>
diff --git a/res/values-pt/strings.xml b/res/values-pt/strings.xml
index 546ae12..e2786b5 100644
--- a/res/values-pt/strings.xml
+++ b/res/values-pt/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Navegador"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Escolha o arquivo para envio"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nova janela"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nova janela anônima"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Janelas"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Favoritos"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Mais visitados"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Navegador"</string>
     <string name="cancel" msgid="3017274947407233702">"Cancelar"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Sem correspondências"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 correspondência"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> correspondências"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> correspondências"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Carregando..."</string>
     <string name="page_info" msgid="4048529256302257195">"Informações da página"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Visualizar informações da página"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Avançar"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Cancelar"</string>
-    <string name="location" msgid="969988560160364559">"Local"</string>
-    <string name="name" msgid="5990326151488445481">"Nome"</string>
+    <string name="location" msgid="3411848697912600125">"Endereço"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Adicionar a"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Nova pasta"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Marcador"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Adicionar favorito"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Adicionar aos favoritos"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Adicionar esta página aos favoritos"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Editar favorito"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Adicionar atalho à Página inicial"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Adicionar à página inicial"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Abrir"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Excluir favorito"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Remover dos favoritos"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"O favorito \"<xliff:g id="BOOKMARK">%s</xliff:g>\" será excluído."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Abrir em uma nova janela"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Ir"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Localizar na página"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Abrir nova guia anônima"</string>
     <string name="select_dot" msgid="6299170761900561967">"Selecionar texto"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Janelas atuais"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Fechar"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Copiar URL da página"</string>
     <string name="share_page" msgid="593756995297268343">"Compartilhar página"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Salvar como arquivo da web"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Arquivo da web salvo."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Falha ao salvar arquivo da web."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Abrir"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Abrir em uma nova janela"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Link do favorito"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatar páginas da web para se ajustarem à tela"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Apenas modo paisagem"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Exibir páginas apenas na orientação mais larga, com a tela no modo paisagem"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Configurações pessoais"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizar com o Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Compartilhar favoritos e outros dados entre o navegador do Android e o Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Conta do Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizar favoritos"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizar favoritos entre o navegador do Android e o Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Iniciar sincroniz."</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Sel. conta p/ comp."</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Configurações de privacidade"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Limpar cache"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Limpar conteúdo e bancos de dados armazenados localmente em cache"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japonês (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japonês (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japonês (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificação de texto"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de conectividade de dados"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Excluir todos os dados"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancelar"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Definindo o plano de fundo..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Favoritos"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Não há nenhum favorito"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizar com Conta do Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Seus favoritos do Android não estão associados a uma Conta do Google"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Remover os favoritos do Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Adicionar favoritos do Android aos favoritos de <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-rm/strings.xml b/res/values-rm/strings.xml
new file mode 100644
index 0000000..d32eb22
--- /dev/null
+++ b/res/values-rm/strings.xml
@@ -0,0 +1,380 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2007 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+  
+          http://www.apache.org/licenses/LICENSE-2.0
+  
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="application_name" msgid="1935869255545976415">"Navigatur"</string>
+    <string name="choose_upload" msgid="3649366287575002063">"Tscherner ina datoteca per importar"</string>
+    <string name="new_tab" msgid="4505722538297295141">"Nova fanestra"</string>
+    <!-- no translation found for new_incognito_tab (5821404839654751753) -->
+    <skip />
+    <string name="active_tabs" msgid="3050623868203544623">"Fanestra"</string>
+    <string name="tab_bookmarks" msgid="2305793036003473653">"Segnapaginas"</string>
+    <string name="tab_most_visited" msgid="1077402532455000703">"Visità il pli savens"</string>
+    <string name="tab_history" msgid="1979267558744613746">"Cronologia"</string>
+    <string name="added_to_bookmarks" msgid="1020224130695956728">"Agiuntà als segnapaginas"</string>
+    <string name="removed_from_bookmarks" msgid="6063705902028438800">"Allontanà dals segnapaginas"</string>
+    <string name="sign_in_to" msgid="5939425800148759165">"S\'annunziar tar <xliff:g id="HOSTNAME">%s1</xliff:g> «<xliff:g id="REALM">%s2</xliff:g>»"</string>
+    <string name="username" msgid="5057566336518215922">"Num"</string>
+    <string name="password" msgid="1177138552305184404">"Pled-clav"</string>
+    <string name="action" msgid="183105774472071343">"S\'annunziar"</string>
+    <string name="bookmarks_search" msgid="5229596268214362873">"Navigatur"</string>
+    <string name="cancel" msgid="3017274947407233702">"Interrumper"</string>
+    <string name="ok" msgid="1509280796718850364">"OK"</string>
+    <string name="title_bar_loading" msgid="7438217780834640678">"Chargiar…"</string>
+    <string name="page_info" msgid="4048529256302257195">"Infos davart la pagina"</string>
+    <string name="page_info_view" msgid="5303490449842635158">"Mussar las infurmaziuns da la pagina"</string>
+    <string name="page_info_address" msgid="2222306609532903254">"Adressa:"</string>
+    <string name="ssl_warnings_header" msgid="79744901983636370">"I ha dà in problem cun il certificat da segirezza per questa pagina."</string>
+    <string name="ssl_continue" msgid="8031515015829358457">"Cuntinuar"</string>
+    <string name="security_warning" msgid="6607795404322797541">"Avertiment da segirezza"</string>
+    <string name="view_certificate" msgid="1472768887529093862">"Mussar il certificat"</string>
+    <string name="ssl_untrusted" msgid="5369967226521102194">"Quest certificat n\'è betg vegnì emess dad in post da certificaziun fidà."</string>
+    <string name="ssl_mismatch" msgid="558688832420069896">"Il num da la website na correspunda betg al num sin il certificat."</string>
+    <string name="ssl_expired" msgid="5739349389499575559">"Quest certificat è scrudà."</string>
+    <string name="ssl_not_yet_valid" msgid="2893167846212645846">"Quest certificat n\'è anc betg valid."</string>
+    <string name="ssl_certificate" msgid="5226747157992111668">"Certificat da segirezza"</string>
+    <string name="ssl_certificate_is_valid" msgid="7096160815933145579">"Quest certificat è valid."</string>
+    <string name="issued_to" msgid="9032338008819841339">"Emess a:"</string>
+    <string name="common_name" msgid="5745530093500062357">"Num general:"</string>
+    <string name="org_name" msgid="8868889052889991293">"Organisaziun:"</string>
+    <string name="org_unit" msgid="4489056376307768196">"Unitad d\'organisaziun:"</string>
+    <string name="issued_by" msgid="6959484326943152487">"Emess da:"</string>
+    <string name="validity_period" msgid="57988851973181309">"Validitad:"</string>
+    <string name="issued_on" msgid="2082890654801808368">"Emess ils:"</string>
+    <string name="expires_on" msgid="8061200430557020704">"Scroda ils:"</string>
+    <string name="stopping" msgid="4839698519340302982">"Fermar…"</string>
+    <string name="stop" msgid="5687251076030630074">"Fermar"</string>
+    <string name="reload" msgid="8585220783228408062">"Actualisar"</string>
+    <string name="back" msgid="8414603107175713668">"Enavos"</string>
+    <string name="forward" msgid="4288210890526641577">"Vinavant"</string>
+    <string name="save" msgid="5922311934992468496">"OK"</string>
+    <string name="do_not_save" msgid="6777633870113477714">"Interrumper"</string>
+    <!-- outdated translation 969988560160364559 -->     <string name="location" msgid="3411848697912600125">"Adressa"</string>
+    <!-- no translation found for containing_folder (6771180232953030479) -->
+    <skip />
+    <!-- no translation found for new_folder (7743540149088867917) -->
+    <skip />
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <!-- outdated translation 5990326151488445481 -->     <string name="name" msgid="5462672162695365387">"Num"</string>
+    <string name="http" msgid="2163722670597250102">"http://"</string>
+    <!-- outdated translation 588165100024086565 -->     <string name="save_to_bookmarks" msgid="6101482434920313244">"Agiuntar in segnapagina"</string>
+    <!-- no translation found for bookmark_this_page (7530739804320811054) -->
+    <skip />
+    <string name="edit_bookmark" msgid="5024089053490231905">"Modifitgar il segnapagina"</string>
+    <!-- outdated translation 9202323987633899835 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Crear scursanidas sin il visur da partenza"</string>
+    <string name="open_bookmark" msgid="8473581305759935790">"Avrir"</string>
+    <string name="remove_bookmark" msgid="8407495852801410891">"Stizzar il segnapagina"</string>
+    <string name="remove_from_bookmarks" msgid="4374080666576982775">"Stizzar dals segnapaginas"</string>
+    <string name="remove_history_item" msgid="5021424935726728618">"Stizzar da la cronologia"</string>
+    <string name="set_as_homepage" msgid="4752937379414905560">"Definir sco pagina da partenza"</string>
+    <string name="bookmark_saved" msgid="2766434679871317557">"Memorisà en ils segnapaginas."</string>
+    <string name="bookmark_not_saved" msgid="700600955089376724">"Impussibel da memorisar il segnapagina."</string>
+    <string name="homepage_set" msgid="8768087280310966395">"Definì ina pagina da partenza."</string>
+    <string name="bookmark_needs_title" msgid="6245900436119218187">"Il segnapagina sto avair in num."</string>
+    <string name="bookmark_needs_url" msgid="7809876865972755158">"Il segnapagina sto avair in lieu da memorisaziun."</string>
+    <string name="bookmark_url_not_valid" msgid="6719785633980202419">"La URL è nuncorrecta."</string>
+    <string name="bookmark_cannot_save_url" msgid="791722768778386941">"Impussibel d\'agiuntar questa URL a Voss segnapaginas."</string>
+    <string name="delete_bookmark" msgid="2422989994934201992">"Stizzar"</string>
+    <string name="bookmark_page" msgid="6845189305130307274">"Segnapagina per l\'ultima pagina visitada"</string>
+    <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniaturas"</string>
+    <string name="switch_to_list" msgid="8900531247982121055">"Vista da glista"</string>
+    <string name="current_page" msgid="7510129573681663135">"da "</string>
+    <string name="delete_bookmark_warning" msgid="758043186202032205">"\"Il segnapagina \"\"<xliff:g id="BOOKMARK">%s</xliff:g>\"\" vegn stizzà.\""</string>
+    <string name="open_in_new_window" msgid="6596775546468054510">"Avrir en ina nova fanestra"</string>
+    <string name="goto_dot" msgid="3895839050522602723">"Dai"</string>
+    <!-- no translation found for incognito_tab (5419458065370134289) -->
+    <skip />
+    <string name="select_dot" msgid="6299170761900561967">"Selecziunar text"</string>
+    <string name="tab_picker_title" msgid="864478399057782913">"Fanestras actualas"</string>
+    <string name="tab_picker_remove_tab" msgid="630087809802479397">"Serrar"</string>
+    <string name="bookmarks" msgid="1961279134885867815">"Segnapaginas"</string>
+    <string name="shortcut_bookmark" msgid="3974876480401135895">"Segnapagina"</string>
+    <string name="history" msgid="2451240511251410032">"Cronologia"</string>
+    <string name="menu_view_download" msgid="2124570321712995120">"Telechargiadas"</string>
+    <string name="copy_page_url" msgid="7635062169011319208">"Copiar la URL da la pagina"</string>
+    <string name="share_page" msgid="593756995297268343">"Barattar la pagina"</string>
+    <!-- no translation found for menu_save_webarchive (3934652434001459581) -->
+    <skip />
+    <!-- no translation found for webarchive_saved (7045250341467345007) -->
+    <skip />
+    <!-- no translation found for webarchive_failed (2880998204746620260) -->
+    <skip />
+    <string name="contextmenu_openlink" msgid="7237961252214188935">"Avrir"</string>
+    <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Avrir en ina nova fanestra"</string>
+    <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Agiuntar la colliaziun als segnapaginas"</string>
+    <string name="contextmenu_savelink" msgid="5508554930832538184">"Memorisar la colliaziun"</string>
+    <string name="contextmenu_sharelink" msgid="5392275392280130331">"Barattar la colliaziun"</string>
+    <string name="contextmenu_copy" msgid="398860586635404030">"Copiar"</string>
+    <string name="contextmenu_copylink" msgid="5153657160294534270">"Copiar la URL da la colliaziun"</string>
+    <string name="contextmenu_download_image" msgid="4243829645180686912">"Memorisar il maletg"</string>
+    <string name="contextmenu_view_image" msgid="3870625602053600905">"Mussar il maletg"</string>
+    <string name="contextmenu_set_wallpaper" msgid="3691902960115350686">"Definir sco fund davos"</string>
+    <string name="contextmenu_dial_dot" msgid="5856550683415933806">"Cumponer..."</string>
+    <string name="contextmenu_add_contact" msgid="3183511922223645716">"Agiuntar in contact"</string>
+    <string name="contextmenu_send_mail" msgid="1014513374828775660">"Trametter in e-mail"</string>
+    <string name="contextmenu_map" msgid="7471390435434034912">"Charta"</string>
+    <string name="choosertitle_sharevia" msgid="4600490613341909086">"Cundivider cun agid da"</string>
+    <string name="clear" msgid="7070043081700011461">"Stizzar"</string>
+    <string name="replace" msgid="4843033491070384047">"Remplazzar"</string>
+    <string name="browser_bookmarks_page_bookmarks_text" msgid="6787605028726162673">"Segnapaginas"</string>
+    <string name="menu_preferences" msgid="6709237687234102240">"Parameters"</string>
+    <string name="pref_content_title" msgid="722227111894838633">"Parameters dal cuntegn da la pagina"</string>
+    <string name="pref_content_load_images" msgid="2125616852957377561">"Chargiar ils maletgs"</string>
+    <string name="pref_content_load_images_summary" msgid="5055874125248398584">"Mussar ils maletgs da las paginas web"</string>
+    <string name="pref_content_block_popups" msgid="7808433807197256726">"Bloccar las fanestras pop-up"</string>
+    <string name="pref_content_javascript" msgid="4570972030299516843">"Activar JavaScript"</string>
+    <string name="pref_content_open_in_background" msgid="824123779725118663">"Avrir davos las culissas"</string>
+    <string name="pref_content_plugins" msgid="7231944644794301582">"Activar ils plug-ins"</string>
+  <string-array name="pref_content_plugins_choices">
+    <item msgid="6745108155096660725">"Adina activ"</item>
+    <item msgid="2484126708670016519">"Sin dumonda"</item>
+    <item msgid="8547442717307793863">"Deactivà"</item>
+  </string-array>
+    <string name="pref_content_open_in_background_summary" msgid="1737664075721181678">"Avrir las novas fanestras davos la fanestra actuala"</string>
+    <string name="pref_content_homepage" msgid="6082437160778559806">"Definir la pagina da partenza"</string>
+    <!-- no translation found for pref_content_search_engine (1620101310821644144) -->
+    <skip />
+    <!-- no translation found for pref_content_search_engine_summary (5162667665858487316) -->
+    <skip />
+    <string name="pref_use_current" msgid="1493179933653044553">"Utilisar la pagina actuala"</string>
+    <string name="pref_content_autofit" msgid="8260474534053660809">"Adattar las paginas auto."</string>
+    <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Adattar las paginas web al visur"</string>
+    <string name="pref_content_landscape_only" msgid="2022546812766219672">"Visualisaziun mo en il format orizontal"</string>
+    <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Mussar las paginas mo en il format pli lad orizontal"</string>
+    <!-- no translation found for pref_personal_title (1447687455755683695) -->
+    <skip />
+    <!-- no translation found for pref_personal_sync_with_chrome (1695182180332194033) -->
+    <skip />
+    <!-- no translation found for pref_personal_sync_with_chrome_summary (7414133931827321055) -->
+    <skip />
+    <!-- no translation found for pref_personal_google_account (952360133341490071) -->
+    <skip />
+    <!-- no translation found for pref_personal_sync_bookmarks (59237515966184432) -->
+    <skip />
+    <!-- no translation found for pref_personal_sync_bookmarks_summary (4791767605662205482) -->
+    <skip />
+    <!-- no translation found for pref_personal_start_syncing (6046972042512655232) -->
+    <skip />
+    <!-- no translation found for pref_personal_account_dialog_title (1390867119887955530) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
+    <string name="pref_privacy_title" msgid="1052470980370846151">"Parameters da la protecziun da datas"</string>
+    <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Stizzar il cache"</string>
+    <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Stizzar las bancas da datas ed il cuntegn ord il cache local"</string>
+    <string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Las bancas da datas ed ils cuntegns en il cache local vegnan stizzads."</string>
+    <string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Stizzar tut ils cookies"</string>
+    <string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Stizzar tut ils cookies dal navigatur"</string>
+    <string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Tut ils cookies vegnan stizzads."</string>
+    <string name="pref_privacy_clear_history" msgid="8723795508825198477">"Stizzar la cronologia"</string>
+    <string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Stizzar la cronologia dal navigatur"</string>
+    <string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"La cronologia dal navigatur vegn stizzada."</string>
+    <string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Stizzar datas da formular"</string>
+    <string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Stizzar tut las datas da formular memorisadas"</string>
+    <string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Tut las datas da formulars memorisadas vegnan stizzadas."</string>
+    <string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Stizzar ils pleds-clav"</string>
+    <string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Stizzar tut ils pleds-clav memorisads"</string>
+    <string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Tut ils pleds-clav memorisads vegnan stizzads."</string>
+    <string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Activar la posiziun"</string>
+    <string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Autorisar las websites da dumandar l\'access a Vossa posiziun"</string>
+    <string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Stizzar l\'access a datas da posiziun"</string>
+    <string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Stizzar l\'access a datas da posiziun per tut las websites."</string>
+    <string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Stizzar l\'access a datas da posiziun per tut las websites"</string>
+    <string name="pref_security_title" msgid="5763978646932160021">"Parameters da segirezza"</string>
+    <string name="pref_security_remember_passwords" msgid="6492957683454529549">"Memorisar ils pleds-clav"</string>
+    <string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Memorisar ils nums d\'utilisader ed ils pleds-clav per las websites"</string>
+    <string name="pref_security_save_form_data" msgid="1213669802810198893">"Memorisar las datas da formular"</string>
+    <string name="pref_security_save_form_data_summary" msgid="4994074685153708026">"Memorisar las datas endatadas en formulars per reutilisar ellas"</string>
+    <string name="pref_security_show_security_warning" msgid="8901135676266754559">"Avertiments da segirezza"</string>
+    <string name="pref_security_show_security_warning_summary" msgid="8968906112720511704">"Mussar in avertiment en cas da problems da segirezza cun ina website"</string>
+    <string name="pref_security_accept_cookies" msgid="3201367661925047989">"Acceptar cookies"</string>
+    <string name="pref_security_accept_cookies_summary" msgid="1465118934875026920">"Permetter a las websites da memorisar e leger cookies"</string>
+    <string name="pref_text_size" msgid="3827031324346612208">"Grondezza dal text"</string>
+  <string-array name="pref_text_size_choices">
+    <item msgid="4952686548944739548">"Fitg pitschna"</item>
+    <item msgid="1950030433642671460">"Pitschna"</item>
+    <item msgid="4338347520133294584">"Normala"</item>
+    <item msgid="5043128215356351184">"Gronda"</item>
+    <item msgid="7201512237890458902">"Fitg grond"</item>
+  </string-array>
+    <string name="pref_text_size_dialogtitle" msgid="3625388833512647865">"Grondezza dal text"</string>
+    <string name="pref_default_zoom" msgid="8076142259097187395">"Zoom predefinì"</string>
+  <string-array name="pref_default_zoom_choices">
+    <item msgid="549583171195154919">"Lontan"</item>
+    <item msgid="5619034257768161024">"Mesauna"</item>
+    <item msgid="3840999588443167001">"Damanaivel"</item>
+  </string-array>
+    <string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom predefinì"</string>
+    <string name="pref_content_load_page" msgid="2219810141690955452">"Avrir las paginas en la survista"</string>
+    <string name="pref_content_load_page_summary" msgid="8792093504054149369">"Mussar ina survista da las paginas novas"</string>
+    <string name="pref_extras_title" msgid="3091250467679722382">"Parameters avanzads"</string>
+    <string name="pref_extras_website_settings" msgid="67866640052455549">"Parameters per websites"</string>
+    <string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Parameters avanzads per singulas websites"</string>
+    <string name="pref_extras_reset_default" msgid="8904000515846202110">"Reinizialisar il standard"</string>
+    <string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restaurar ils parameters predefinids"</string>
+    <string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Ils parameters da standard vegnan restituids."</string>
+    <string name="pref_extras_reset_default_dlg_title" msgid="2250334970728938936">"Restituir las valurs predefinidas"</string>
+    <string name="pref_development_title" msgid="3263854204533056480">"Debugar"</string>
+    <string name="pref_default_text_encoding" msgid="5742965543955558478">"Codaziun dal text"</string>
+    <!-- no translation found for pref_default_text_encoding_choices:7 (2193955365569270096) -->
+    <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codaziun dal text"</string>
+    <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problem da connectivitad da datas"</string>
+    <string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problem da datoteca"</string>
+    <string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confermar"</string>
+    <string name="browserFrameFormResubmitMessage" msgid="2752182215695632138">"La pagina che Vus vulais laschar mussar cuntegna datas ch\'èn gia vegnidas tramessas («POSTDATA»). Sche Vus tramettais danovamain las datas vegn mintga acziun ch\'il formular da la pagina ha exequì repetida (sco per exempel ina tschertga u ina cumpra online)."</string>
+    <string name="loadSuspendedTitle" msgid="675991625288706944">"Nagina connexiun da rait"</string>
+    <string name="loadSuspended" msgid="3133656588880851273">"Impussibel da chargiar questa pagina en il navigatur senza connexiun a l\'internet."</string>
+    <string name="clear_history" msgid="5998307092715979619">"Stizzar la cronologia"</string>
+    <string name="browser_history" msgid="1038987118290272525">"Paginas visitadas dacurt"</string>
+    <string name="empty_history" msgid="8738772352308207274">"La cronologia è vida."</string>
+    <string name="add_new_bookmark" msgid="8086367791400349049">"Agiuntar in segnapagina…"</string>
+    <string name="add_bookmark_short" msgid="3783984330998103735">"Agiuntar"</string>
+    <string name="search_hint" msgid="4647356319916631820">"Tschertgar u endatar ina URL"</string>
+    <string name="search_button_text" msgid="5235226933877634410">"Dai"</string>
+    <string name="search_settings_description" msgid="1422401062529014107">"Segnapaginas e cronologia web"</string>
+    <string name="attention" msgid="3473639060042811244">"Attenziun"</string>
+    <string name="popup_window_attempt" msgid="2673111696288657989">"Questa website emprova dad avrir ina fanestra pop-up."</string>
+    <string name="allow" msgid="1157313689171991335">"Permetter"</string>
+    <string name="block" msgid="9172175889884707800">"Bloccar"</string>
+    <string name="too_many_windows_dialog_title" msgid="5175503564948906442">"Cuntanschì la limita da fanestras"</string>
+    <string name="too_many_windows_dialog_message" msgid="1398571800233959583">"Impussibel dad avrir ina nova fanestra. Il dumber maximal da fanestras avertas è cuntanschì."</string>
+    <string name="too_many_subwindows_dialog_title" msgid="3805453941587725944">"La fanestra pop-up è gia averta"</string>
+    <string name="too_many_subwindows_dialog_message" msgid="5827289829907966657">"Impussibel d\'avrir ina nova fanestra. Ina unica fanestra po esser averta a la giada."</string>
+    <string name="download_title" msgid="2122874021047565594">"Cronologia da telechargiadas"</string>
+    <string name="download_unknown_filename" msgid="4013465542563652175">"&lt;Nunenconuschent&gt;"</string>
+    <string name="download_menu_open" msgid="4888327480367757513">"Avrir"</string>
+    <string name="download_menu_clear" msgid="6264454531553418124">"Stizzar da la glista"</string>
+    <string name="download_menu_delete" msgid="8815502136393894148">"Stizzar"</string>
+    <string name="download_menu_cancel" msgid="2545333007601851574">"Interrumper la telechargiada"</string>
+    <string name="download_menu_cancel_all" msgid="2136550823151999166">"Interrumper tut las telechargiadas"</string>
+    <string name="download_cancel_dlg_title" msgid="8909108500262799748">"Interrumper las telechargiadas"</string>
+    <string name="download_cancel_dlg_msg" msgid="6285389170052357797">"Las <xliff:g id="DOWNLOAD_COUNT">%d</xliff:g> telechargiadas vegnan annulladas e stizzadas da la cronologia da telechargiadas."</string>
+    <string name="download_delete_file" msgid="5330036497843073249">"La datoteca vegn stizzada."</string>
+    <string name="download_file_error_dlg_title" msgid="2693630283595384874">"Capacitad da memorisar nunsuffizienta"</string>
+    <string name="download_file_error_dlg_msg" msgid="5156405410324072471">"Impussibel da telechargiar <xliff:g id="FILENAME">%s</xliff:g>."\n"Rumi la memoria da Voss telefon ed empruvai anc ina giada."</string>
+    <string name="download_failed_generic_dlg_title" msgid="6106781095337833391">"Telechargiada betg reussida"</string>
+    <!-- outdated translation 605904452159416792 -->     <string name="download_no_sdcard_dlg_title" product="nosdcard" msgid="56777245081568508">"Nagina carta SD"</string>
+    <string name="download_no_sdcard_dlg_title" product="default" msgid="605904452159416792">"Nagina carta SD"</string>
+    <!-- outdated translation 2616399456116301518 -->     <string name="download_no_sdcard_dlg_msg" product="nosdcard" msgid="3144652102051031721">"Per telechargiar <xliff:g id="FILENAME">%s</xliff:g> è necessaria ina carta SD."</string>
+    <string name="download_no_sdcard_dlg_msg" product="default" msgid="2616399456116301518">"Per telechargiar <xliff:g id="FILENAME">%s</xliff:g> è necessaria ina carta SD."</string>
+    <!-- outdated translation 6877712666046917741 -->     <string name="download_sdcard_busy_dlg_title" product="nosdcard" msgid="8081445664689818973">"Carta SD betg disponibla"</string>
+    <string name="download_sdcard_busy_dlg_title" product="default" msgid="6877712666046917741">"Carta SD betg disponibla"</string>
+    <!-- outdated translation 3473883538192835204 -->     <string name="download_sdcard_busy_dlg_msg" product="nosdcard" msgid="3979329954835690147">"La carta SD è occupada. Tscherni «Deactivar la memoria USB» en l\'avis per permetter telechargiadas."</string>
+    <string name="download_sdcard_busy_dlg_msg" product="default" msgid="3473883538192835204">"La carta SD è occupada. Tscherni «Deactivar la memoria USB» en l\'avis per permetter telechargiadas."</string>
+    <string name="download_no_application_title" msgid="1286056729168874295">"Impussibel dad avrir la datoteca"</string>
+    <string name="retry" msgid="1835923075542266721">"Repeter"</string>
+    <string name="no_downloads" msgid="3947445710685021498">"La cronologia da telechargiadas è vida."</string>
+    <string name="download_error" msgid="413496839831257187">"La telechargiada n\'è betg reussida."</string>
+    <string name="download_success" msgid="2279041638155595203">"Terminà la telechargiada da <xliff:g id="FILE">%s</xliff:g>."</string>
+    <string name="download_running" msgid="2622942231322015059">"Telechargiada en process…"</string>
+    <string name="download_pending" msgid="2599683668575349559">"Cumenzar la telechargiada…"</string>
+    <string name="download_pending_network" msgid="6548714525679461053">"Spetgar ina connexiun da datas…"</string>
+    <string name="download_running_paused" msgid="6418029352085656495">"Spetgar la connexiun da datas…"</string>
+    <string name="download_canceled" msgid="6057083743144492515">"Telechargiada interrutta."</string>
+    <string name="download_not_acceptable" msgid="313769696131563652">"Impussibel da telechargiar. Il cuntegn na vegn betg sustegnì da quest telefon."</string>
+    <string name="download_file_error" msgid="1206648050615176113">"Impussibel da terminar la telechargiada. La capacitad da memorisar è nunsuffizienta."</string>
+    <string name="download_length_required" msgid="9038605488460437406">"Impussibel da cumenzar a telechargiar. La grondezza da l\'element na po betg vegnir distinguida."</string>
+    <string name="download_precondition_failed" msgid="8327584102874295580">"La telechargiada è vegnida interrutta e na po betg vegnir cuntinuada."</string>
+    <!-- no translation found for search_the_web (6046130189241962337) -->
+    <skip />
+    <!-- no translation found for webstorage_outofspace_notification_title (1160474608059771788) -->
+    <skip />
+    <string name="webstorage_outofspace_notification_text" msgid="7341075135051829692">"Cliccai qua per gudagnar capacitad da memorisar."</string>
+    <string name="webstorage_clear_data_title" msgid="689484577124333977">"Stizzar las datas memorisadas"</string>
+    <string name="webstorage_clear_data_dialog_title" msgid="345457466368974706">"Stizzar las datas memorisadas"</string>
+    <string name="webstorage_clear_data_dialog_message" msgid="6678281256970470125">"Tut las datas memorisadas da questa website vegnan stizzadas."</string>
+    <string name="webstorage_clear_data_dialog_ok_button" msgid="2516563534211898636">"Stizzar tut"</string>
+    <string name="webstorage_clear_data_dialog_cancel_button" msgid="2028867751958942762">"Interrumper"</string>
+    <string name="webstorage_origin_summary_mb_stored" msgid="1985885826292236210">"MB memorisads sin Voss telefon"</string>
+    <string name="loading_video" msgid="4887871585216091096">"Chargiar il video"</string>
+    <string name="geolocation_permissions_prompt_message" msgid="356796102004052471">"<xliff:g id="WEBSITE_ORIGIN">%s</xliff:g> vul savair Vossa posiziun geografica."</string>
+    <string name="geolocation_permissions_prompt_share" msgid="9084486342048347976">"Tradir mia posiziun"</string>
+    <string name="geolocation_permissions_prompt_dont_share" msgid="6303025160237860300">"Refusar"</string>
+    <string name="geolocation_permissions_prompt_remember" msgid="3118526300707348308">"Memorisar las preferenzas"</string>
+    <string name="geolocation_permissions_prompt_toast_allowed" msgid="987286072035125498">"Questa website ha access a Vossa posiziun. Modifitgai questa opziun en Parameters -&gt; Parameters da la website"</string>
+    <string name="geolocation_permissions_prompt_toast_disallowed" msgid="7695100950212692515">"Questa pagina n\'ha betg access a Vossa posiziun. Midai questa opziun en Parameters -&gt; Parameters da la website"</string>
+    <string name="geolocation_settings_page_title" msgid="1745477985097536528">"Stizzar l\'access a la posiziun"</string>
+    <string name="geolocation_settings_page_summary_allowed" msgid="9180251524290811398">"Questa website ha actualmain access a Vossa posiziun"</string>
+    <string name="geolocation_settings_page_summary_not_allowed" msgid="4589649082203102544">"Questa website n\'ha per il mument betg access a Vossa posiziun."</string>
+    <string name="geolocation_settings_page_dialog_title" msgid="1549842043381347668">"Stizzar l\'access a datas da posiziun"</string>
+    <string name="geolocation_settings_page_dialog_message" msgid="7586671987576403993">"L\'access da questa website a datas da posiziun vegn stizzà."</string>
+    <string name="geolocation_settings_page_dialog_ok_button" msgid="4789434178048077287">"Stizzar l\'access"</string>
+    <string name="geolocation_settings_page_dialog_cancel_button" msgid="7941036504673409747">"Interrumper"</string>
+    <string name="website_settings_clear_all" msgid="8739804325997655980">"Stizzar tut"</string>
+    <string name="website_settings_clear_all_dialog_title" msgid="7791826325122461718">"Stizzar tut ils parameters da la website?"</string>
+    <string name="website_settings_clear_all_dialog_message" msgid="6150502090601476333">"Tut las datas da la website e las autorisaziuns da posiziun vegnan stizzadas."</string>
+    <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Stizzar tut las datas"</string>
+    <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Interrumper"</string>
+    <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Il maletg dal fund davos vegn endrizzà…"</string>
+    <!-- no translation found for defaultBookmarksUpButton (2303951020715704735) -->
+    <skip />
+    <!-- no translation found for empty_bookmarks_folder (7843361614634930942) -->
+    <skip />
+    <!-- no translation found for rlz_access_point (7165847807377650632) -->
+    <skip />
+    <!-- no translation found for import_bookmarks_dialog_title (3325557652271172128) -->
+    <skip />
+    <!-- no translation found for import_bookmarks_dialog_description (2187665745413495303) -->
+    <skip />
+    <!-- no translation found for import_bookmarks_dialog_remove (8105572409059113340) -->
+    <skip />
+    <!-- no translation found for import_bookmarks_dialog_import (6933613853573899218) -->
+    <skip />
+</resources>
diff --git a/res/values-ru-xlarge/strings.xml b/res/values-ru-xlarge/strings.xml
new file mode 100644
index 0000000..9442ad4
--- /dev/null
+++ b/res/values-ru-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Новая вкладка"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Новая вкладка инкогнито"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Вкладки"</string>
+</resources>
diff --git a/res/values-ru/strings.xml b/res/values-ru/strings.xml
index c811ac3..db5d8d2 100644
--- a/res/values-ru/strings.xml
+++ b/res/values-ru/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Браузер"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Выберите файл для загрузки"</string>
     <string name="new_tab" msgid="4505722538297295141">"Новое окно"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Новое окно в режиме инкогнито"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Окна"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Закладки"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Часто посещаемые"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Браузер"</string>
     <string name="cancel" msgid="3017274947407233702">"Отмена"</string>
     <string name="ok" msgid="1509280796718850364">"ОК"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Соответствий нет"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 соответствие"</item>
-    <item quantity="few" msgid="5544267486978946555">"Соответствий: <xliff:g id="NUMBER">%d</xliff:g>"</item>
-    <item quantity="other" msgid="6616125067364315405">"Соответствий: <xliff:g id="NUMBER">%d</xliff:g>"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Загрузка…"</string>
     <string name="page_info" msgid="4048529256302257195">"Информация о странице"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Информация о странице"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Вперед"</string>
     <string name="save" msgid="5922311934992468496">"ОК"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Отмена"</string>
-    <string name="location" msgid="969988560160364559">"URL-адрес"</string>
-    <string name="name" msgid="5990326151488445481">"Имя"</string>
+    <string name="location" msgid="3411848697912600125">"Адрес"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Добавить в"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Новая папка"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Ярлык"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Добавить закладку"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Добавить в Закладки"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Закладка для этой страницы"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Изменить закладку"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Добавить ярлык на главную страницу"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Добавить на главный экран"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Открыть"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Удалить закладку"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Удалить из закладок"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Закладка \"<xliff:g id="BOOKMARK">%s</xliff:g>\" будет удалена."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Открыть в новом окне"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Поиск"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Найти на странице"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Открыть новую вкладку в режиме инкогнито"</string>
     <string name="select_dot" msgid="6299170761900561967">"Выбрать текст"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Открытые окна"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Закрыть"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Загрузки"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Копировать URL страницы"</string>
     <string name="share_page" msgid="593756995297268343">"Отправить страницу"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Сохранить как веб-архив"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Веб-архив сохранен."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Не удалось сохранить веб-архив."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Открыть"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Открыть в новом окне"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Добавить ссылку в закладки"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Адаптировать контент к размеру экрана мобильного устройства"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Только горизонтально"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Показывать страницы только в горизонтальной ориентации"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Личные настройки"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Синхронизировать с Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Совместно использовать закладки и другие данные в браузере Android и Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Аккаунт Google"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Синхронизировать закладки"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Синхронизировать закладки браузера Android и Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Синхронизировать"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Выберите аккаунт Google"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Настройки конфиденциальности"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Очистить кэш"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Удалить контент и данные, сохраненные браузером"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Японская (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Японская (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Японская (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Корейская (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Кодировка текста"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Проблема с подключением"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Удалить все данные"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Отмена"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Установка фонового рисунка..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Закладки"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Нет закладок"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Синхронизация с аккаунтом Google"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Закладки Android не связаны с аккаунтом Google"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Удалить закладки Android"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Добавить закладки Android в аккаунт <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-sv-xlarge/strings.xml b/res/values-sv-xlarge/strings.xml
new file mode 100644
index 0000000..13b5470
--- /dev/null
+++ b/res/values-sv-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Ny flik"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Ny inkognitoflik"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Flikar"</string>
+</resources>
diff --git a/res/values-sv/strings.xml b/res/values-sv/strings.xml
index be60ec5..4f7e321 100644
--- a/res/values-sv/strings.xml
+++ b/res/values-sv/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Webbläs."</string>
     <string name="choose_upload" msgid="3649366287575002063">"Välj filen som du vill överföra"</string>
     <string name="new_tab" msgid="4505722538297295141">"Nytt fönster"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Nytt inkognitofönster"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Fönster"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Bokmärken"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"Mest besökta"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Webbläsare"</string>
     <string name="cancel" msgid="3017274947407233702">"Avbryt"</string>
     <string name="ok" msgid="1509280796718850364">"OK"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Inga träffar"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 träff"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> träffar"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> träffar"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Hämtar…"</string>
     <string name="page_info" msgid="4048529256302257195">"Sidinformation"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Visa sidinformation"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"Framåt"</string>
     <string name="save" msgid="5922311934992468496">"OK"</string>
     <string name="do_not_save" msgid="6777633870113477714">"Avbryt"</string>
-    <string name="location" msgid="969988560160364559">"Plats"</string>
-    <string name="name" msgid="5990326151488445481">"Namn"</string>
+    <string name="location" msgid="3411848697912600125">"Adress"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Lägg till"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Ny mapp"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Etikett"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Lägg till bokmärke"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Lägg till i bokmärken"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Lägg till bokmärke för den här sidan"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Redigera bokmärke"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Lägg till genväg till startsidan"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Lägg till på startsidan"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Öppna"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Ta bort bokmärke"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Ta bort från bokmärken"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Bokmärket <xliff:g id="BOOKMARK">%s</xliff:g> tas bort."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Öppna i nytt fönster"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Kör"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Sök på sidan"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Öppna ny inkognitoflik"</string>
     <string name="select_dot" msgid="6299170761900561967">"Markera text"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Aktuellt fönster"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Stäng"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"Hämtningar"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Kopiera sidans webbadress"</string>
     <string name="share_page" msgid="593756995297268343">"Dela sida"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Spara som webbarkiv"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Webbarkivet har sparats"</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Det gick inte att spara webbarkivet."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Öppna"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Öppna i nytt fönster"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Skapa ett bokmärke av länken"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Anpassa webbsidor efter skärmen"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Endast liggande"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Visa bara sidor i det bredare, liggande formatet"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Personliga inställningar"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synkronisera med Google Chrome"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Dela bokmärken och andra data mellan Androids webbläsare och Google Chrome"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google-konto"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synkronisera bokmärken"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synkronisera bokmärken mellan Androids webbläsare och Google Chrome"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synkronisera nu"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Välj Google-konto"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Sekretessinställningar"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Rensa cacheminne"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Ta bort innehåll och databaser som cachelagrats lokalt"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japansk (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japansk (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japansk (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"koreanska (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Textkodning"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problem med dataanslutning"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Ta bort alla data"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Avbryt"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Anger bakgrund..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bokmärken"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Det finns inga bokmärken"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synkronisera med Google-konto"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Dina Android-bokmärken har inte kopplats till något Google-konto"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Ta bort dina Android-bokmärken"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Lägg till dina Android-bokmärken i bokmärkena för <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
 </resources>
diff --git a/res/values-tr-xlarge/strings.xml b/res/values-tr-xlarge/strings.xml
new file mode 100644
index 0000000..cf3cf07
--- /dev/null
+++ b/res/values-tr-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"Yeni sekme"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"Yeni gizli sekme"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"Sekmeler"</string>
+</resources>
diff --git a/res/values-tr/strings.xml b/res/values-tr/strings.xml
index 7564ca6..52cb29f 100644
--- a/res/values-tr/strings.xml
+++ b/res/values-tr/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"Tarayıcı"</string>
     <string name="choose_upload" msgid="3649366287575002063">"Yükleme için dosya seçin"</string>
     <string name="new_tab" msgid="4505722538297295141">"Yeni pencere"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"Yeni gizli pencere"</string>
     <string name="active_tabs" msgid="3050623868203544623">"Pencereler"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"Favoriler"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"En çok ziyaret edilenler"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"Tarayıcı"</string>
     <string name="cancel" msgid="3017274947407233702">"İptal"</string>
     <string name="ok" msgid="1509280796718850364">"Tamam"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"Eşleşme yok"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 eşleşme"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> eşleşme"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> eşleşme"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"Yükleniyor…"</string>
     <string name="page_info" msgid="4048529256302257195">"Sayfa bilgileri"</string>
     <string name="page_info_view" msgid="5303490449842635158">"Sayfa bilgilerini görüntüle"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"İleri"</string>
     <string name="save" msgid="5922311934992468496">"Tamam"</string>
     <string name="do_not_save" msgid="6777633870113477714">"İptal"</string>
-    <string name="location" msgid="969988560160364559">"Konum"</string>
-    <string name="name" msgid="5990326151488445481">"Ad"</string>
+    <string name="location" msgid="3411848697912600125">"Adres"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"Şu klasöre ekle"</string>
+    <string name="new_folder" msgid="7743540149088867917">"Yeni klasör"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"Etiket"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"Favori ekle"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"Yer İşaretlerine Ekle"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"Bu sayfaya yer işareti koy"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"Favorileri düzenle"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Ana ekrana kısayol ekle"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Ana Ekrana Ekle"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"Aç"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"Favoriyi sil"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"Favorilerden kaldır"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"Favori \"<xliff:g id="BOOKMARK">%s</xliff:g>\" silinecek."</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"Yeni pencerede aç"</string>
     <string name="goto_dot" msgid="3895839050522602723">"Git"</string>
-    <string name="find_dot" msgid="6259312434696611957">"Sayfada bul"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"Yeni gizli sekme aç"</string>
     <string name="select_dot" msgid="6299170761900561967">"Metin seç"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"Geçerli pencereler"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"Kapat"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"İndirme işlemleri"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"Sayfa url\'sini kopyala"</string>
     <string name="share_page" msgid="593756995297268343">"Sayfayı paylaş"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"Web Arşivi olarak Kaydet"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"Web arşivi kaydedildi."</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"Web arşivi kaydedilemedi."</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"Aç"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Yeni pencerede aç"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Favori bağlantısı"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"Web sayfalarını ekrana sığacak şekilde biçimlendir"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"Yalnızca yatay görüntü"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Sayfaları yalnızca daha geniş, yatay ekran yönünde görüntüle"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"Kişisel ayarlar"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Google Chrome ile senkronize et"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Yer işaretlerini ve diğer verileri Android Tarayıcı ile Google Chrome arasında paylaş"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google hesabı"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Yer işaretlerini senkronize et"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Yer işaretlerini Android Tarayıcı ve Google Chrome arasında senkronize et"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Senk. başlat"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Paylaşım için Google hesabını seçin"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"Gizlilik ayarları"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Önbelleği temizle"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Yerel olarak önbelleğe alınmış içeriği ve veritabanlarını temizle"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"Japonca (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"Japonca (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"Japonca (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"Korece (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Metin kodlama"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Veri bağlantısı sorunu"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Tüm verileri sil"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"İptal"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Duvar kağıdı ayarlanıyor..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Yer işaretleri"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Hiçbir yer işareti yok"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Google hesabı ile senkronize et"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Android yer işaretleriniz bir Google hesabı ile ilişkilendirilmemiş"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Android yer işaretlerinizi kaldırın"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Android yer işaretlerinizi <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> yer işaretlerine ekleyin"</string>
 </resources>
diff --git a/res/values-xlarge/dimensions.xml b/res/values-xlarge/dimensions.xml
new file mode 100644
index 0000000..c335c19
--- /dev/null
+++ b/res/values-xlarge/dimensions.xml
@@ -0,0 +1,16 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+    Copyright (C) 2010 The Android Open Source Project Licensed under the
+    Apache License, Version 2.0 (the "License"); you may not use this file
+    except in compliance with the License. You may obtain a copy of the
+    License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+    applicable law or agreed to in writing, software distributed under the
+    License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+    CONDITIONS OF ANY KIND, either express or implied. See the License for
+    the specific language governing permissions and limitations under the
+    License.
+-->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <dimen name="bookmarkThumbnailWidth">180dip</dimen>
+    <dimen name="bookmarkThumbnailHeight">120dip</dimen>
+</resources>
\ No newline at end of file
diff --git a/res/values-xlarge/strings.xml b/res/values-xlarge/strings.xml
new file mode 100644
index 0000000..07b2b34
--- /dev/null
+++ b/res/values-xlarge/strings.xml
@@ -0,0 +1,25 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <!-- Name of menu item of a new tab.
+         Also used in the title bar when displaying a new tab [CHAR LIMIT=30] -->
+    <string name="new_tab">New tab</string>
+    <!-- Name of menu item of a new incognito tab.  Also used in the
+         title bar when displaying a new tab [CHAR LIMIT=30] -->
+    <string name="new_incognito_tab">New incognito tab</string>
+    <!-- Name of menu item which brings up a list of the currently active tabs -->
+    <string name="active_tabs">Tabs</string>
+</resources>
diff --git a/res/values-xlarge/styles.xml b/res/values-xlarge/styles.xml
new file mode 100644
index 0000000..57bcb91
--- /dev/null
+++ b/res/values-xlarge/styles.xml
@@ -0,0 +1,60 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+ *
+ * Copyright 2006,2007,2008 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+-->
+
+<resources>
+    <style name="BrowserTheme" parent="@android:Theme.Holo">
+        <item name="android:windowBackground">@color/white</item>
+        <item name="android:colorBackground">#FFFFFFFF</item>
+        <item name="android:windowActionBar">true</item>
+        <item name="android:windowNoTitle">false</item>
+        <item name="android:actionBarStyle">@style/ActionBarStyle</item>
+        <item name="android:actionButtonStyle">@style/ActionButton</item>
+    </style>
+    <style name="Dialog" parent="@android:style/Theme.Holo.Dialog" >
+        <item name="android:windowActionBar">false</item>
+    </style>
+    <style name="BookmarkTheme" parent="@android:Theme.Holo">
+        <item name="android:windowActionBar">false</item>
+        <item name="android:windowNoTitle">true</item>
+        <item name="android:colorBackgroundCacheHint">@null</item>
+        <item name="android:windowFrame">@null</item>
+        <item name="android:windowContentOverlay">@null</item>
+        <item name="android:windowIsFloating">true</item>
+        <item name="android:backgroundDimEnabled">false</item>
+        <item name="android:windowIsTranslucent">true</item>
+    </style>
+    <style name="ShortCutTheme" parent="@android:Theme.Holo">
+    </style>
+    <style name="ActionBarStyle">
+        <item name="android:height">48dip</item>
+        <item name="android:padding">0dip</item>
+        <item name="android:background">@drawable/tabbar_bg</item>
+        <item name="android:displayOptions">hideHome</item>
+    </style>
+    <style name="ActionButton">
+        <item name="android:background">@drawable/browserbarbutton</item>
+    </style>
+    <style name="SuggestionLineMedium"
+            parent="@android:style/TextAppearance.Holo.Medium.Inverse">
+    </style>
+    <style name="SuggestionLineSmall"
+            parent="@android:style/TextAppearance.Holo.Small.Inverse">
+    </style>
+</resources>
diff --git a/res/values-zh-rCN-xlarge/strings.xml b/res/values-zh-rCN-xlarge/strings.xml
new file mode 100644
index 0000000..4a1b2da
--- /dev/null
+++ b/res/values-zh-rCN-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"新建标签页"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"新建隐身标签页"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"标签页"</string>
+</resources>
diff --git a/res/values-zh-rCN/strings.xml b/res/values-zh-rCN/strings.xml
index 05e0a5e..f5c0f99 100644
--- a/res/values-zh-rCN/strings.xml
+++ b/res/values-zh-rCN/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"浏览器"</string>
     <string name="choose_upload" msgid="3649366287575002063">"选择要上传的文件"</string>
     <string name="new_tab" msgid="4505722538297295141">"新窗口"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"新隐身窗口"</string>
     <string name="active_tabs" msgid="3050623868203544623">"窗口"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"书签"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"访问最多"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"浏览器"</string>
     <string name="cancel" msgid="3017274947407233702">"取消"</string>
     <string name="ok" msgid="1509280796718850364">"确定"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"没有匹配项"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 个匹配项"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> 个匹配项"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> 个匹配项"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"正在载入..."</string>
     <string name="page_info" msgid="4048529256302257195">"网页信息"</string>
     <string name="page_info_view" msgid="5303490449842635158">"查看网页信息"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"前进"</string>
     <string name="save" msgid="5922311934992468496">"确定"</string>
     <string name="do_not_save" msgid="6777633870113477714">"取消"</string>
-    <string name="location" msgid="969988560160364559">"地点"</string>
-    <string name="name" msgid="5990326151488445481">"姓名"</string>
+    <string name="location" msgid="3411848697912600125">"地址"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"添加到"</string>
+    <string name="new_folder" msgid="7743540149088867917">"新建文件夹"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"标签"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"添加书签"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"添加到书签"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"将此页加为书签"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"编辑书签"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"向主屏幕添加快捷方式"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"添加到主屏幕"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"打开"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"删除书签"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"从书签中删除"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"将会删除书签“<xliff:g id="BOOKMARK">%s</xliff:g>”。"</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"在新窗口中打开"</string>
     <string name="goto_dot" msgid="3895839050522602723">"转至"</string>
-    <string name="find_dot" msgid="6259312434696611957">"页内查找"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"打开新的隐身标签页"</string>
     <string name="select_dot" msgid="6299170761900561967">"选择文本"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"当前窗口"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"关闭"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"下载内容"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"复制网页网址"</string>
     <string name="share_page" msgid="593756995297268343">"分享网页"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"另存为网络存档"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"网络存档已保存。"</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"无法保存网络存档。"</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"打开"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"在新窗口中打开"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"将链接加入书签"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"调整网页版面以适合屏幕大小"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"仅以横向模式显示"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"仅以横向宽屏模式显示网页"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"个人设置"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"与谷歌浏览器同步"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"在 Android 浏览器和谷歌浏览器之间共享书签和其他数据"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google 帐户"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"同步书签"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"在 Android 浏览器和谷歌浏览器之间同步书签"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"开始同步"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"选择要与其共享数据的 Google 帐户"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"隐私权设置"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"清除缓存"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"清除存储在本地缓存中的内容和数据库"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"日语 (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"日语 (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"日语 (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"韩语 (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"文字编码"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"数据连接性问题"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"删除所有数据"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"取消"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"正在设置壁纸..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"书签"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"无书签"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"与 Google 帐户同步"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Android 书签尚未与 Google 帐户关联"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"删除 Android 书签"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"将 Android 书签添加到 <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> 的书签中"</string>
 </resources>
diff --git a/res/values-zh-rTW-xlarge/strings.xml b/res/values-zh-rTW-xlarge/strings.xml
new file mode 100644
index 0000000..156a1ea
--- /dev/null
+++ b/res/values-zh-rTW-xlarge/strings.xml
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--  Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <string name="new_tab" msgid="7275656655054293038">"新分頁"</string>
+    <string name="new_incognito_tab" msgid="5149742197322201152">"新無痕式分頁"</string>
+    <string name="active_tabs" msgid="5324492165541331128">"分頁"</string>
+</resources>
diff --git a/res/values-zh-rTW/strings.xml b/res/values-zh-rTW/strings.xml
index 49e5c3f..37d30d1 100644
--- a/res/values-zh-rTW/strings.xml
+++ b/res/values-zh-rTW/strings.xml
@@ -19,6 +19,7 @@
     <string name="application_name" msgid="1935869255545976415">"瀏覽器"</string>
     <string name="choose_upload" msgid="3649366287575002063">"選擇要上載的檔案"</string>
     <string name="new_tab" msgid="4505722538297295141">"新視窗"</string>
+    <string name="new_incognito_tab" msgid="5821404839654751753">"新的無痕式視窗"</string>
     <string name="active_tabs" msgid="3050623868203544623">"視窗"</string>
     <string name="tab_bookmarks" msgid="2305793036003473653">"書籤"</string>
     <string name="tab_most_visited" msgid="1077402532455000703">"常用網頁"</string>
@@ -32,12 +33,6 @@
     <string name="bookmarks_search" msgid="5229596268214362873">"瀏覽器"</string>
     <string name="cancel" msgid="3017274947407233702">"取消"</string>
     <string name="ok" msgid="1509280796718850364">"確定"</string>
-  <plurals name="matches_found">
-    <item quantity="zero" msgid="6242659159545399963">"沒有相配項"</item>
-    <item quantity="one" msgid="4352019729062956802">"1 個相配項"</item>
-    <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> 個相符項目"</item>
-    <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> 個相符項目"</item>
-  </plurals>
     <string name="title_bar_loading" msgid="7438217780834640678">"載入中..."</string>
     <string name="page_info" msgid="4048529256302257195">"頁面資訊"</string>
     <string name="page_info_view" msgid="5303490449842635158">"檢視頁面資訊"</string>
@@ -67,12 +62,23 @@
     <string name="forward" msgid="4288210890526641577">"下一頁"</string>
     <string name="save" msgid="5922311934992468496">"確定"</string>
     <string name="do_not_save" msgid="6777633870113477714">"取消"</string>
-    <string name="location" msgid="969988560160364559">"位置"</string>
-    <string name="name" msgid="5990326151488445481">"名稱"</string>
+    <string name="location" msgid="3411848697912600125">"地址"</string>
+    <string name="containing_folder" msgid="6771180232953030479">"新增至"</string>
+    <string name="new_folder" msgid="7743540149088867917">"新資料夾"</string>
+    <!-- no translation found for no_subfolders (5880411440592452802) -->
+    <skip />
+    <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+    <skip />
+    <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+    <skip />
+    <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+    <skip />
+    <string name="name" msgid="5462672162695365387">"標籤"</string>
     <string name="http" msgid="2163722670597250102">"http://"</string>
-    <string name="save_to_bookmarks" msgid="588165100024086565">"新增書籤"</string>
+    <string name="save_to_bookmarks" msgid="6101482434920313244">"加入書籤"</string>
+    <string name="bookmark_this_page" msgid="7530739804320811054">"將這個網頁加入書籤"</string>
     <string name="edit_bookmark" msgid="5024089053490231905">"編輯書籤"</string>
-    <string name="create_shortcut_bookmark" msgid="9202323987633899835">"新增捷徑至首頁"</string>
+    <!-- outdated translation 4528337239019328891 -->     <string name="create_shortcut_bookmark" msgid="1995095662095484289">"加入主螢幕"</string>
     <string name="open_bookmark" msgid="8473581305759935790">"開啟"</string>
     <string name="remove_bookmark" msgid="8407495852801410891">"刪除書籤"</string>
     <string name="remove_from_bookmarks" msgid="4374080666576982775">"從書籤中移除"</string>
@@ -93,7 +99,7 @@
     <string name="delete_bookmark_warning" msgid="758043186202032205">"刪除「<xliff:g id="BOOKMARK">%s</xliff:g>」書籤?"</string>
     <string name="open_in_new_window" msgid="6596775546468054510">"在新視窗開啟"</string>
     <string name="goto_dot" msgid="3895839050522602723">"前往"</string>
-    <string name="find_dot" msgid="6259312434696611957">"在頁面中尋找"</string>
+    <string name="incognito_tab" msgid="5419458065370134289">"開啟新的無痕式分頁"</string>
     <string name="select_dot" msgid="6299170761900561967">"選取文字"</string>
     <string name="tab_picker_title" msgid="864478399057782913">"目前視窗"</string>
     <string name="tab_picker_remove_tab" msgid="630087809802479397">"關閉"</string>
@@ -103,6 +109,9 @@
     <string name="menu_view_download" msgid="2124570321712995120">"下載"</string>
     <string name="copy_page_url" msgid="7635062169011319208">"複製網頁網址"</string>
     <string name="share_page" msgid="593756995297268343">"分享網頁"</string>
+    <string name="menu_save_webarchive" msgid="3934652434001459581">"另存為網頁封存"</string>
+    <string name="webarchive_saved" msgid="7045250341467345007">"已儲存網頁封存。"</string>
+    <string name="webarchive_failed" msgid="2880998204746620260">"無法儲存網頁封存。"</string>
     <string name="contextmenu_openlink" msgid="7237961252214188935">"開啟"</string>
     <string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"在新視窗開啟"</string>
     <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"將連結加入書籤"</string>
@@ -143,6 +152,52 @@
     <string name="pref_content_autofit_summary" msgid="4587831659894879986">"配合螢幕大小調整網頁版面"</string>
     <string name="pref_content_landscape_only" msgid="2022546812766219672">"僅以水平模式顯示"</string>
     <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"僅以橫向寬螢幕瀏覽模式顯示網頁"</string>
+    <string name="pref_personal_title" msgid="1447687455755683695">"個人設定"</string>
+    <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"與Google 瀏覽器保持同步"</string>
+    <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"共享「Android 瀏覽器」和「Google 瀏覽器」之間的書籤及其他資料"</string>
+    <string name="pref_personal_google_account" msgid="952360133341490071">"Google 帳戶"</string>
+    <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"同步處理書籤"</string>
+    <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"同步處理「Android 瀏覽器」和「Google 瀏覽器」之間的書籤"</string>
+    <string name="pref_personal_start_syncing" msgid="6046972042512655232">"開始同步"</string>
+    <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"請選取要與其共用的 Google 帳戶"</string>
+    <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+    <skip />
+    <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+    <skip />
+    <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+    <skip />
+    <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+    <skip />
+    <!-- no translation found for autofill_profile_editor_delete_profile (7112035941146003753) -->
+    <skip />
     <string name="pref_privacy_title" msgid="1052470980370846151">"隱私設定"</string>
     <string name="pref_privacy_clear_cache" msgid="3380316479925886998">"清除快取"</string>
     <string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"清除本機快取內容與資料庫"</string>
@@ -208,6 +263,7 @@
     <item msgid="891615911084608570">"日文 (ISO-2022-JP)"</item>
     <item msgid="5589150448475151241">"日文 (SHIFT_JIS)"</item>
     <item msgid="7356792686950371843">"日文 (EUC-JP)"</item>
+    <item msgid="2193955365569270096">"韓文 (EUC-KR)"</item>
   </string-array>
     <string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"文字編碼"</string>
     <string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"資料連線問題"</string>
@@ -296,4 +352,11 @@
     <string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"刪除所有資料"</string>
     <string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"取消"</string>
     <string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"設定桌布..."</string>
+    <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"書籤"</string>
+    <string name="empty_bookmarks_folder" msgid="7843361614634930942">"沒有任何書籤"</string>
+    <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+    <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"與 Google 帳戶保持同步"</string>
+    <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"您的 Android 書籤未與任何 Google 帳戶建立關聯"</string>
+    <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"移除您的 Android 書籤"</string>
+    <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"將您的 Android 書籤新增至 <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> 的書籤"</string>
 </resources>
diff --git a/res/values/colors.xml b/res/values/colors.xml
index 68bf253..822c3b4 100644
--- a/res/values/colors.xml
+++ b/res/values/colors.xml
@@ -20,19 +20,8 @@
 <!-- FIXME: Change the name of this file!  It is now being used generically
     for the browser -->
 <resources>
-    <color name="username_text">#ffffffff</color>
-    <color name="username_edit">#ff000000</color>
-
-    <color name="password_text">#ffffffff</color>
-    <color name="password_edit">#ff000000</color>
-
-    <color name="ssl_text_label">#ffffffff</color>
-    <color name="ssl_text_value">#ffffffff</color>
-    
     <color name="white">#ffffffff</color>
     <color name="black">#ff000000</color>
     
-    
-
     <color name="geolocation_permissions_prompt_background">#ffdddddd</color>
 </resources>
diff --git a/res/values/dimensions.xml b/res/values/dimensions.xml
new file mode 100644
index 0000000..f550cf7
--- /dev/null
+++ b/res/values/dimensions.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+    Copyright (C) 2010 The Android Open Source Project Licensed under the
+    Apache License, Version 2.0 (the "License"); you may not use this file
+    except in compliance with the License. You may obtain a copy of the
+    License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+    applicable law or agreed to in writing, software distributed under the
+    License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+    CONDITIONS OF ANY KIND, either express or implied. See the License for
+    the specific language governing permissions and limitations under the
+    License.
+-->
+<resources
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <!-- The width of a selected tab -->
+    <dimen
+        name="tab_width_selected">300dp</dimen>
+    <!-- The width of an unselected tab -->
+    <dimen
+        name="tab_width_unselected">300dp</dimen>
+
+    <dimen name="bookmarkThumbnailWidth">90dip</dimen>
+    <dimen name="bookmarkThumbnailHeight">80dip</dimen>
+    <dimen name="add_bookmark_width">500dip</dimen>
+    <dimen name="folder_selector_height">300dip</dimen>
+</resources>
diff --git a/res/values/integers.xml b/res/values/integers.xml
new file mode 100644
index 0000000..c923805
--- /dev/null
+++ b/res/values/integers.xml
@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+    Copyright (C) 2010 The Android Open Source Project Licensed under the
+    Apache License, Version 2.0 (the "License"); you may not use this file
+    except in compliance with the License. You may obtain a copy of the
+    License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+    applicable law or agreed to in writing, software distributed under the
+    License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+    CONDITIONS OF ANY KIND, either express or implied. See the License for
+    the specific language governing permissions and limitations under the
+    License.
+-->
+<resources
+    xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+    <!-- The number of lines in the suggestions dropdown in landscape -->
+    <integer name="max_suggest_lines_landscape">6</integer>
+    <!-- The number of lines in the suggestions dropdown in portrait -->
+    <integer name="max_suggest_lines_portrait">12</integer>
+    <!--  The maximum number of open tabs -->
+    <integer name="max_tabs">16</integer>
+    <!--  The duration of the tab animations in millisecs  -->
+    <integer name="tab_animation_duration">500</integer>
+    <integer name="max_width_crumb">200</integer>
+</resources>
diff --git a/res/values/strings.xml b/res/values/strings.xml
index fc0d68b..7d7fd0f 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -20,6 +20,9 @@
     <string name="choose_upload">Choose file for upload</string>
     <!-- Name of menu item of a new tab.  Also used in the title bar when displaying a new tab -->
     <string name="new_tab">New window</string>
+    <!-- Name of menu item of a new incognito tab.  Also used in the
+         title bar when displaying a new tab [CHAR LIMIT=30] -->
+    <string name="new_incognito_tab">New incognito window</string>
     <!-- Name of menu item which brings up a list of the currently active tabs -->
     <string name="active_tabs">Windows</string>
     <!-- Name of tab containing bookmarks -->
@@ -44,25 +47,11 @@
     <string name="action">Sign in</string>
     <!-- The name of the bookmarks and history search suggestion source.  -->
     <string name="bookmarks_search">Browser</string>
-
     <!-- Label for a cancel button.  It is used for multiple cancel buttons in different contexts -->
     <string name="cancel">Cancel</string>
     <!-- Label for a confirm button.  Used in multiple contexts. -->
     <string name="ok">OK</string>
 
-    <!-- Displayed on the Find dialog to display the number of matches
-         found in the current page. -->
-    <plurals name="matches_found">
-        <!-- Case of no matches -->
-        <item quantity="zero">No matches</item>
-        <!-- Case of one match -->
-        <item quantity="one">1 match</item>
-        <!-- Case of "few" (two) matches -->
-        <item quantity="few"><xliff:g id="number" example="2">%d</xliff:g> matches</item>
-        <!-- Case of several matches -->
-        <item quantity="other"><xliff:g id="number" example="137">%d</xliff:g> matches</item>
-    </plurals>
-
     <!-- Displayed on the title bar while the page is loading -->
     <string name="title_bar_loading">Loading\u2026</string>
 
@@ -133,17 +122,33 @@
     <!-- Button label to cancel saving a bookmark. -->
     <string name="do_not_save">Cancel</string>
     <!-- Field label in Bookmark dialog box: refers to URL of the page to bookmark -->
-    <string name="location">Location</string>
+    <string name="location">Address</string>
+    <!-- Field label in Bookmark dialog box: refers to the folder in which to save the bookmark -->
+    <string name="containing_folder">Add to</string>
+    <!-- Default name for a new folder and label for a button that allows the user to create a new folder
+         in the add bookmark dialog -->
+    <string name="new_folder">New folder</string>
+    <!-- Label stating that the currently open folder has no subfolders
+         in the add bookmark dialog [CHAR-LIMIT=none]-->
+    <string name="no_subfolders">No subfolders</string>
+    <!-- Menu item to use the top level bookmarks folder to save a bookmark in. [CHAR-LIMIT=30]-->
+    <string name="add_to_bookmarks_menu_option">Bookmarks</string>
+    <!-- Menu item to save the newly created bookmark to the home screen. [CHAR-LIMIT=30]-->
+    <string name="add_to_homescreen_menu_option">Home screen</string>
+    <!-- Menu item to open a picker to determine which folder to save a bookmark in. [CHAR-LIMIT=30]-->
+    <string name="add_to_other_folder_menu_option">Other folder\u2026</string>
     <!-- Field label in Bookmark dialog box: title that the user wishes to use for the bookmark -->
-    <string name="name">Name</string>
+    <string name="name">Label</string>
     <!-- Initial value in Location field in Bookmark dialog box -->
     <string name="http">http://</string>
-    <!-- Menu item that opens a dialog to save a bookmark, initialized with the current page -->
-    <string name="save_to_bookmarks">Add bookmark</string>
+    <!-- Menu item that opens a dialog to save a bookmark for the current page -->
+    <string name="save_to_bookmarks">Add to Bookmarks</string>
+    <!-- Title of the dialog to bookmark a page -->
+    <string name="bookmark_this_page">Bookmark this page</string>
     <!-- Menu item on the bookmarks page, to edit an existing bookmark -->
     <string name="edit_bookmark">Edit bookmark</string>
     <!-- Context menu item to create a shortcut to the bookmark on the desktop -->
-    <string name="create_shortcut_bookmark">Add shortcut to Home</string>
+    <string name="create_shortcut_bookmark">Add shortcut to home</string>
     <!-- Context menu item to open the currently highlighted bookmark -->
     <string name="open_bookmark">Open</string>
     <!-- Menu item to remove the currently highlighted bookmark-->
@@ -194,9 +199,8 @@
     <string name="open_in_new_window">Open in new window</string>
     <!-- Menu item to open a dialog which allows the user to enter a url or do search-->
     <string name="goto_dot">Go</string>
-    <!-- Menu item that opens up a dialog which allows the user to provide a
-            string and search for it on the page. -->
-    <string name="find_dot">Find on page</string>
+    <!-- Menu item that opens up a new incognito tab.  -->
+    <string name="incognito_tab">Open new incognito tab</string>
     <!-- Menu item to switch to text selection mode for copy and paste. -->
     <string name="select_dot">Select text</string>
     <!-- Title of current windows screen; appears in title bar -->
@@ -217,6 +221,12 @@
     <string name="copy_page_url">Copy page url</string>
     <!-- Menu item -->
     <string name="share_page">Share page</string>
+    <!-- Menu item for saving a page as a web archive. -->
+    <string name="menu_save_webarchive">Save as Web Archive</string>
+    <!-- Toast informing the user that the page has been saved. -->
+    <string name="webarchive_saved">Web archive saved.</string>
+    <!-- Toast informing the user that saving the page has failed. -->
+    <string name="webarchive_failed">Failed to save web archive.</string>
     <!-- Context Menu item open the currently selected link in the current
             window.-->
     <string name="contextmenu_openlink">Open</string>
@@ -309,8 +319,14 @@
     <string name="pref_content_search_engine">Set search engine</string>
     <!-- Settings summary -->
     <string name="pref_content_search_engine_summary">Select a search engine</string>
-    <!-- Settings button label -->
-    <string name="pref_use_current">Use current page</string>
+    <!-- Settings button label that to pick what to set the homepage to [CHAR LIMIT=40] -->
+    <string name="pref_set_homepage_to">Set to\u2026</string>
+    <!-- Settings button label to set the homepage to the current page [CHAR LIMIT=40] -->
+    <string name="pref_use_current">Current page</string>
+    <!-- Settings button label to set the homepage to a blank page [CHAR LIMIT=40] -->
+    <string name="pref_use_blank">Blank page</string>
+    <!-- Settings button label to set the homepage to the default page [CHAR LIMIT=40] -->
+    <string name="pref_use_default">Default page</string>
     <!-- Settings label -->
     <string name="pref_content_autofit">Auto-fit pages</string>
     <!-- Settings summary -->
@@ -319,6 +335,68 @@
     <string name="pref_content_landscape_only">Landscape-only display</string>
     <!-- Settings summary -->
     <string name="pref_content_landscape_only_summary">Display pages only in the wider, landscape screen orientation</string>
+
+    <!-- Settings screen & section title for "Personal settings". These include things like
+         configuring bookmark syncing to Google servers and form auto fill settings. [CHAR-LIMIT=32] -->
+    <string name="pref_personal_title">Personal settings</string>
+    <!-- Checkbox setting to enable or disable syncing bookmarks and other data with Google Chrome. [CHAR-LIMIT=48] -->
+    <string name="pref_personal_sync_with_chrome">Sync with Google Chrome</string>
+    <!-- Checkbox setting to enable or disable syncing bookmarks and other data with Google Chrome. [CHAR-LIMIT=none] -->
+    <string name="pref_personal_sync_with_chrome_summary">Share bookmarks &amp; other data between Android Browser and Google Chrome</string>
+    <!-- Label indicating which Google account is being used to sync bookmarks between Android and Chrome [CHAR-LIMIT=20] -->
+    <string name="pref_personal_google_account">Google account</string>
+    <!-- Checkbox setting to enable or disable syncing bookmarks with Google Chrome. [CHAR-LIMIT=32] -->
+    <string name="pref_personal_sync_bookmarks">Sync bookmarks</string>
+    <!-- Summary for a checkbox setting to enable or disable syncing bookmarks with Google Chrome. [CHAR-LIMIT=none] -->
+    <string name="pref_personal_sync_bookmarks_summary">Sync bookmarks between Android Browser and Google Chrome</string>
+    <!-- Button to start a sync of bookmarks and other data between the Android Browser and Google Chrome [CHAR-LIMIT=20] -->
+    <string name="pref_personal_start_syncing">Start syncing</string>
+    <!-- Dialog title used when asking the user which Google account they want to use to sync data between Android Browser and Google Chrome [CHAR-LIMIT=20] -->
+    <string name="pref_personal_account_dialog_title">Select Google account to share with</string>
+
+    <!-- Checkbox setting for enabling/disabling the form AutoFill feature [CHAR-LIMIT=32] -->
+    <string name="pref_autofill_enabled">Form AutoFill</string>
+    <!-- Settings summary for the form AutoFill feature. [CHAR-LIMIT=none] -->
+    <string name="pref_autofill_enabled_summary">Fill out web forms in a single click</string>
+    <!-- Label for option that when clicked opens the AutoFill settings screen. Also used as the title of that AutoFill Settings screen. [CHAR-LIMIT=32] -->
+    <string name="pref_autofill_profile_editor">AutoFill Settings</string>
+    <!-- Summary for the AutoFill Settings preference [CHAR-LIMIT=none] -->
+    <string name="pref_autofill_profile_editor_summary">Set up &amp; manage data for AutoFilled forms</string>
+
+    <!-- String for the user's full name in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_name">Full name:</string>
+    <!-- String for the user's e-mail address in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_email_address">Email:</string>
+    <!-- String for the user's company name in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_company_name">Company name:</string>
+    <!-- String for the first line of the user's address in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_address_line_1">Address line 1:</string>
+    <!-- String to suggest to the user the kind of data to be used for the first line of the address. CHAR-LIMIT=64] -->
+    <string name="autofill_profile_editor_address_line_1_hint">Street address, P.O. box, c/o</string>
+    <!-- String for the second line of the user's address in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_address_line_2">Address line 2:</string>
+    <!-- String to suggest to the user the kind of data to be used for the second line of the address. CHAR-LIMIT=64] -->
+    <string name="autofill_profile_editor_address_line_2_hint">Apartment, suite, unit, building, floor etc.</string>
+    <!-- String for the user's city or town in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_city">City / Town:</string>
+    <!-- String for the user's state or province or region in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_state">State / Province / Region:</string>
+    <!-- String for the user's zip code in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_zip_code">Zip code:</string>
+    <!-- String for the user's country in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_country">Country:</string>
+    <!-- String for the user's phone number in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+    <string name="autofill_profile_editor_phone_number">Phone:</string>
+
+    <!-- Button text to save the AutoFill profile [CHAR-LIMIT=20] -->
+    <string name="autofill_profile_editor_save_profile">Save profile</string>
+    <!-- Toast message displayed when the profile has been successfully saved [CHAR-LIMIT=none] -->
+    <string name="autofill_profile_successful_save">Profile saved</string>
+    <!-- Toast message displayed when the profile has been successfully deleted [CHAR-LIMIT=none] -->
+    <string name="autofill_profile_successful_delete">Profile deleted</string>
+    <!-- Button text to delete all the AutoFill profile data [CHAR-LIMIT=20] -->
+    <string name="autofill_profile_editor_delete_profile">Delete profile data</string>
+
     <!-- Settings screen, section title -->
     <string name="pref_privacy_title">Privacy settings</string>
     <!-- Settings label -->
@@ -477,6 +555,8 @@
         <item>Japanese (ISO-2022-JP)</item>
         <item>Japanese (SHIFT_JIS)</item>
         <item>Japanese (EUC-JP)</item>
+        <!-- No need to translate a EUC-KR part, and there is no string length limits. -->
+        <item>Korean (EUC-KR)</item>
         <!-- TODO: We should add a lot more encodings.  -->
     </string-array>
     <!-- Dialog box title -->
@@ -490,6 +570,7 @@
         <item>ISO-2022-JP</item>
         <item>SHIFT_JIS</item>
         <item>EUC-JP</item>
+        <item>EUC-KR</item>
     </string-array>
     <string name="pref_default_text_encoding_default" translatable="false">Latin-1</string>
     <!-- Title for a dialog displayed when the browser has a data connectivity
@@ -753,4 +834,26 @@
     <string name="error_console_eval_text_hint" translatable="false">Evaluate JavaScript</string>
     <string name="error_console_eval_button_text" translatable="false">Evaluate</string>
 
+    <!-- The default state to the "up to parent folder" button in the bookmarks UI. This
+         is displayed when the user is at the highest level and cannot go up [CHAR LIMIT=16] -->
+    <string name="defaultBookmarksUpButton">Bookmarks</string>
+
+    <!-- The string that is displayed when there are no bookmarks to display.
+         This is centered in the middle of the screen [CHAR LIMIT=NONE] -->
+    <string name="empty_bookmarks_folder">There are no bookmarks</string>
+
+    <!-- Access point for RLZ tracking. -->
+    <string name="rlz_access_point">Y1</string>
+
+    <!-- Title for a dialog asking the user what they want to do with their bookmarks when adding a sync account [CHAR-LIMIT=32] -->
+    <string name="import_bookmarks_dialog_title">Sync with Google account</string>
+
+    <!-- Description for a dialog asking the user what they want to do with their bookmarks when adding a sync account [CHAR-LIMIT=none] -->
+    <string name="import_bookmarks_dialog_description">Your Android bookmarks are not associated with a Google account</string>
+
+    <!-- Button allowing users to remove all of their existing bookmarks when setting up syncing with their bookmarks stored in Google Chrome [CHAR-LIMIT=64] -->
+    <string name="import_bookmarks_dialog_remove">Remove your Android bookmarks</string>
+
+    <!-- Button allowing users to import all of their existing bookmarks into an account when setting up syncing with their bookmarks stored in Google Chrome [CHAR-LIMIT=64] -->
+    <string name="import_bookmarks_dialog_import">Add your Android bookmarks to bookmarks for <xliff:g id="Google account" example="account@example.com">%s</xliff:g></string>
 </resources>
diff --git a/res/values/styles.xml b/res/values/styles.xml
index 2e8510a..a1ca842 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -1,38 +1,62 @@
 <?xml version="1.0" encoding="utf-8"?>
 <!--
-/* 
+/*
  *
  * Copyright 2006,2007,2008 The Android Open Source Project
  *
- * Licensed under the Apache License, Version 2.0 (the "License"); 
- * you may not use this file except in compliance with the License. 
- * You may obtain a copy of the License at 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
  *
- *     http://www.apache.org/licenses/LICENSE-2.0 
+ *     http://www.apache.org/licenses/LICENSE-2.0
  *
- * Unless required by applicable law or agreed to in writing, software 
- * distributed under the License is distributed on an "AS IS" BASIS, 
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
- * See the License for the specific language governing permissions and 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
  * limitations under the License.
  */
 -->
 <resources>
     <style name="BrowserTheme" parent="@android:Theme.Black">
-        <item name="android:windowBackground">@color/white</item>
-        <item name="android:colorBackground">#FFFFFFFF</item>
         <item name="android:windowNoTitle">true</item>
         <item name="android:windowContentOverlay">@null</item>
     </style>
-
+    <style name="Dialog" parent="@android:style/Theme.Dialog">
+        <item name="android:background">@color/black</item>
+    </style>
+    <style name="ActionBar" parent="@android:style/Widget.ActionBar">
+        <item name="android:background">@color/black</item>
+    </style>
     <style name="BookmarkTheme" parent="@android:Theme.Black">
         <item name="android:windowNoTitle">true</item>
         <item name="android:windowContentOverlay">@null</item>
     </style>
-
+    <style name="ShortcutTheme" parent="@android:Theme.Black">
+        <item name="android:windowNoTitle">true</item>
+        <item name="android:windowContentOverlay">@null</item>
+    </style>
     <style name="TitleBar">
         <item name="android:windowEnterAnimation">@anim/title_bar_enter</item>
         <item name="android:windowExitAnimation">@anim/title_bar_exit</item>
     </style>
+        <style name="HoloIcon">
+        <item name="android:paddingLeft">16dip</item>
+        <item name="android:paddingRight">16dip</item>
+    </style>
+    <style name="HoloButton" parent="@style/HoloIcon">
+        <item name="android:background">@drawable/browserbarbutton</item>
+    </style>
+    <style name="TabTitleSelected" parent="@android:style/TextAppearance.Small">
+        <item name="android:textColor">?android:attr/textColorPrimary</item>
+        <item name="android:textStyle">bold</item>
+    </style>
+    <style name="TabTitleUnselected" parent="@android:style/TextAppearance.Small">
+        <item name="android:textColor">?android:attr/textColorSecondary</item>
+        <item name="android:textStyle">normal</item>
+    </style>
+    <style name="SuggestionLineMedium" parent="@android:style/TextAppearance.Medium">
+    </style>
+    <style name="SuggestionLineSmall" parent="@android:style/TextAppearance.Small">
+    </style>
 </resources>
-
diff --git a/res/xml/advanced_preferences.xml b/res/xml/advanced_preferences.xml
new file mode 100644
index 0000000..075232d
--- /dev/null
+++ b/res/xml/advanced_preferences.xml
@@ -0,0 +1,41 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2008 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<PreferenceScreen
+        xmlns:android="http://schemas.android.com/apk/res/android">
+
+        <!-- Entries and values in this list are set dynamically. -->
+        <com.android.browser.search.SearchEnginePreference
+                android:key="search_engine"
+                android:title="@string/pref_content_search_engine"
+                android:defaultValue="google"
+                android:summary="@string/pref_content_search_engine_summary"
+                android:dialogTitle="@string/pref_content_search_engine" />
+
+        <PreferenceScreen
+              android:key="website_settings"
+              android:title="@string/pref_extras_website_settings"
+              android:summary="@string/pref_extras_website_settings_summary" />
+
+        <com.android.browser.BrowserYesNoPreference
+                android:key="reset_default_preferences"
+                android:title="@string/pref_extras_reset_default"
+                android:summary="@string/pref_extras_reset_default_summary"
+                android:dialogMessage="@string/pref_extras_reset_default_dlg" 
+                android:dialogTitle="@string/pref_extras_reset_default_dlg_title" 
+                android:dialogIcon="@android:drawable/ic_dialog_alert" />
+
+</PreferenceScreen>
diff --git a/res/xml/bookmarkstackwidget.xml b/res/xml/bookmarkstackwidget.xml
new file mode 100644
index 0000000..56e7351
--- /dev/null
+++ b/res/xml/bookmarkstackwidget.xml
@@ -0,0 +1,25 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<!-- 2x2 Widget displaying the user's bookmarks as thumbnails. -->
+<appwidget-provider
+    xmlns:android="http://schemas.android.com/apk/res/android"
+    android:minWidth="146dip"
+    android:minHeight="146dip"
+    android:updatePeriodMillis="3600000"
+    android:previewImage="@drawable/preview"
+    android:initialLayout="@layout/bookmarkstackwidget">
+</appwidget-provider>
diff --git a/res/xml/browser_preferences.xml b/res/xml/browser_preferences.xml
index 1da85ec..cb4e0b5 100644
--- a/res/xml/browser_preferences.xml
+++ b/res/xml/browser_preferences.xml
@@ -139,6 +139,12 @@
                 android:title="@string/pref_security_save_form_data"
                 android:summary="@string/pref_security_save_form_data_summary" />
 
+        <CheckBoxPreference
+                android:key="autofill_enabled"
+                android:defaultValue="false"
+                android:title="@string/pref_autofill_enabled"
+                android:summary="@string/pref_autofill_enabled_summary" />
+
         <com.android.browser.BrowserYesNoPreference
                 android:key="privacy_clear_form_data"
                 android:title="@string/pref_privacy_clear_form_data"
diff --git a/res/xml/debug_preferences.xml b/res/xml/debug_preferences.xml
index c1ed1e6..54b2bd5 100644
--- a/res/xml/debug_preferences.xml
+++ b/res/xml/debug_preferences.xml
@@ -16,59 +16,54 @@
 
 <PreferenceScreen 
         xmlns:android="http://schemas.android.com/apk/res/android" >
-    <PreferenceCategory
-        android:title="@string/pref_development_title" 
-        android:key="debug_menu" >
 
-        <!-- The javascript console is enabled by default when the user has
-             also enabled debug mode by navigating to about:debug. -->
-        <CheckBoxPreference
-            android:key="javascript_console"
-            android:defaultValue="true"
-            android:title="@string/pref_development_error_console" />
-                        
-        <CheckBoxPreference
-            android:key="small_screen"
-            android:defaultValue="false"
-            android:title="@string/pref_development_single_column_rendering" />   
-
-        <CheckBoxPreference
-            android:key="wide_viewport"
-            android:defaultValue="true"
-            android:title="@string/pref_development_viewport" />
+    <!-- The javascript console is enabled by default when the user has
+         also enabled debug mode by navigating to about:debug. -->
+    <CheckBoxPreference
+        android:key="javascript_console"
+        android:defaultValue="true"
+        android:title="@string/pref_development_error_console" />
                     
-        <CheckBoxPreference
-            android:key="normal_layout"
-            android:defaultValue="false"
-            android:title="@string/pref_development_normal_rendering" />       
-        
-        <CheckBoxPreference
-            android:key="enable_tracing"
-            android:defaultValue="false"
-            android:title="@string/pref_development_trace" />
+    <CheckBoxPreference
+        android:key="small_screen"
+        android:defaultValue="false"
+        android:title="@string/pref_development_single_column_rendering" />   
+
+    <CheckBoxPreference
+        android:key="wide_viewport"
+        android:defaultValue="true"
+        android:title="@string/pref_development_viewport" />
+                
+    <CheckBoxPreference
+        android:key="normal_layout"
+        android:defaultValue="false"
+        android:title="@string/pref_development_normal_rendering" />       
     
-        <CheckBoxPreference
-            android:key="enable_light_touch"
-            android:defaultValue="false"
-            android:title="Enable light touch" />
+    <CheckBoxPreference
+        android:key="enable_tracing"
+        android:defaultValue="false"
+        android:title="@string/pref_development_trace" />
 
-        <CheckBoxPreference
-            android:key="enable_nav_dump"
-            android:defaultValue="false"
-            android:title="@string/pref_development_nav_dump" />
+    <CheckBoxPreference
+        android:key="enable_light_touch"
+        android:defaultValue="false"
+        android:title="Enable light touch" />
 
-        <EditTextPreference
-            android:key="js_engine_flags"
-            android:title="@string/js_engine_flags"
-            android:singleLine="true" />
+    <CheckBoxPreference
+        android:key="enable_nav_dump"
+        android:defaultValue="false"
+        android:title="@string/pref_development_nav_dump" />
 
-        <ListPreference
-            android:key="user_agent"
-            android:title="@string/pref_development_uastring"
-            android:entries="@array/pref_development_ua_choices"
-            android:entryValues="@array/pref_development_ua_values"
-            android:defaultValue="0"/>
+    <EditTextPreference
+        android:key="js_engine_flags"
+        android:title="@string/js_engine_flags"
+        android:singleLine="true" />
 
-    </PreferenceCategory>
+    <ListPreference
+        android:key="user_agent"
+        android:title="@string/pref_development_uastring"
+        android:entries="@array/pref_development_ua_choices"
+        android:entryValues="@array/pref_development_ua_values"
+        android:defaultValue="0"/>
 
 </PreferenceScreen>
diff --git a/res/xml/page_content_preferences.xml b/res/xml/page_content_preferences.xml
new file mode 100644
index 0000000..84497dc
--- /dev/null
+++ b/res/xml/page_content_preferences.xml
@@ -0,0 +1,98 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2008 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<PreferenceScreen
+        xmlns:android="http://schemas.android.com/apk/res/android">
+
+    <ListPreference
+            android:key="text_size"
+            android:title="@string/pref_text_size"
+            android:defaultValue="NORMAL"
+            android:entries="@array/pref_text_size_choices"
+            android:entryValues="@array/pref_text_size_values"
+            android:dialogTitle="@string/pref_text_size_dialogtitle" />
+
+    <ListPreference
+            android:key="default_zoom"
+            android:title="@string/pref_default_zoom"
+            android:defaultValue="MEDIUM"
+            android:entries="@array/pref_default_zoom_choices"
+            android:entryValues="@array/pref_default_zoom_values"
+            android:dialogTitle="@string/pref_default_zoom_dialogtitle" />
+
+    <CheckBoxPreference
+            android:key="load_page"
+            android:defaultValue="true"
+            android:title="@string/pref_content_load_page"
+            android:summary="@string/pref_content_load_page_summary" />
+
+    <ListPreference
+            android:key="default_text_encoding"
+            android:title="@string/pref_default_text_encoding"
+            android:defaultValue="@string/pref_default_text_encoding_default"
+            android:entries="@array/pref_default_text_encoding_choices"
+            android:entryValues="@array/pref_default_text_encoding_values"
+            android:dialogTitle="@string/pref_default_text_encoding_dialogtitle" />
+
+    <CheckBoxPreference
+            android:key="block_popup_windows"
+            android:defaultValue="true"
+            android:title="@string/pref_content_block_popups" /> 
+
+    <CheckBoxPreference
+            android:key="load_images"
+            android:defaultValue="true"
+            android:title="@string/pref_content_load_images"
+            android:summary="@string/pref_content_load_images_summary" />   
+
+    <CheckBoxPreference
+            android:key="autofit_pages"
+            android:defaultValue="true"
+            android:title="@string/pref_content_autofit"
+            android:summary="@string/pref_content_autofit_summary" />  
+
+    <CheckBoxPreference
+            android:key="landscape_only"
+            android:defaultValue="false"
+            android:title="@string/pref_content_landscape_only"
+            android:summary="@string/pref_content_landscape_only_summary" />
+
+    <CheckBoxPreference
+            android:key="enable_javascript"
+            android:defaultValue="true"
+            android:title="@string/pref_content_javascript" />     
+
+    <ListPreference
+            android:key="plugin_state"
+            android:title="@string/pref_content_plugins"
+            android:defaultValue="ON"
+            android:entries="@array/pref_content_plugins_choices"
+            android:entryValues="@array/pref_content_plugins_values"
+            android:dialogTitle="@string/pref_content_plugins" />
+
+    <CheckBoxPreference
+            android:key="open_in_background"
+            android:defaultValue="false"
+            android:title="@string/pref_content_open_in_background"
+            android:summary="@string/pref_content_open_in_background_summary" />
+
+    <com.android.browser.BrowserHomepagePreference
+            android:key="homepage" 
+            android:title="@string/pref_content_homepage"
+            android:hint="@string/http"
+            android:inputType="textUri|textMultiLine" />
+
+</PreferenceScreen>
diff --git a/res/xml/personal_preferences.xml b/res/xml/personal_preferences.xml
new file mode 100644
index 0000000..939d14c
--- /dev/null
+++ b/res/xml/personal_preferences.xml
@@ -0,0 +1,35 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2008 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">
+
+    <Preference android:key="sync_with_chrome"
+        android:title="@string/pref_personal_sync_with_chrome"
+        android:summary="@string/pref_personal_sync_with_chrome_summary"
+    />
+
+    <CheckBoxPreference android:key="autofill_enabled"
+        android:title="@string/pref_autofill_enabled"
+        android:summary="@string/pref_autofill_enabled_summary"
+    />
+
+    <PreferenceScreen
+        android:fragment="com.android.browser.AutoFillSettingsFragment"
+        android:key="autofill_profile"
+        android:title="@string/pref_autofill_profile_editor"
+        android:summary="@string/pref_autofill_profile_editor_summary" />
+
+</PreferenceScreen>
diff --git a/res/xml/preference_headers.xml b/res/xml/preference_headers.xml
new file mode 100644
index 0000000..1a54990
--- /dev/null
+++ b/res/xml/preference_headers.xml
@@ -0,0 +1,38 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<preference-headers xmlns:android="http://schemas.android.com/apk/res/android">
+
+    <header android:fragment="com.android.browser.preferences.PageContentPreferencesFragment"
+        android:title="@string/pref_content_title"
+    />
+
+    <header android:fragment="com.android.browser.preferences.PersonalPreferencesFragment"
+        android:title="@string/pref_personal_title"
+    />
+
+    <header android:fragment="com.android.browser.preferences.PrivacyPreferencesFragment"
+        android:title="@string/pref_privacy_title"
+    />
+    
+    <header android:fragment="com.android.browser.preferences.SecurityPreferencesFragment"
+        android:title="@string/pref_security_title"
+    />
+
+    <header android:fragment="com.android.browser.preferences.AdvancedPreferencesFragment"
+        android:title="@string/pref_extras_title"
+    />
+</preference-headers>
diff --git a/res/xml/privacy_preferences.xml b/res/xml/privacy_preferences.xml
new file mode 100644
index 0000000..a6ea16b
--- /dev/null
+++ b/res/xml/privacy_preferences.xml
@@ -0,0 +1,79 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2008 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<PreferenceScreen
+        xmlns:android="http://schemas.android.com/apk/res/android">
+
+    <com.android.browser.BrowserYesNoPreference
+            android:key="privacy_clear_cache"
+            android:title="@string/pref_privacy_clear_cache"
+            android:summary="@string/pref_privacy_clear_cache_summary"
+            android:dialogMessage="@string/pref_privacy_clear_cache_dlg"
+            android:dialogTitle="@string/clear"
+            android:dialogIcon="@android:drawable/ic_dialog_alert" />
+
+    <com.android.browser.BrowserYesNoPreference
+            android:key="privacy_clear_history"
+            android:title="@string/pref_privacy_clear_history"
+            android:summary="@string/pref_privacy_clear_history_summary"
+            android:dialogMessage="@string/pref_privacy_clear_history_dlg"
+            android:dialogTitle="@string/clear"
+            android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+
+    <CheckBoxPreference
+            android:key="accept_cookies"
+            android:defaultValue="true"
+            android:title="@string/pref_security_accept_cookies"
+            android:summary="@string/pref_security_accept_cookies_summary" />
+
+    <com.android.browser.BrowserYesNoPreference
+            android:key="privacy_clear_cookies"
+            android:title="@string/pref_privacy_clear_cookies"
+            android:summary="@string/pref_privacy_clear_cookies_summary"
+            android:dialogMessage="@string/pref_privacy_clear_cookies_dlg"
+            android:dialogTitle="@string/clear"
+            android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+
+    <CheckBoxPreference
+            android:key="save_formdata"
+            android:defaultValue="true"
+            android:title="@string/pref_security_save_form_data"
+            android:summary="@string/pref_security_save_form_data_summary" />
+
+    <com.android.browser.BrowserYesNoPreference
+            android:key="privacy_clear_form_data"
+            android:title="@string/pref_privacy_clear_form_data"
+            android:summary="@string/pref_privacy_clear_form_data_summary"
+            android:dialogMessage="@string/pref_privacy_clear_form_data_dlg"
+            android:dialogTitle="@string/clear"
+            android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+
+    <CheckBoxPreference
+            android:key="enable_geolocation"
+            android:defaultValue="true"
+            android:title="@string/pref_privacy_enable_geolocation"
+            android:summary="@string/pref_privacy_enable_geolocation_summary" />
+
+    <com.android.browser.BrowserYesNoPreference
+            android:key="privacy_clear_geolocation_access"
+            android:dependency="enable_geolocation"
+            android:title="@string/pref_privacy_clear_geolocation_access"
+            android:summary="@string/pref_privacy_clear_geolocation_access_summary"
+            android:dialogMessage="@string/pref_privacy_clear_geolocation_access_dlg"
+            android:dialogTitle="@string/clear"
+            android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+
+</PreferenceScreen>
diff --git a/res/xml/security_preferences.xml b/res/xml/security_preferences.xml
new file mode 100644
index 0000000..8d4464b
--- /dev/null
+++ b/res/xml/security_preferences.xml
@@ -0,0 +1,40 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2008 The Android Open Source Project
+
+     Licensed under the Apache License, Version 2.0 (the "License");
+     you may not use this file except in compliance with the License.
+     You may obtain a copy of the License at
+
+          http://www.apache.org/licenses/LICENSE-2.0
+
+     Unless required by applicable law or agreed to in writing, software
+     distributed under the License is distributed on an "AS IS" BASIS,
+     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+     See the License for the specific language governing permissions and
+     limitations under the License.
+-->
+
+<PreferenceScreen
+        xmlns:android="http://schemas.android.com/apk/res/android">
+
+    <CheckBoxPreference
+            android:key="remember_passwords"
+            android:defaultValue="true"
+            android:title="@string/pref_security_remember_passwords"
+            android:summary="@string/pref_security_remember_passwords_summary" />
+
+    <com.android.browser.BrowserYesNoPreference
+            android:key="privacy_clear_passwords"
+            android:title="@string/pref_privacy_clear_passwords"
+            android:summary="@string/pref_privacy_clear_passwords_summary"
+            android:dialogMessage="@string/pref_privacy_clear_passwords_dlg" 
+            android:dialogTitle="@string/clear" 
+            android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+            
+    <CheckBoxPreference
+            android:key="show_security_warnings"
+            android:defaultValue="true"
+            android:title="@string/pref_security_show_security_warning"
+            android:summary="@string/pref_security_show_security_warning_summary" />
+
+</PreferenceScreen>
diff --git a/src/com/android/browser/ActiveTabsPage.java b/src/com/android/browser/ActiveTabsPage.java
index 2de7787..e450a99 100644
--- a/src/com/android/browser/ActiveTabsPage.java
+++ b/src/com/android/browser/ActiveTabsPage.java
@@ -20,6 +20,7 @@
 import android.graphics.Bitmap;
 import android.os.Handler;
 import android.util.AttributeSet;
+import android.util.Log;
 import android.view.KeyEvent;
 import android.view.LayoutInflater;
 import android.view.View;
@@ -32,6 +33,7 @@
 import android.widget.TextView;
 
 public class ActiveTabsPage extends LinearLayout {
+    private static final String LOGTAG = "TabPicker";
     private final BrowserActivity   mBrowserActivity;
     private final LayoutInflater    mFactory;
     private final TabControl        mControl;
@@ -51,12 +53,15 @@
                 public void onItemClick(AdapterView<?> parent, View view,
                         int position, long id) {
                     if (mControl.canCreateNewTab()) {
-                        position--;
+                        position -= 2;
                     }
                     boolean needToAttach = false;
-                    if (position == -1) {
+                    if (position == -2) {
                         // Create a new tab
                         mBrowserActivity.openTabToHomePage();
+                    } else if (position == -1) {
+                        // Create a new incognito tab
+                        mBrowserActivity.openIncognitoTab();
                     } else {
                         // Open the corresponding tab
                         // If the tab is the current one, switchToTab will
@@ -98,7 +103,7 @@
         public int getCount() {
             int count = mControl.getTabCount();
             if (mControl.canCreateNewTab()) {
-                count++;
+                count += 2;
             }
             // XXX: This is a workaround to be more like a real adapter. Most
             // adapters call notifyDataSetChanged() whenever the internal data
@@ -128,23 +133,28 @@
         }
         public int getItemViewType(int position) {
             if (mControl.canCreateNewTab()) {
-                position--;
+                position -= 2;
             }
             // Do not recycle the "add new tab" item.
-            return position == -1 ? IGNORE_ITEM_VIEW_TYPE : 1;
+            return position < 0 ? IGNORE_ITEM_VIEW_TYPE : 1;
         }
         public View getView(int position, View convertView, ViewGroup parent) {
             final int tabCount = mControl.getTabCount();
             if (mControl.canCreateNewTab()) {
-                position--;
+                position -= 2;
             }
 
             if (convertView == null) {
-                convertView = mFactory.inflate(position == -1 ?
-                        R.layout.tab_view_add_tab : R.layout.tab_view, null);
+                if (position == -2) {
+                    convertView = mFactory.inflate(R.layout.tab_view_add_tab, null);
+                } else if (position == -1) {
+                    convertView = mFactory.inflate(R.layout.tab_view_add_incognito_tab, null);
+                } else {
+                    convertView = mFactory.inflate(R.layout.tab_view, null);
+                }
             }
 
-            if (position != -1) {
+            if (position >= 0) {
                 TextView title =
                         (TextView) convertView.findViewById(R.id.title);
                 TextView url = (TextView) convertView.findViewById(R.id.url);
@@ -152,7 +162,19 @@
                         (ImageView) convertView.findViewById(R.id.favicon);
                 View close = convertView.findViewById(R.id.close);
                 Tab tab = mControl.getTab(position);
+                if (tab.getWebView() == null) {
+                    // This means that populatePickerData will have to use the
+                    // saved state.
+                    Log.w(LOGTAG, "Tab " + position + " has a null WebView and "
+                            + (tab.getSavedState() == null ? "null" : "non-null")
+                            + " saved state ");
+                }
                 tab.populatePickerData();
+                if (tab.getTitle() == null || tab.getTitle().length() == 0) {
+                    Log.w(LOGTAG, "Tab " + position + " has no title. "
+                            + "Check above in the Logs to see whether it has a "
+                            + "null WebView or null WebHistoryItem");
+                }
                 title.setText(tab.getTitle());
                 url.setText(tab.getUrl());
                 Bitmap icon = tab.getFavicon();
diff --git a/src/com/android/browser/AddBookmarkPage.java b/src/com/android/browser/AddBookmarkPage.java
index 594f985..1292bf6 100644
--- a/src/com/android/browser/AddBookmarkPage.java
+++ b/src/com/android/browser/AddBookmarkPage.java
@@ -16,32 +16,72 @@
 
 package com.android.browser;
 
+import com.android.browser.provider.BrowserProvider2;
+
 import android.app.Activity;
+import android.app.LoaderManager;
 import android.content.ContentResolver;
+import android.content.ContentUris;
+import android.content.ContentValues;
 import android.content.Context;
+import android.content.CursorLoader;
 import android.content.Intent;
+import android.content.Loader;
+import android.content.SharedPreferences;
 import android.content.res.Resources;
 import android.database.Cursor;
 import android.graphics.Bitmap;
 import android.net.ParseException;
+import android.net.Uri;
 import android.net.WebAddress;
 import android.os.Bundle;
 import android.os.Handler;
 import android.os.Message;
-import android.provider.Browser;
+import android.preference.PreferenceManager;
+import android.provider.BrowserContract;
+import android.text.TextUtils;
+import android.view.KeyEvent;
+import android.view.LayoutInflater;
+import android.view.MenuItem;
 import android.view.View;
+import android.view.ViewGroup;
 import android.view.Window;
+import android.view.WindowManager;
+import android.view.inputmethod.EditorInfo;
+import android.view.inputmethod.InputMethodManager;
+import android.widget.AdapterView;
+import android.widget.CursorAdapter;
 import android.widget.EditText;
+import android.widget.ListView;
+import android.widget.PopupMenu;
 import android.widget.TextView;
 import android.widget.Toast;
 
 import java.net.URI;
 import java.net.URISyntaxException;
-import java.util.Date;
+import java.util.ArrayList;
+import java.util.Stack;
 
-public class AddBookmarkPage extends Activity {
+public class AddBookmarkPage extends Activity
+        implements View.OnClickListener, TextView.OnEditorActionListener,
+        AdapterView.OnItemClickListener, LoaderManager.LoaderCallbacks<Cursor>,
+        BreadCrumbView.Controller, PopupMenu.OnMenuItemClickListener {
+
+    public static final long DEFAULT_FOLDER_ID = -1;
+    public static final String TOUCH_ICON_URL = "touch_icon_url";
+    // Place on an edited bookmark to remove the saved thumbnail
+    public static final String REMOVE_THUMBNAIL = "remove_thumbnail";
+    public static final String USER_AGENT = "user_agent";
+
+    private static final int MAX_CRUMBS_SHOWN = 2;
 
     private final String LOGTAG = "Bookmarks";
+    // Set to true to see the crash on the code I would like to run.
+    private final boolean DEBUG_CRASH = false;
+
+    // IDs for the CursorLoaders that are used.
+    private final int LOADER_ID_FOLDER_CONTENTS = 0;
+    private final int LOADER_ID_ALL_FOLDERS = 1;
 
     private EditText    mTitle;
     private EditText    mAddress;
@@ -50,72 +90,513 @@
     private boolean     mEditingExisting;
     private Bundle      mMap;
     private String      mTouchIconUrl;
-    private Bitmap      mThumbnail;
     private String      mOriginalUrl;
+    private TextView mFolder;
+    private View mDefaultView;
+    private View mFolderSelector;
+    private EditText mFolderNamer;
+    private View mAddNewFolder;
+    private View mAddSeparator;
+    private long mCurrentFolder = 0;
+    private FolderAdapter mAdapter;
+    private BreadCrumbView mCrumbs;
+    private TextView mFakeTitle;
+    private View mCrumbHolder;
+    private ListView mListView;
+    private boolean mSaveToHomeScreen;
+
+    private static class Folder {
+        String Name;
+        long Id;
+        Folder(String name, long id) {
+            Name = name;
+            Id = id;
+        }
+    }
 
     // Message IDs
     private static final int SAVE_BOOKMARK = 100;
+    private static final int TOUCH_ICON_DOWNLOADED = 101;
 
     private Handler mHandler;
 
-    private View.OnClickListener mSaveBookmark = new View.OnClickListener() {
-        public void onClick(View v) {
-            if (save()) {
-                finish();
+    private InputMethodManager getInputMethodManager() {
+        return (InputMethodManager) getSystemService(INPUT_METHOD_SERVICE);
+    }
+
+    @Override
+    public void onTop(int level, Object data) {
+        if (null == data) return;
+        Folder folderData = (Folder) data;
+        long folder = folderData.Id;
+        Uri uri = BrowserContract.Bookmarks.buildFolderUri(folder);
+        LoaderManager manager = getLoaderManager();
+        CursorLoader loader = (CursorLoader) ((Loader) manager.getLoader(
+                LOADER_ID_FOLDER_CONTENTS));
+        loader.setUri(uri);
+        loader.forceLoad();
+        updateVisible();
+        if (mFolderNamer.getVisibility() == View.VISIBLE) {
+            completeOrCancelFolderNaming(true);
+        }
+    }
+
+    /**
+     * Update the views shown to only show the two deepest levels of crumbs.
+     * Note that this method depends on internal knowledge of BreadCrumbView.
+     */
+    private void updateVisible() {
+      if (MAX_CRUMBS_SHOWN > 0) {
+          int invisibleCrumbs = mCrumbs.size() - MAX_CRUMBS_SHOWN;
+          // This class always uses a back button, which is the first child.
+          int childIndex = 1;
+          if (invisibleCrumbs > 0) {
+              int crumbIndex = 0;
+              while (crumbIndex < invisibleCrumbs) {
+                  // Set the crumb to GONE.
+                  mCrumbs.getChildAt(childIndex).setVisibility(View.GONE);
+                  childIndex++;
+                  // Each crumb is followed by a separator (except the last
+                  // one).  Also make it GONE
+                  mCrumbs.getChildAt(childIndex).setVisibility(View.GONE);
+                  childIndex++;
+                  // Move to the next crumb.
+                  crumbIndex++;
+              }
+          }
+          // Make sure the last two are visible.
+          int childCount = mCrumbs.getChildCount();
+          while (childIndex < childCount) {
+              mCrumbs.getChildAt(childIndex).setVisibility(View.VISIBLE);
+              childIndex++;
+          }
+      }
+    }
+
+    @Override
+    public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
+        if (v == mFolderNamer) {
+            if (v.getText().length() > 0) {
+                if (actionId == EditorInfo.IME_NULL) {
+                    // Only want to do this once.
+                    if (event.getAction() == KeyEvent.ACTION_UP) {
+                        completeOrCancelFolderNaming(false);
+                    }
+                }
+            }
+            // Steal the key press; otherwise a newline will be added
+            return true;
+        }
+        return false;
+    }
+
+    private void switchToDefaultView(boolean changedFolder) {
+        mFolderSelector.setVisibility(View.GONE);
+        mDefaultView.setVisibility(View.VISIBLE);
+        mCrumbHolder.setVisibility(View.GONE);
+        mFakeTitle.setVisibility(View.VISIBLE);
+        if (changedFolder) {
+            Object data = mCrumbs.getTopData();
+            if (data != null) {
+                Folder folder = (Folder) data;
+                mCurrentFolder = folder.Id;
+                mFolder.setText(folder.Name);
             }
         }
-    };
+    }
 
-    private View.OnClickListener mCancel = new View.OnClickListener() {
-        public void onClick(View v) {
-            finish();
+    @Override
+    public void onClick(View v) {
+        if (v == mButton) {
+            if (mFolderSelector.getVisibility() == View.VISIBLE) {
+                // We are showing the folder selector.
+                if (mFolderNamer.getVisibility() == View.VISIBLE) {
+                    completeOrCancelFolderNaming(false);
+                } else {
+                    // User has selected a folder.  Go back to the opening page
+                    mSaveToHomeScreen = false;
+                    switchToDefaultView(true);
+                }
+            } else if (save()) {
+                finish();
+            }
+        } else if (v == mCancelButton) {
+            if (mFolderNamer.getVisibility() == View.VISIBLE) {
+                completeOrCancelFolderNaming(true);
+            } else if (mFolderSelector.getVisibility() == View.VISIBLE) {
+                switchToDefaultView(false);
+            } else {
+                finish();
+            }
+        } else if (v == mFolder) {
+            // FIXME: We want to use mFolder as an anchor, but cannot until we
+            // fix the issue that the PopupMenu will not extend past the edge of
+            // the dialog.
+            PopupMenu popup = new PopupMenu(this, mFakeTitle);
+            popup.getMenuInflater().inflate(R.menu.folder_choice,
+                    popup.getMenu());
+            popup.setOnMenuItemClickListener(this);
+            popup.show();
+        } else if (v == mAddNewFolder) {
+            mFolderNamer.setVisibility(View.VISIBLE);
+            mFolderNamer.setText(R.string.new_folder);
+            mFolderNamer.requestFocus();
+            updateList();
+            mAddNewFolder.setVisibility(View.GONE);
+            mAddSeparator.setVisibility(View.GONE);
+            getInputMethodManager().showSoftInput(mFolderNamer,
+                    InputMethodManager.SHOW_IMPLICIT);
         }
-    };
+    }
+
+    @Override
+    public boolean onMenuItemClick(MenuItem item) {
+        switch(item.getItemId()) {
+            case R.id.bookmarks:
+                mCurrentFolder = getBookmarksBarId(this);
+                mFolder.setText(item.getTitle());
+                mSaveToHomeScreen = false;
+                break;
+            case R.id.home_screen:
+                // Create a short cut to the home screen
+                mSaveToHomeScreen = true;
+                mFolder.setText(item.getTitle());
+                break;
+            case R.id.other:
+                switchToFolderSelector();
+                break;
+            default:
+                return false;
+        }
+        return true;
+    }
+
+    // Refresh the ListView to hide or show the empty view, as necessary.
+    // Should be called after mFolderNamer is shown or hidden.
+    private void updateList() {
+        if (mAdapter.getCount() == 0) {
+            // XXX: Is there a better way to refresh the ListView?
+            mListView.setAdapter(mAdapter);
+        }
+    }
+
+    private void completeOrCancelFolderNaming(boolean cancel) {
+        if (!cancel && !TextUtils.isEmpty(mFolderNamer.getText())) {
+            String name = mFolderNamer.getText().toString();
+            long id = addFolderToCurrent(mFolderNamer.getText().toString());
+            descendInto(name, id);
+        }
+        mFolderNamer.setVisibility(View.GONE);
+        mAddNewFolder.setVisibility(View.VISIBLE);
+        mAddSeparator.setVisibility(View.VISIBLE);
+        getInputMethodManager().hideSoftInputFromWindow(
+                mFolderNamer.getWindowToken(), 0);
+        updateList();
+    }
+
+    private long addFolderToCurrent(String name) {
+        // Add the folder to the database
+        ContentValues values = new ContentValues();
+        values.put(BrowserContract.Bookmarks.TITLE,
+                name);
+        values.put(BrowserContract.Bookmarks.IS_FOLDER, 1);
+        long currentFolder;
+        Object data = mCrumbs.getTopData();
+        if (data != null) {
+            currentFolder = ((Folder) data).Id;
+        } else {
+            currentFolder = getBookmarksBarId(this);
+        }
+        values.put(BrowserContract.Bookmarks.PARENT, currentFolder);
+        Uri uri = getContentResolver().insert(
+                BrowserContract.Bookmarks.CONTENT_URI, values);
+        if (uri != null) {
+            return ContentUris.parseId(uri);
+        } else {
+            return -1;
+        }
+    }
+
+    private void switchToFolderSelector() {
+        mDefaultView.setVisibility(View.GONE);
+        mFolderSelector.setVisibility(View.VISIBLE);
+        mCrumbHolder.setVisibility(View.VISIBLE);
+        mFakeTitle.setVisibility(View.GONE);
+        mAddNewFolder.setVisibility(View.VISIBLE);
+        mAddSeparator.setVisibility(View.VISIBLE);
+    }
+
+    private void descendInto(String foldername, long id) {
+        if (id != DEFAULT_FOLDER_ID) {
+            mCrumbs.pushView(foldername, new Folder(foldername, id));
+            mCrumbs.notifyController();
+        }
+    }
+
+    @Override
+    public Loader<Cursor> onCreateLoader(int id, Bundle args) {
+        String[] projection;
+        switch (id) {
+            case LOADER_ID_ALL_FOLDERS:
+                projection = new String[] {
+                        BrowserContract.Bookmarks._ID,
+                        BrowserContract.Bookmarks.PARENT,
+                        BrowserContract.Bookmarks.TITLE,
+                        BrowserContract.Bookmarks.IS_FOLDER
+                };
+                return new CursorLoader(this,
+                        BrowserContract.Bookmarks.CONTENT_URI,
+                        projection,
+                        BrowserContract.Bookmarks.IS_FOLDER + " != 0",
+                        null,
+                        null);
+            case LOADER_ID_FOLDER_CONTENTS:
+                projection = new String[] {
+                        BrowserContract.Bookmarks._ID,
+                        BrowserContract.Bookmarks.TITLE,
+                        BrowserContract.Bookmarks.IS_FOLDER
+                };
+                return new CursorLoader(this,
+                        BrowserContract.Bookmarks.buildFolderUri(
+                        mCurrentFolder),
+                        projection,
+                        BrowserContract.Bookmarks.IS_FOLDER + " != 0",
+                        null,
+                        null);
+            default:
+                throw new AssertionError("Asking for nonexistant loader!");
+        }
+    }
+
+    @Override
+    public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
+        switch (loader.getId()) {
+            case LOADER_ID_FOLDER_CONTENTS:
+                mAdapter.changeCursor(cursor);
+                break;
+            case LOADER_ID_ALL_FOLDERS:
+                long parent = mCurrentFolder;
+                int idIndex = cursor.getColumnIndexOrThrow(
+                        BrowserContract.Bookmarks._ID);
+                int titleIndex = cursor.getColumnIndexOrThrow(
+                        BrowserContract.Bookmarks.TITLE);
+                int parentIndex = cursor.getColumnIndexOrThrow(
+                        BrowserContract.Bookmarks.PARENT);
+                Stack folderStack = new Stack();
+                while ((parent != BrowserProvider2.FIXED_ID_ROOT) &&
+                        (parent != 0)) {
+                    // First, find the folder corresponding to the current
+                    // folder
+                    if (!cursor.moveToFirst()) {
+                        throw new AssertionError("No folders in the database!");
+                    }
+                    long folder;
+                    do {
+                        folder = cursor.getLong(idIndex);
+                    } while (folder != parent && cursor.moveToNext());
+                    if (cursor.isAfterLast()) {
+                        throw new AssertionError("Folder(id=" + parent
+                                + ") holding this bookmark does not exist!");
+                    }
+                    String name = cursor.getString(titleIndex);
+                    if (parent == mCurrentFolder) {
+                        mFolder.setText(name);
+                    }
+                    folderStack.push(new Folder(name, parent));
+                    parent = cursor.getLong(parentIndex);
+                }
+                while (!folderStack.isEmpty()) {
+                    Folder thisFolder = (Folder) folderStack.pop();
+                    mCrumbs.pushView(thisFolder.Name, thisFolder);
+                }
+                getLoaderManager().stopLoader(LOADER_ID_ALL_FOLDERS);
+                updateVisible();
+                break;
+            default:
+                break;
+        }
+    }
+
+    @Override
+    public void onItemClick(AdapterView<?> parent, View view, int position,
+            long id) {
+        TextView tv = (TextView) view.findViewById(android.R.id.text1);
+        // Switch to the folder that was clicked on.
+        descendInto(tv.getText().toString(), id);
+    }
+
+    /**
+     * Shows a list of names of folders.
+     */
+    private class FolderAdapter extends CursorAdapter {
+        public FolderAdapter(Context context) {
+            super(context, null);
+        }
+
+        @Override
+        public void bindView(View view, Context context, Cursor cursor) {
+            ((TextView) view.findViewById(android.R.id.text1)).setText(
+                    cursor.getString(cursor.getColumnIndexOrThrow(
+                    BrowserContract.Bookmarks.TITLE)));
+        }
+
+        @Override
+        public View newView(Context context, Cursor cursor, ViewGroup parent) {
+            View view = LayoutInflater.from(context).inflate(
+                    R.layout.folder_list_item, null);
+            view.setBackgroundDrawable(context.getResources().
+                    getDrawable(android.R.drawable.list_selector_background));
+            return view;
+        }
+
+        @Override
+        public boolean isEmpty() {
+            // Do not show the empty view if the user is creating a new folder.
+            return super.isEmpty() && mFolderNamer.getVisibility() == View.GONE;
+        }
+    }
 
     protected void onCreate(Bundle icicle) {
         super.onCreate(icicle);
-        requestWindowFeature(Window.FEATURE_LEFT_ICON);
+        if (DEBUG_CRASH) {
+            requestWindowFeature(Window.FEATURE_NO_TITLE);
+        } else {
+            requestWindowFeature(Window.FEATURE_LEFT_ICON);
+        }
+
+        mMap = getIntent().getExtras();
+
         setContentView(R.layout.browser_add_bookmark);
-        setTitle(R.string.save_to_bookmarks);
-        getWindow().setFeatureDrawableResource(Window.FEATURE_LEFT_ICON, R.drawable.ic_list_bookmark);
-        
+
+        Window window = getWindow();
+        if (!DEBUG_CRASH) {
+            setTitle(R.string.bookmark_this_page);
+            window.setFeatureDrawableResource(Window.FEATURE_LEFT_ICON, R.drawable.ic_list_bookmark);
+        }
+
         String title = null;
         String url = null;
-        mMap = getIntent().getExtras();
+
+        mFakeTitle = (TextView) findViewById(R.id.fake_title);
+
         if (mMap != null) {
             Bundle b = mMap.getBundle("bookmark");
             if (b != null) {
                 mMap = b;
                 mEditingExisting = true;
-                setTitle(R.string.edit_bookmark);
+                mFakeTitle.setText(R.string.edit_bookmark);
+                if (!DEBUG_CRASH) {
+                    setTitle(R.string.bookmark_this_page);
+                }
+            } else {
+                int gravity = mMap.getInt("gravity", -1);
+                if (gravity != -1) {
+                    WindowManager.LayoutParams l = window.getAttributes();
+                    l.gravity = gravity;
+                    window.setAttributes(l);
+                }
             }
-            title = mMap.getString("title");
-            url = mOriginalUrl = mMap.getString("url");
-            mTouchIconUrl = mMap.getString("touch_icon_url");
-            mThumbnail = (Bitmap) mMap.getParcelable("thumbnail");
+            title = mMap.getString(BrowserContract.Bookmarks.TITLE);
+            url = mOriginalUrl = mMap.getString(BrowserContract.Bookmarks.URL);
+            mTouchIconUrl = mMap.getString(TOUCH_ICON_URL);
+            mCurrentFolder = mMap.getLong(BrowserContract.Bookmarks.PARENT, DEFAULT_FOLDER_ID);
+        }
+        if (mCurrentFolder == DEFAULT_FOLDER_ID) {
+            mCurrentFolder = getBookmarksBarId(this);
         }
 
         mTitle = (EditText) findViewById(R.id.title);
         mTitle.setText(title);
+
         mAddress = (EditText) findViewById(R.id.address);
         mAddress.setText(url);
 
-        View.OnClickListener accept = mSaveBookmark;
         mButton = (TextView) findViewById(R.id.OK);
-        mButton.setOnClickListener(accept);
+        mButton.setOnClickListener(this);
 
         mCancelButton = findViewById(R.id.cancel);
-        mCancelButton.setOnClickListener(mCancel);
-        
-        if (!getWindow().getDecorView().isInTouchMode()) {
+        mCancelButton.setOnClickListener(this);
+
+        mFolder = (TextView) findViewById(R.id.folder);
+        mFolder.setOnClickListener(this);
+
+        mDefaultView = findViewById(R.id.default_view);
+        mFolderSelector = findViewById(R.id.folder_selector);
+
+        mFolderNamer = (EditText) findViewById(R.id.folder_namer);
+        mFolderNamer.setOnEditorActionListener(this);
+
+        mAddNewFolder = findViewById(R.id.add_new_folder);
+        mAddNewFolder.setOnClickListener(this);
+        mAddSeparator = findViewById(R.id.add_divider);
+
+        mCrumbs = (BreadCrumbView) findViewById(R.id.crumbs);
+        mCrumbs.setUseBackButton(true);
+        mCrumbs.setController(this);
+        String name = getString(R.string.bookmarks);
+        mCrumbs.pushView(name, false,
+                new Folder(name, BrowserProvider2.FIXED_ID_ROOT));
+        mCrumbHolder = findViewById(R.id.crumb_holder);
+
+        mAdapter = new FolderAdapter(this);
+        mListView = (ListView) findViewById(R.id.list);
+        View empty = findViewById(R.id.empty);
+        mListView.setEmptyView(empty);
+        mListView.setAdapter(mAdapter);
+        mListView.setOnItemClickListener(this);
+        LoaderManager manager = getLoaderManager();
+        if (mCurrentFolder != BrowserProvider2.FIXED_ID_ROOT) {
+            // Find all the folders
+            manager.initLoader(LOADER_ID_ALL_FOLDERS, null, this);
+        }
+        // Find the contents of the current folder
+        manager.initLoader(LOADER_ID_FOLDER_CONTENTS, null, this);
+
+
+        if (!window.getDecorView().isInTouchMode()) {
             mButton.requestFocus();
         }
     }
 
+    // FIXME: Use a CursorLoader
+    private long getBookmarksBarId(Context context) {
+        SharedPreferences prefs
+                = PreferenceManager.getDefaultSharedPreferences(context);
+        String accountName =
+                prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+        String accountType =
+                prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+        if (TextUtils.isEmpty(accountName) || TextUtils.isEmpty(accountType)) {
+            return BrowserProvider2.FIXED_ID_ROOT;
+        }
+        Cursor cursor = null;
+        try {
+            cursor = context.getContentResolver().query(
+                    BrowserContract.Bookmarks.CONTENT_URI,
+                    new String[] { BrowserContract.Bookmarks._ID },
+                    BrowserContract.ChromeSyncColumns.SERVER_UNIQUE + "=? AND "
+                            + BrowserContract.Bookmarks.ACCOUNT_NAME + "=? AND "
+                            + BrowserContract.Bookmarks.ACCOUNT_TYPE + "=?",
+                    new String[] {
+                            BrowserContract.ChromeSyncColumns
+                                    .FOLDER_NAME_BOOKMARKS_BAR,
+                            accountName,
+                            accountType },
+                    null);
+            if (cursor != null && cursor.moveToFirst()) {
+                return cursor.getLong(0);
+            }
+        } finally {
+            if (cursor != null) cursor.close();
+        }
+        return BrowserProvider2.FIXED_ID_ROOT;
+    }
+
     /**
      * Runnable to save a bookmark, so it can be performed in its own thread.
      */
     private class SaveBookmarkRunnable implements Runnable {
+        // FIXME: This should be an async task.
         private Message mMessage;
         private Context mContext;
         public SaveBookmarkRunnable(Context ctx, Message msg) {
@@ -125,18 +606,18 @@
         public void run() {
             // Unbundle bookmark data.
             Bundle bundle = mMessage.getData();
-            String title = bundle.getString("title");
-            String url = bundle.getString("url");
-            boolean invalidateThumbnail = bundle.getBoolean(
-                    "invalidateThumbnail");
+            String title = bundle.getString(BrowserContract.Bookmarks.TITLE);
+            String url = bundle.getString(BrowserContract.Bookmarks.URL);
+            boolean invalidateThumbnail = bundle.getBoolean(REMOVE_THUMBNAIL);
             Bitmap thumbnail = invalidateThumbnail ? null
-                    : (Bitmap) bundle.getParcelable("thumbnail");
-            String touchIconUrl = bundle.getString("touchIconUrl");
+                    : (Bitmap) bundle.getParcelable(BrowserContract.Bookmarks.THUMBNAIL);
+            String touchIconUrl = bundle.getString(TOUCH_ICON_URL);
 
             // Save to the bookmarks DB.
             try {
                 final ContentResolver cr = getContentResolver();
-                Bookmarks.addBookmark(null, cr, url, title, thumbnail, true);
+                Bookmarks.addBookmark(AddBookmarkPage.this, false, url,
+                        title, thumbnail, true, mCurrentFolder);
                 if (touchIconUrl != null) {
                     new DownloadTouchIcon(mContext, cr, url).execute(mTouchIconUrl);
                 }
@@ -163,6 +644,15 @@
                                         Toast.LENGTH_LONG).show();
                             }
                             break;
+                        case TOUCH_ICON_DOWNLOADED:
+                            Bundle b = msg.getData();
+                            sendBroadcast(BookmarkUtils.createAddToHomeIntent(
+                                    AddBookmarkPage.this,
+                                    b.getString(BrowserContract.Bookmarks.URL),
+                                    b.getString(BrowserContract.Bookmarks.TITLE),
+                                    (Bitmap) b.getParcelable(BrowserContract.Bookmarks.TOUCH_ICON),
+                                    (Bitmap) b.getParcelable(BrowserContract.Bookmarks.FAVICON)));
+                            break;
                     }
                 }
             };
@@ -176,8 +666,9 @@
         createHandler();
 
         String title = mTitle.getText().toString().trim();
-        String unfilteredUrl = 
-                BrowserActivity.fixUrl(mAddress.getText().toString());
+        String unfilteredUrl;
+        unfilteredUrl = BrowserActivity.fixUrl(mAddress.getText().toString());
+
         boolean emptyTitle = title.length() == 0;
         boolean emptyUrl = unfilteredUrl.trim().length() == 0;
         Resources r = getResources();
@@ -189,6 +680,7 @@
                 mAddress.setError(r.getText(R.string.bookmark_needs_url));
             }
             return false;
+
         }
         String url = unfilteredUrl.trim();
         try {
@@ -212,7 +704,7 @@
                     } catch (ParseException e) {
                         throw new URISyntaxException("", "");
                     }
-                    if (address.mHost.length() == 0) {
+                    if (address.getHost().length() == 0) {
                         throw new URISyntaxException("", "");
                     }
                     url = address.toString();
@@ -223,28 +715,65 @@
             return false;
         }
 
+        if (mSaveToHomeScreen) {
+            mEditingExisting = false;
+        }
+
+        boolean urlUnmodified = url.equals(mOriginalUrl);
+
         if (mEditingExisting) {
-            mMap.putString("title", title);
-            mMap.putString("url", url);
-            mMap.putBoolean("invalidateThumbnail", !url.equals(mOriginalUrl));
+            mMap.putString(BrowserContract.Bookmarks.TITLE, title);
+            mMap.putString(BrowserContract.Bookmarks.URL, url);
+            mMap.putBoolean(REMOVE_THUMBNAIL, !urlUnmodified);
+            // FIXME: This does not work yet
+            mMap.putLong(BrowserContract.Bookmarks.PARENT, mCurrentFolder);
             setResult(RESULT_OK, (new Intent()).setAction(
                     getIntent().toString()).putExtras(mMap));
         } else {
-            // Post a message to write to the DB.
+            Bitmap thumbnail;
+            Bitmap favicon;
+            if (urlUnmodified) {
+                thumbnail = (Bitmap) mMap.getParcelable(
+                        BrowserContract.Bookmarks.THUMBNAIL);
+                favicon = (Bitmap) mMap.getParcelable(
+                        BrowserContract.Bookmarks.FAVICON);
+            } else {
+                thumbnail = null;
+                favicon = null;
+            }
+
             Bundle bundle = new Bundle();
-            bundle.putString("title", title);
-            bundle.putString("url", url);
-            bundle.putParcelable("thumbnail", mThumbnail);
-            bundle.putBoolean("invalidateThumbnail", !url.equals(mOriginalUrl));
-            bundle.putString("touchIconUrl", mTouchIconUrl);
-            Message msg = Message.obtain(mHandler, SAVE_BOOKMARK);
-            msg.setData(bundle);
-            // Start a new thread so as to not slow down the UI
-            Thread t = new Thread(new SaveBookmarkRunnable(getApplicationContext(), msg));
-            t.start();
+            bundle.putString(BrowserContract.Bookmarks.TITLE, title);
+            bundle.putString(BrowserContract.Bookmarks.URL, url);
+            bundle.putParcelable(BrowserContract.Bookmarks.FAVICON, favicon);
+
+            if (mSaveToHomeScreen) {
+                if (mTouchIconUrl != null && urlUnmodified) {
+                    Message msg = Message.obtain(mHandler,
+                            TOUCH_ICON_DOWNLOADED);
+                    msg.setData(bundle);
+                    DownloadTouchIcon icon = new DownloadTouchIcon(this, msg,
+                            mMap.getString(USER_AGENT));
+                    icon.execute(mTouchIconUrl);
+                } else {
+                    sendBroadcast(BookmarkUtils.createAddToHomeIntent(this, url,
+                            title, null /*touchIcon*/, favicon));
+                }
+            } else {
+                bundle.putParcelable(BrowserContract.Bookmarks.THUMBNAIL, thumbnail);
+                bundle.putBoolean(REMOVE_THUMBNAIL, !urlUnmodified);
+                bundle.putString(TOUCH_ICON_URL, mTouchIconUrl);
+                // Post a message to write to the DB.
+                Message msg = Message.obtain(mHandler, SAVE_BOOKMARK);
+                msg.setData(bundle);
+                // Start a new thread so as to not slow down the UI
+                Thread t = new Thread(new SaveBookmarkRunnable(getApplicationContext(), msg));
+                t.start();
+            }
             setResult(RESULT_OK);
             LogTag.logBookmarkAdded(url, "bookmarkview");
         }
         return true;
     }
+
 }
diff --git a/src/com/android/browser/AutoFillProfileDatabase.java b/src/com/android/browser/AutoFillProfileDatabase.java
new file mode 100644
index 0000000..3345e92
--- /dev/null
+++ b/src/com/android/browser/AutoFillProfileDatabase.java
@@ -0,0 +1,154 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.database.Cursor;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteOpenHelper;
+import android.provider.BaseColumns;
+import android.util.Log;
+import android.webkit.WebSettings.AutoFillProfile;
+
+public class AutoFillProfileDatabase {
+
+    static final String LOGTAG = "AutoFillProfileDatabase";
+
+    static final String DATABASE_NAME = "autofill.db";
+    static final int DATABASE_VERSION = 2;
+    static final String PROFILES_TABLE_NAME = "profiles";
+    private AutoFillProfileDatabaseHelper mOpenHelper;
+    private static AutoFillProfileDatabase sInstance;
+
+    public static final class Profiles implements BaseColumns {
+        private Profiles() { }
+
+        static final String FULL_NAME = "fullname";
+        static final String EMAIL_ADDRESS = "email";
+        static final String COMPANY_NAME = "companyname";
+        static final String ADDRESS_LINE_1 = "addressline1";
+        static final String ADDRESS_LINE_2 = "addressline2";
+        static final String CITY = "city";
+        static final String STATE = "state";
+        static final String ZIP_CODE = "zipcode";
+        static final String COUNTRY = "country";
+        static final String PHONE_NUMBER = "phone";
+    }
+
+    private static class AutoFillProfileDatabaseHelper extends SQLiteOpenHelper {
+        AutoFillProfileDatabaseHelper(Context context) {
+             super(context, DATABASE_NAME, null, DATABASE_VERSION);
+        }
+
+        @Override
+        public void onCreate(SQLiteDatabase db) {
+            db.execSQL("CREATE TABLE " + PROFILES_TABLE_NAME + " ("
+                    + Profiles._ID + " INTEGER PRIMARY KEY,"
+                    + Profiles.FULL_NAME + " TEXT,"
+                    + Profiles.EMAIL_ADDRESS + " TEXT,"
+                    + Profiles.COMPANY_NAME + " TEXT,"
+                    + Profiles.ADDRESS_LINE_1 + " TEXT,"
+                    + Profiles.ADDRESS_LINE_2 + " TEXT,"
+                    + Profiles.CITY + " TEXT,"
+                    + Profiles.STATE + " TEXT,"
+                    + Profiles.ZIP_CODE + " TEXT,"
+                    + Profiles.COUNTRY + " TEXT,"
+                    + Profiles.PHONE_NUMBER + " TEXT"
+                    + " );");
+        }
+
+        @Override
+        public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
+            Log.w(LOGTAG, "Upgrading database from version " + oldVersion + " to "
+                    + newVersion + ", which will destroy all old data");
+            db.execSQL("DROP TABLE IF EXISTS " + PROFILES_TABLE_NAME);
+            onCreate(db);
+        }
+    }
+
+    private AutoFillProfileDatabase(Context context) {
+        mOpenHelper = new AutoFillProfileDatabaseHelper(context);
+    }
+
+    public static AutoFillProfileDatabase getInstance(Context context) {
+        if (sInstance == null) {
+            sInstance = new AutoFillProfileDatabase(context);
+        }
+        return sInstance;
+    }
+
+    private SQLiteDatabase getDatabase(boolean writable) {
+        return writable ? mOpenHelper.getWritableDatabase() : mOpenHelper.getReadableDatabase();
+    }
+
+    public void addOrUpdateProfile(final int id, AutoFillProfile profile) {
+        final String sql = "INSERT OR REPLACE INTO " + PROFILES_TABLE_NAME + " ("
+                + Profiles._ID + ","
+                + Profiles.FULL_NAME + ","
+                + Profiles.EMAIL_ADDRESS + ","
+                + Profiles.COMPANY_NAME + ","
+                + Profiles.ADDRESS_LINE_1 + ","
+                + Profiles.ADDRESS_LINE_2 + ","
+                + Profiles.CITY + ","
+                + Profiles.STATE + ","
+                + Profiles.ZIP_CODE + ","
+                + Profiles.COUNTRY + ","
+                + Profiles.PHONE_NUMBER
+                + ") VALUES (?,?,?,?,?,?,?,?,?,?,?);";
+        final Object[] params = { id,
+                profile.getFullName(),
+                profile.getEmailAddress(),
+                profile.getCompanyName(),
+                profile.getAddressLine1(),
+                profile.getAddressLine2(),
+                profile.getCity(),
+                profile.getState(),
+                profile.getZipCode(),
+                profile.getCountry(),
+                profile.getPhoneNumber() };
+        getDatabase(true).execSQL(sql, params);
+    }
+
+    public Cursor getProfile(int id) {
+        final String[] cols = {
+                Profiles.FULL_NAME,
+                Profiles.EMAIL_ADDRESS,
+                Profiles.COMPANY_NAME,
+                Profiles.ADDRESS_LINE_1,
+                Profiles.ADDRESS_LINE_2,
+                Profiles.CITY,
+                Profiles.STATE,
+                Profiles.ZIP_CODE,
+                Profiles.COUNTRY,
+                Profiles.PHONE_NUMBER
+        };
+
+        final String[] selectArgs = { Integer.toString(id) };
+        return getDatabase(false).query(PROFILES_TABLE_NAME, cols, Profiles._ID + "=?", selectArgs,
+                null, null, null, "1");
+    }
+
+    public void dropProfile(int id) {
+        final String sql = "DELETE FROM " + PROFILES_TABLE_NAME +" WHERE " + Profiles._ID + " = ?;";
+        final Object[] params = { id };
+        getDatabase(true).execSQL(sql, params);
+    }
+
+    public void close() {
+        mOpenHelper.close();
+    }
+}
diff --git a/src/com/android/browser/AutoFillSettingsFragment.java b/src/com/android/browser/AutoFillSettingsFragment.java
new file mode 100644
index 0000000..06a4256
--- /dev/null
+++ b/src/com/android/browser/AutoFillSettingsFragment.java
@@ -0,0 +1,168 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Fragment;
+import android.os.Bundle;
+import android.os.Handler;
+import android.os.Message;
+import android.util.Log;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.View.OnClickListener;
+import android.view.LayoutInflater;
+import android.webkit.WebSettings.AutoFillProfile;
+import android.widget.Button;
+import android.widget.EditText;
+import android.widget.Toast;
+
+public class AutoFillSettingsFragment extends Fragment {
+
+    private static final String LOGTAG = "AutoFillSettingsFragment";
+
+    private EditText mFullNameEdit;
+    private EditText mEmailEdit;
+    private EditText mCompanyEdit;
+    private EditText mAddressLine1Edit;
+    private EditText mAddressLine2Edit;
+    private EditText mCityEdit;
+    private EditText mStateEdit;
+    private EditText mZipEdit;
+    private EditText mCountryEdit;
+    private EditText mPhoneEdit;
+
+    // Used to display toast after DB interactions complete.
+    private Handler mHandler;
+
+    private final static int PROFILE_SAVED_MSG = 100;
+    private final static int PROFILE_DELETED_MSG = 101;
+
+    // For now we support just one profile so it's safe to hardcode the
+    // id to 1 here. In the future this unique identifier will be set
+    // dynamically.
+    private int mUniqueId = 1;
+
+    public AutoFillSettingsFragment() {
+        mHandler = new Handler() {
+            @Override
+            public void handleMessage(Message msg) {
+                switch (msg.what) {
+                case PROFILE_SAVED_MSG:
+                    Toast.makeText(getActivity(), R.string.autofill_profile_successful_save,
+                            Toast.LENGTH_SHORT).show();
+                    break;
+
+                case PROFILE_DELETED_MSG:
+                    Toast.makeText(getActivity(), R.string.autofill_profile_successful_delete,
+                            Toast.LENGTH_SHORT).show();
+                    break;
+                }
+            }
+        };
+    }
+
+    @Override
+    public void onCreate(Bundle savedState) {
+        super.onCreate(savedState);
+    }
+
+    @Override
+    public View onCreateView(LayoutInflater inflater, ViewGroup container,
+            Bundle savedInstanceState) {
+        View v = inflater.inflate(R.layout.autofill_settings_fragment, container, false);
+
+        mFullNameEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_name_edit);
+        mEmailEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_email_address_edit);
+        mCompanyEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_company_name_edit);
+        mAddressLine1Edit = (EditText)v.findViewById(
+                R.id.autofill_profile_editor_address_line_1_edit);
+        mAddressLine2Edit = (EditText)v.findViewById(
+                R.id.autofill_profile_editor_address_line_2_edit);
+        mCityEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_city_edit);
+        mStateEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_state_edit);
+        mZipEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_zip_code_edit);
+        mCountryEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_country_edit);
+        mPhoneEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_phone_number_edit);
+
+        Button saveButton = (Button)v.findViewById(R.id.autofill_profile_editor_save_button);
+        saveButton.setOnClickListener(new OnClickListener() {
+            public void onClick(View button) {
+                AutoFillProfile newProfile = new AutoFillProfile(
+                        mUniqueId,
+                        mFullNameEdit.getText().toString(),
+                        mEmailEdit.getText().toString(),
+                        mCompanyEdit.getText().toString(),
+                        mAddressLine1Edit.getText().toString(),
+                        mAddressLine2Edit.getText().toString(),
+                        mCityEdit.getText().toString(),
+                        mStateEdit.getText().toString(),
+                        mZipEdit.getText().toString(),
+                        mCountryEdit.getText().toString(),
+                        mPhoneEdit.getText().toString());
+
+                BrowserSettings.getInstance().setAutoFillProfile(getActivity(), newProfile,
+                        mHandler.obtainMessage(PROFILE_SAVED_MSG));
+            }
+        });
+
+        Button deleteButton = (Button)v.findViewById(R.id.autofill_profile_editor_delete_button);
+        deleteButton.setOnClickListener(new OnClickListener() {
+            public void onClick(View button) {
+                // Clear the UI.
+                mFullNameEdit.setText("");
+                mEmailEdit.setText("");
+                mCompanyEdit.setText("");
+                mAddressLine1Edit.setText("");
+                mAddressLine2Edit.setText("");
+                mCityEdit.setText("");
+                mStateEdit.setText("");
+                mZipEdit.setText("");
+                mCountryEdit.setText("");
+                mPhoneEdit.setText("");
+
+                // Update browser settings and native with a null profile. This will
+                // trigger the current profile to get deleted from the DB.
+                BrowserSettings.getInstance().setAutoFillProfile(getActivity(), null,
+                        mHandler.obtainMessage(PROFILE_DELETED_MSG));
+            }
+        });
+
+       Button cancelButton = (Button)v.findViewById(R.id.autofill_profile_editor_cancel_button);
+       cancelButton.setOnClickListener(new OnClickListener() {
+           public void onClick(View button) {
+               getFragmentManager().popBackStack();
+           }
+        });
+
+        // Populate the text boxes with any pre existing AutoFill data.
+        AutoFillProfile activeProfile = BrowserSettings.getInstance().getAutoFillProfile();
+        if (activeProfile != null) {
+            mFullNameEdit.setText(activeProfile.getFullName());
+            mEmailEdit.setText(activeProfile.getEmailAddress());
+            mCompanyEdit.setText(activeProfile.getCompanyName());
+            mAddressLine1Edit.setText(activeProfile.getAddressLine1());
+            mAddressLine2Edit.setText(activeProfile.getAddressLine2());
+            mCityEdit.setText(activeProfile.getCity());
+            mStateEdit.setText(activeProfile.getState());
+            mZipEdit.setText(activeProfile.getZipCode());
+            mCountryEdit.setText(activeProfile.getCountry());
+            mPhoneEdit.setText(activeProfile.getPhoneNumber());
+        }
+
+        return v;
+    }
+}
diff --git a/src/com/android/browser/BookmarkUtils.java b/src/com/android/browser/BookmarkUtils.java
new file mode 100644
index 0000000..0fdad15
--- /dev/null
+++ b/src/com/android/browser/BookmarkUtils.java
@@ -0,0 +1,168 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.content.Intent;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.Paint;
+import android.graphics.Path;
+import android.graphics.PorterDuff;
+import android.graphics.PorterDuffXfermode;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.net.Uri;
+import android.provider.Browser;
+import android.util.Log;
+
+class BookmarkUtils {
+    private final static String LOGTAG = "BookmarkUtils";
+
+    // XXX: There is no public string defining this intent so if Home changes the value, we
+    // have to update this string.
+    private static final String INSTALL_SHORTCUT = "com.android.launcher.action.INSTALL_SHORTCUT";
+
+    enum BookmarkIconType {
+        ICON_INSTALLABLE_WEB_APP, // Icon for an installable web app (launches WebAppRuntime).
+        ICON_HOME_SHORTCUT        // Icon for a shortcut on the home screen (launches Browser).
+    };
+
+    /**
+     * Creates an icon to be associated with this bookmark. If available, the apple touch icon
+     * will be used, else we draw our own depending on the type of "bookmark" being created.
+     */
+    static Bitmap createIcon(Context context, Bitmap touchIcon, Bitmap favicon,
+            BookmarkIconType type) {
+        int iconDimension = context.getResources().getDimensionPixelSize(
+                android.R.dimen.app_icon_size);
+
+        Bitmap bm = Bitmap.createBitmap(iconDimension, iconDimension, Bitmap.Config.ARGB_8888);
+        Canvas canvas = new Canvas(bm);
+        Rect iconBounds = new Rect(0, 0, bm.getWidth(), bm.getHeight());
+
+        // Use the apple-touch-icon if available
+        if (touchIcon != null) {
+            drawTouchIconToCanvas(touchIcon, canvas, iconBounds);
+        } else {
+            // No touch icon so create our own.
+            // Set the background based on the type of shortcut (either webapp or home shortcut).
+            Bitmap icon = getIconBackground(context, type);
+
+            if (icon != null) {
+                // Now draw the correct icon background into our new bitmap.
+                canvas.drawBitmap(icon, null, iconBounds, null);
+            }
+
+            // If we have a favicon, overlay it in a nice rounded white box on top of the
+            // background.
+            if (favicon != null) {
+                drawFaviconToCanvas(favicon, canvas, iconBounds,
+                        context.getResources().getDisplayMetrics().density);
+            }
+        }
+        return bm;
+    }
+
+    /**
+     * Convenience method for creating an intent that will add a shortcut to the home screen.
+     */
+    static Intent createAddToHomeIntent(Context context, String url, String title,
+            Bitmap touchIcon, Bitmap favicon) {
+        Intent i = new Intent(INSTALL_SHORTCUT);
+        Intent shortcutIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
+        long urlHash = url.hashCode();
+        long uniqueId = (urlHash << 32) | shortcutIntent.hashCode();
+        shortcutIntent.putExtra(Browser.EXTRA_APPLICATION_ID, Long.toString(uniqueId));
+        i.putExtra(Intent.EXTRA_SHORTCUT_INTENT, shortcutIntent);
+        i.putExtra(Intent.EXTRA_SHORTCUT_NAME, title);
+        i.putExtra(Intent.EXTRA_SHORTCUT_ICON, createIcon(context, touchIcon, favicon,
+                BookmarkIconType.ICON_HOME_SHORTCUT));
+
+        // Do not allow duplicate items
+        i.putExtra("duplicate", false);
+        return i;
+    }
+
+    private static Bitmap getIconBackground(Context context, BookmarkIconType type) {
+        if (type == BookmarkIconType.ICON_HOME_SHORTCUT) {
+            // Want to create a shortcut icon on the homescreen, so the icon
+            // background is the red bookmark.
+            return BitmapFactory.decodeResource(context.getResources(),
+                    R.drawable.ic_launcher_shortcut_browser_bookmark);
+        } else if (type == BookmarkIconType.ICON_INSTALLABLE_WEB_APP) {
+            // Use the web browser icon as the background for the icon for an installable
+            // web app.
+            return BitmapFactory.decodeResource(context.getResources(),
+                    R.drawable.ic_launcher_browser);
+        }
+        return null;
+    }
+
+    private static void drawTouchIconToCanvas(Bitmap touchIcon, Canvas canvas, Rect iconBounds) {
+        Rect src = new Rect(0, 0, touchIcon.getWidth(), touchIcon.getHeight());
+
+        // Paint used for scaling the bitmap and drawing the rounded rect.
+        Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
+        paint.setFilterBitmap(true);
+        canvas.drawBitmap(touchIcon, src, iconBounds, paint);
+
+        // Construct a path from a round rect. This will allow drawing with
+        // an inverse fill so we can punch a hole using the round rect.
+        Path path = new Path();
+        path.setFillType(Path.FillType.INVERSE_WINDING);
+        RectF rect = new RectF(iconBounds);
+        rect.inset(1, 1);
+        path.addRoundRect(rect, 8f, 8f, Path.Direction.CW);
+
+        // Reuse the paint and clear the outside of the rectangle.
+        paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
+        canvas.drawPath(path, paint);
+    }
+
+    private static void drawFaviconToCanvas(Bitmap favicon, Canvas canvas, Rect iconBounds,
+            float density) {
+        // Make a Paint for the white background rectangle and for
+        // filtering the favicon.
+        Paint p = new Paint(Paint.ANTI_ALIAS_FLAG | Paint.FILTER_BITMAP_FLAG);
+        p.setStyle(Paint.Style.FILL_AND_STROKE);
+        p.setColor(Color.WHITE);
+
+        // Create a rectangle that is slightly wider than the favicon
+        final float iconSize = 16 * density; // 16x16 favicon
+        final float padding = 2 * density; // white padding around icon
+        final float rectSize = iconSize + 2 * padding;
+        final float x = iconBounds.exactCenterX() - (rectSize / 2);
+        // Note: Subtract 2 dip from the y position since the box is
+        // slightly higher than center. Use padding since it is already
+        // 2 * density.
+        final float y = iconBounds.exactCenterY() - (rectSize / 2) - padding;
+        RectF r = new RectF(x, y, x + rectSize, y + rectSize);
+
+        // Draw a white rounded rectangle behind the favicon
+        canvas.drawRoundRect(r, 2, 2, p);
+
+        // Draw the favicon in the same rectangle as the rounded
+        // rectangle but inset by the padding
+        // (results in a 16x16 favicon).
+        r.inset(padding, padding);
+        canvas.drawBitmap(favicon, null, r, p);
+    }
+
+};
diff --git a/src/com/android/browser/Bookmarks.java b/src/com/android/browser/Bookmarks.java
index 5ada9dc..383ae7f 100644
--- a/src/com/android/browser/Bookmarks.java
+++ b/src/com/android/browser/Bookmarks.java
@@ -20,16 +20,20 @@
 import android.content.ContentUris;
 import android.content.ContentValues;
 import android.content.Context;
+import android.content.SharedPreferences;
 import android.database.Cursor;
 import android.graphics.Bitmap;
 import android.net.Uri;
-import android.provider.Browser;
+import android.os.AsyncTask;
+import android.preference.PreferenceManager;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Combined;
+import android.provider.BrowserContract.Images;
 import android.util.Log;
 import android.webkit.WebIconDatabase;
 import android.widget.Toast;
 
 import java.io.ByteArrayOutputStream;
-import java.util.Date;
 
 /**
  *  This class is purely to have a common place for adding/deleting bookmarks.
@@ -53,89 +57,38 @@
      *  @param context Context of the calling Activity.  This is used to make
      *          Toast confirming that the bookmark has been added.  If the
      *          caller provides null, the Toast will not be shown.
-     *  @param cr The ContentResolver being used to add the bookmark to the db.
      *  @param url URL of the website to be bookmarked.
      *  @param name Provided name for the bookmark.
      *  @param thumbnail A thumbnail for the bookmark.
      *  @param retainIcon Whether to retain the page's icon in the icon database.
      *          This will usually be <code>true</code> except when bookmarks are
      *          added by a settings restore agent.
+     *  @param parent ID of the parent folder.
      */
-    /* package */ static void addBookmark(Context context,
-            ContentResolver cr, String url, String name,
-            Bitmap thumbnail, boolean retainIcon) {
+    /* package */ static void addBookmark(Context context, boolean showToast, String url,
+            String name, Bitmap thumbnail, boolean retainIcon, long parent) {
         // Want to append to the beginning of the list
-        long creationTime = new Date().getTime();
-        ContentValues map = new ContentValues();
-        Cursor cursor = null;
+        ContentValues values = new ContentValues();
         try {
-            cursor = Browser.getVisitedLike(cr, url);
-            if (cursor.moveToFirst() && cursor.getInt(
-                    Browser.HISTORY_PROJECTION_BOOKMARK_INDEX) == 0) {
-                // This means we have been to this site but not bookmarked
-                // it, so convert the history item to a bookmark
-                map.put(Browser.BookmarkColumns.CREATED, creationTime);
-                map.put(Browser.BookmarkColumns.TITLE, name);
-                map.put(Browser.BookmarkColumns.BOOKMARK, 1);
-                map.put(Browser.BookmarkColumns.THUMBNAIL,
-                        bitmapToBytes(thumbnail));
-                cr.update(Browser.BOOKMARKS_URI, map,
-                        "_id = " + cursor.getInt(0), null);
-            } else {
-                int count = cursor.getCount();
-                boolean matchedTitle = false;
-                for (int i = 0; i < count; i++) {
-                    // One or more bookmarks already exist for this site.
-                    // Check the names of each
-                    cursor.moveToPosition(i);
-                    if (cursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX)
-                            .equals(name)) {
-                        // The old bookmark has the same name.
-                        // Update its creation time.
-                        map.put(Browser.BookmarkColumns.CREATED,
-                                creationTime);
-                        cr.update(Browser.BOOKMARKS_URI, map,
-                                "_id = " + cursor.getInt(0), null);
-                        matchedTitle = true;
-                        break;
-                    }
-                }
-                if (!matchedTitle) {
-                    // Adding a bookmark for a site the user has visited,
-                    // or a new bookmark (with a different name) for a site
-                    // the user has visited
-                    map.put(Browser.BookmarkColumns.TITLE, name);
-                    map.put(Browser.BookmarkColumns.URL, url);
-                    map.put(Browser.BookmarkColumns.CREATED, creationTime);
-                    map.put(Browser.BookmarkColumns.BOOKMARK, 1);
-                    map.put(Browser.BookmarkColumns.DATE, 0);
-                    map.put(Browser.BookmarkColumns.THUMBNAIL,
-                            bitmapToBytes(thumbnail));
-                    int visits = 0;
-                    if (count > 0) {
-                        // The user has already bookmarked, and possibly
-                        // visited this site.  However, they are creating
-                        // a new bookmark with the same url but a different
-                        // name.  The new bookmark should have the same
-                        // number of visits as the already created bookmark.
-                        visits = cursor.getInt(
-                                Browser.HISTORY_PROJECTION_VISITS_INDEX);
-                    }
-                    // Bookmark starts with 3 extra visits so that it will
-                    // bubble up in the most visited and goto search box
-                    map.put(Browser.BookmarkColumns.VISITS, visits + 3);
-                    cr.insert(Browser.BOOKMARKS_URI, map);
-                }
-            }
+            SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
+            String accountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+            String accountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+            values.put(BrowserContract.Bookmarks.ACCOUNT_TYPE, accountType);
+            values.put(BrowserContract.Bookmarks.ACCOUNT_NAME, accountName);
+            values.put(BrowserContract.Bookmarks.TITLE, name);
+            values.put(BrowserContract.Bookmarks.URL, url);
+            values.put(BrowserContract.Bookmarks.IS_FOLDER, 0);
+            values.put(BrowserContract.Bookmarks.THUMBNAIL,
+                    bitmapToBytes(thumbnail));
+            values.put(BrowserContract.Bookmarks.PARENT, parent);
+            context.getContentResolver().insert(BrowserContract.Bookmarks.CONTENT_URI, values);
         } catch (IllegalStateException e) {
             Log.e(LOGTAG, "addBookmark", e);
-        } finally {
-            if (cursor != null) cursor.close();
         }
         if (retainIcon) {
             WebIconDatabase.getInstance().retainIconForPageUrl(url);
         }
-        if (context != null) {
+        if (showToast) {
             Toast.makeText(context, R.string.added_to_bookmarks,
                     Toast.LENGTH_LONG).show();
         }
@@ -155,40 +108,26 @@
             ContentResolver cr, String url, String title) {
         Cursor cursor = null;
         try {
-            cursor = cr.query(
-                    Browser.BOOKMARKS_URI,
-                    Browser.HISTORY_PROJECTION,
-                    "url = ? AND title = ?",
+            cursor = cr.query(BrowserContract.Bookmarks.CONTENT_URI,
+                    new String[] { BrowserContract.Bookmarks._ID },
+                    BrowserContract.Bookmarks.URL + " = ? AND " +
+                            BrowserContract.Bookmarks.TITLE + " = ?",
                     new String[] { url, title },
                     null);
-            boolean first = cursor.moveToFirst();
+
             // Should be in the database no matter what
-            if (!first) {
+            if (!cursor.moveToFirst()) {
                 throw new AssertionError("URL is not in the database! " + url
                         + " " + title);
             }
+
             // Remove from bookmarks
             WebIconDatabase.getInstance().releaseIconForPageUrl(url);
-            Uri uri = ContentUris.withAppendedId(Browser.BOOKMARKS_URI,
-                    cursor.getInt(Browser.HISTORY_PROJECTION_ID_INDEX));
-            int numVisits = cursor.getInt(
-                    Browser.HISTORY_PROJECTION_VISITS_INDEX);
-            if (0 == numVisits) {
-                cr.delete(uri, null, null);
-            } else {
-                // It is no longer a bookmark, but it is still a visited
-                // site.
-                ContentValues values = new ContentValues();
-                values.put(Browser.BookmarkColumns.BOOKMARK, 0);
-                try {
-                    cr.update(uri, values, null, null);
-                } catch (IllegalStateException e) {
-                    Log.e("removeFromBookmarks", "no database!");
-                }
-            }
+            Uri uri = ContentUris.withAppendedId(BrowserContract.Bookmarks.CONTENT_URI,
+                    cursor.getLong(0));
+            cr.delete(uri, null, null);
             if (context != null) {
-                Toast.makeText(context, R.string.removed_from_bookmarks,
-                        Toast.LENGTH_LONG).show();
+                Toast.makeText(context, R.string.removed_from_bookmarks, Toast.LENGTH_LONG).show();
             }
         } catch (IllegalStateException e) {
             Log.e(LOGTAG, "removeFromBookmarks", e);
@@ -219,4 +158,86 @@
         }
         return false;
     }
+
+    static final String QUERY_BOOKMARKS_WHERE =
+            Combined.URL + " == ? OR " +
+            Combined.URL + " == ? OR " +
+            Combined.URL + " LIKE ? || '%' OR " +
+            Combined.URL + " LIKE ? || '%'";
+
+    /* package */ static Cursor queryCombinedForUrl(ContentResolver cr,
+            String originalUrl, String url) {
+        if (cr == null || url == null) {
+            return null;
+        }
+    
+        // If originalUrl is null, just set it to url.
+        if (originalUrl == null) {
+            originalUrl = url;
+        }
+    
+        // Look for both the original url and the actual url. This takes in to
+        // account redirects.
+        String originalUrlNoQuery = removeQuery(originalUrl);
+        String urlNoQuery = removeQuery(url);
+        originalUrl = originalUrlNoQuery + '?';
+        url = urlNoQuery + '?';
+    
+        // Use NoQuery to search for the base url (i.e. if the url is
+        // http://www.yahoo.com/?rs=1, search for http://www.yahoo.com)
+        // Use url to match the base url with other queries (i.e. if the url is
+        // http://www.google.com/m, search for
+        // http://www.google.com/m?some_query)
+        final String[] selArgs = new String[] { originalUrlNoQuery, urlNoQuery, originalUrl, url };
+        final String[] projection = new String[] { Combined.URL };
+        return cr.query(Combined.CONTENT_URI, projection, QUERY_BOOKMARKS_WHERE, selArgs, null);
+    }
+
+    // Strip the query from the given url.
+    static String removeQuery(String url) {
+        if (url == null) {
+            return null;
+        }
+        int query = url.indexOf('?');
+        String noQuery = url;
+        if (query != -1) {
+            noQuery = url.substring(0, query);
+        }
+        return noQuery;
+    }
+
+    /**
+     * Update the bookmark's favicon. This is a convenience method for updating
+     * a bookmark favicon for the originalUrl and url of the passed in WebView.
+     * @param cr The ContentResolver to use.
+     * @param originalUrl The original url before any redirects.
+     * @param url The current url.
+     * @param favicon The favicon bitmap to write to the db.
+     */
+    /* package */ static void updateFavicon(final ContentResolver cr,
+            final String originalUrl, final String url, final Bitmap favicon) {
+        new AsyncTask<Void, Void, Void>() {
+            @Override
+            protected Void doInBackground(Void... unused) {
+                Cursor cursor = queryCombinedForUrl(cr, originalUrl, url);
+                try {
+                    if (cursor.moveToFirst()) {
+                        final ByteArrayOutputStream os = new ByteArrayOutputStream();
+                        favicon.compress(Bitmap.CompressFormat.PNG, 100, os);
+
+                        ContentValues values = new ContentValues();
+                        values.put(Images.FAVICON, os.toByteArray());
+                        values.put(Images.URL, cursor.getString(0));
+
+                        do {
+                            cr.update(Images.CONTENT_URI, values, null, null);
+                        } while (cursor.moveToNext());
+                    }
+                } finally {
+                    if (cursor != null) cursor.close();
+                }
+                return null;
+            }
+        }.execute();
+    }
 }
diff --git a/src/com/android/browser/BookmarksLoader.java b/src/com/android/browser/BookmarksLoader.java
new file mode 100644
index 0000000..770ca60
--- /dev/null
+++ b/src/com/android/browser/BookmarksLoader.java
@@ -0,0 +1,72 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.content.CursorLoader;
+import android.net.Uri;
+import android.provider.BrowserContract.Bookmarks;
+import android.text.TextUtils;
+
+public class BookmarksLoader extends CursorLoader {
+    public static final String ARG_ACCOUNT_TYPE = "acct_type";
+    public static final String ARG_ACCOUNT_NAME = "acct_name";
+
+    public static final int COLUMN_INDEX_ID = 0;
+    public static final int COLUMN_INDEX_URL = 1;
+    public static final int COLUMN_INDEX_TITLE = 2;
+    public static final int COLUMN_INDEX_FAVICON = 3;
+    public static final int COLUMN_INDEX_THUMBNAIL = 4;
+    public static final int COLUMN_INDEX_TOUCH_ICON = 5;
+    public static final int COLUMN_INDEX_IS_FOLDER = 6;
+    public static final int COLUMN_INDEX_PARENT = 8;
+
+    public static final String[] PROJECTION = new String[] {
+        Bookmarks._ID, // 0
+        Bookmarks.URL, // 1
+        Bookmarks.TITLE, // 2
+        Bookmarks.FAVICON, // 3
+        Bookmarks.THUMBNAIL, // 4
+        Bookmarks.TOUCH_ICON, // 5
+        Bookmarks.IS_FOLDER, // 6
+        Bookmarks.POSITION, // 7
+        Bookmarks.PARENT, // 8
+    };
+
+    private String mAccountType;
+    private String mAccountName;
+
+    public BookmarksLoader(Context context, String accountType, String accountName) {
+        super(context, addAccount(Bookmarks.CONTENT_URI_DEFAULT_FOLDER, accountType, accountName),
+                PROJECTION, null, null, null);
+        mAccountType = accountType;
+        mAccountName = accountName;
+    }
+
+    @Override
+    public void setUri(Uri uri) {
+        super.setUri(addAccount(uri, mAccountType, mAccountName));
+    }
+
+    private static Uri addAccount(Uri uri, String accountType, String accountName) {
+        if (!TextUtils.isEmpty(accountType) && !TextUtils.isEmpty(accountName)) {
+            return uri.buildUpon().appendQueryParameter(Bookmarks.PARAM_ACCOUNT_TYPE, accountType).
+                    appendQueryParameter(Bookmarks.PARAM_ACCOUNT_NAME, accountName).build();
+        }
+        return uri;
+    }
+}
diff --git a/src/com/android/browser/BreadCrumbView.java b/src/com/android/browser/BreadCrumbView.java
new file mode 100644
index 0000000..4939b48
--- /dev/null
+++ b/src/com/android/browser/BreadCrumbView.java
@@ -0,0 +1,299 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.graphics.drawable.Drawable;
+import android.text.TextUtils;
+import android.util.AttributeSet;
+import android.view.Gravity;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.widget.ImageButton;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Simple bread crumb view
+ * Use setController to receive callbacks from user interactions
+ * Use pushView, popView, clear, and getTopData to change/access the view stack
+ */
+public class BreadCrumbView extends LinearLayout implements OnClickListener {
+
+    interface Controller {
+        public void onTop(int level, Object data);
+    }
+
+    private ImageButton mBackButton;
+    private Controller mController;
+    private List<Crumb> mCrumbs;
+    private boolean mUseBackButton;
+    private Drawable mSeparatorDrawable;
+
+    /**
+     * @param context
+     * @param attrs
+     * @param defStyle
+     */
+    public BreadCrumbView(Context context, AttributeSet attrs, int defStyle) {
+        super(context, attrs, defStyle);
+        init(context);
+    }
+
+    /**
+     * @param context
+     * @param attrs
+     */
+    public BreadCrumbView(Context context, AttributeSet attrs) {
+        super(context, attrs);
+        init(context);
+    }
+
+    /**
+     * @param context
+     */
+    public BreadCrumbView(Context context) {
+        super(context);
+        init(context);
+    }
+
+    private void init(Context ctx) {
+        mUseBackButton = false;
+        mCrumbs = new ArrayList<Crumb>();
+        mSeparatorDrawable = ctx.getResources().getDrawable(
+                R.drawable.crumb_divider);
+    }
+
+    public void setUseBackButton(boolean useflag) {
+        mUseBackButton = useflag;
+        if (mUseBackButton && (mBackButton == null)) {
+            addBackButton();
+        } else if (!mUseBackButton && (mBackButton != null)) {
+            removeView(mBackButton);
+            mBackButton = null;
+        }
+    }
+
+    public void setController(Controller ctl) {
+        mController = ctl;
+    }
+
+    public Object getTopData() {
+        Crumb c = getTopCrumb();
+        if (c != null) {
+            return c.data;
+        }
+        return null;
+    }
+
+    public int size() {
+        return mCrumbs.size();
+    }
+
+    public void clear() {
+        while (mCrumbs.size() > 1) {
+            pop(false);
+        }
+        pop(true);
+    }
+
+    public void notifyController() {
+        if (mController != null) {
+            if (mCrumbs.size() > 0) {
+                mController.onTop(mCrumbs.size(), getTopCrumb().data);
+            } else {
+                mController.onTop(0, null);
+            }
+        }
+    }
+
+    public void pushView(String name, Object data) {
+        pushView(name, true, data);
+    }
+
+    public void pushView(String name, boolean canGoBack, Object data) {
+        Crumb crumb = new Crumb(name, canGoBack, data);
+        pushCrumb(crumb);
+    }
+
+    public void pushView(View view, Object data) {
+        Crumb crumb = new Crumb(view, true, data);
+        pushCrumb(crumb);
+    }
+
+    public void popView() {
+        pop(true);
+    }
+
+    private void addBackButton() {
+        mBackButton = new ImageButton(mContext);
+        mBackButton.setImageResource(R.drawable.ic_back_normal);
+        mBackButton.setBackgroundResource(R.drawable.browserbarbutton);
+        mBackButton.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT,
+                LayoutParams.MATCH_PARENT));
+        mBackButton.setOnClickListener(this);
+        mBackButton.setVisibility(View.INVISIBLE);
+        addView(mBackButton, 0);
+    }
+
+    private void pushCrumb(Crumb crumb) {
+        if (!mUseBackButton || (mCrumbs.size() > 0)) {
+            addSeparator();
+        }
+        mCrumbs.add(crumb);
+        addView(crumb.crumbView);
+        if (mUseBackButton) {
+            mBackButton.setVisibility(crumb.canGoBack ? View.VISIBLE : View.INVISIBLE);
+        }
+        crumb.crumbView.setOnClickListener(this);
+    }
+
+    private void addSeparator() {
+        ImageView sep = new ImageView(mContext);
+        sep.setImageDrawable(mSeparatorDrawable);
+        sep.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT,
+                LayoutParams.MATCH_PARENT));
+        addView(sep);
+    }
+
+    private void pop(boolean notify) {
+        int n = mCrumbs.size();
+        if (n > 0) {
+            removeLastView();
+            if (!mUseBackButton || (n > 1)) {
+                // remove separator
+                removeLastView();
+            }
+            mCrumbs.remove(n - 1);
+            if (mUseBackButton) {
+                Crumb top = getTopCrumb();
+                if (top != null && top.canGoBack) {
+                    mBackButton.setVisibility(View.VISIBLE);
+                } else {
+                    mBackButton.setVisibility(View.INVISIBLE);
+                }
+            }
+            if (notify) {
+                notifyController();
+            }
+        }
+    }
+
+    private void removeLastView() {
+        int ix = getChildCount();
+        if (ix > 0) {
+            removeViewAt(ix-1);
+        }
+    }
+
+    private Crumb getTopCrumb() {
+        Crumb crumb = null;
+        if (mCrumbs.size() > 0) {
+            crumb = mCrumbs.get(mCrumbs.size() - 1);
+        }
+        return crumb;
+    }
+
+    @Override
+    public void onClick(View v) {
+        if (mBackButton == v) {
+            popView();
+            notifyController();
+        } else {
+            // pop until view matches crumb view
+            while (v != getTopCrumb().crumbView) {
+                pop(false);
+            }
+            notifyController();
+        }
+    }
+    @Override
+    public int getBaseline() {
+        int ix = getChildCount();
+        if (ix > 0) {
+            // If there is at least one crumb, the baseline will be its
+            // baseline.
+            return getChildAt(ix-1).getBaseline();
+        }
+        return super.getBaseline();
+    }
+
+    @Override
+    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
+        int height = mSeparatorDrawable.getIntrinsicHeight();
+        if (mMeasuredHeight < height) {
+            // This should only be an issue if there are currently no separators
+            // showing; i.e. if there is one crumb and no back button.
+            int mode = View.MeasureSpec.getMode(heightMeasureSpec);
+            switch(mode) {
+                case View.MeasureSpec.AT_MOST:
+                    if (View.MeasureSpec.getSize(heightMeasureSpec) < height) {
+                        return;
+                    }
+                    break;
+                case View.MeasureSpec.EXACTLY:
+                    return;
+                default:
+                    break;
+            }
+            setMeasuredDimension(mMeasuredWidth, height);
+        }
+    }
+
+    class Crumb {
+
+        public View crumbView;
+        public boolean canGoBack;
+        public Object data;
+
+        public Crumb(String title, boolean backEnabled, Object tag) {
+            init(makeCrumbView(title), backEnabled, tag);
+        }
+
+        public Crumb(View view, boolean backEnabled, Object tag) {
+            init(view, backEnabled, tag);
+        }
+
+        private void init(View view, boolean back, Object tag) {
+            canGoBack = back;
+            crumbView = view;
+            data = tag;
+        }
+
+        private TextView makeCrumbView(String name) {
+            TextView tv = new TextView(mContext);
+            tv.setTextAppearance(mContext, android.R.style.TextAppearance_Medium);
+            tv.setPadding(16, 0, 16, 0);
+            tv.setGravity(Gravity.CENTER_VERTICAL);
+            tv.setText(name);
+            tv.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT,
+                    LayoutParams.MATCH_PARENT));
+            tv.setMaxWidth(mContext.getResources().getInteger(
+                    R.integer.max_width_crumb));
+            tv.setMaxLines(1);
+            tv.setEllipsize(TextUtils.TruncateAt.END);
+            return tv;
+        }
+
+    }
+
+}
diff --git a/src/com/android/browser/BrowserActivity.java b/src/com/android/browser/BrowserActivity.java
index 0a3fec9..4115b92 100644
--- a/src/com/android/browser/BrowserActivity.java
+++ b/src/com/android/browser/BrowserActivity.java
@@ -16,36 +16,40 @@
 
 package com.android.browser;
 
+import com.android.browser.ScrollWebView.ScrollListener;
+import com.android.browser.search.SearchEngine;
+import com.android.common.Search;
+import com.android.common.speech.LoggingEvents;
+
+import android.app.ActionBar;
 import android.app.Activity;
 import android.app.AlertDialog;
+import android.app.Dialog;
 import android.app.DownloadManager;
 import android.app.ProgressDialog;
 import android.app.SearchManager;
 import android.content.ActivityNotFoundException;
 import android.content.BroadcastReceiver;
+import android.content.ClipboardManager;
 import android.content.ComponentName;
 import android.content.ContentProvider;
 import android.content.ContentProviderClient;
 import android.content.ContentResolver;
-import android.content.ContentUris;
 import android.content.ContentValues;
 import android.content.Context;
 import android.content.DialogInterface;
 import android.content.Intent;
 import android.content.IntentFilter;
-import android.content.pm.PackageInfo;
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.content.res.Configuration;
 import android.content.res.Resources;
 import android.database.Cursor;
-import android.database.DatabaseUtils;
 import android.graphics.Bitmap;
 import android.graphics.BitmapFactory;
 import android.graphics.Canvas;
 import android.graphics.Picture;
 import android.graphics.PixelFormat;
-import android.graphics.Rect;
 import android.graphics.drawable.Drawable;
 import android.net.ConnectivityManager;
 import android.net.NetworkInfo;
@@ -61,83 +65,72 @@
 import android.os.Message;
 import android.os.PowerManager;
 import android.os.Process;
-import android.os.ServiceManager;
 import android.os.SystemClock;
 import android.provider.Browser;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Images;
 import android.provider.ContactsContract;
 import android.provider.ContactsContract.Intents.Insert;
 import android.provider.Downloads;
 import android.provider.MediaStore;
 import android.speech.RecognizerResultsIntent;
-import android.text.IClipboard;
 import android.text.TextUtils;
 import android.text.format.DateFormat;
-import android.util.AttributeSet;
 import android.util.Log;
 import android.util.Patterns;
+import android.view.ActionMode;
 import android.view.ContextMenu;
+import android.view.ContextMenu.ContextMenuInfo;
 import android.view.Gravity;
 import android.view.KeyEvent;
 import android.view.LayoutInflater;
 import android.view.Menu;
 import android.view.MenuInflater;
 import android.view.MenuItem;
+import android.view.MenuItem.OnMenuItemClickListener;
 import android.view.View;
 import android.view.ViewGroup;
 import android.view.Window;
 import android.view.WindowManager;
-import android.view.ContextMenu.ContextMenuInfo;
-import android.view.MenuItem.OnMenuItemClickListener;
+import android.view.accessibility.AccessibilityManager;
 import android.webkit.CookieManager;
 import android.webkit.CookieSyncManager;
 import android.webkit.DownloadListener;
 import android.webkit.HttpAuthHandler;
-import android.webkit.PluginManager;
 import android.webkit.SslErrorHandler;
 import android.webkit.URLUtil;
 import android.webkit.ValueCallback;
 import android.webkit.WebChromeClient;
 import android.webkit.WebHistoryItem;
 import android.webkit.WebIconDatabase;
+import android.webkit.WebSettings;
 import android.webkit.WebView;
 import android.widget.EditText;
 import android.widget.FrameLayout;
 import android.widget.LinearLayout;
 import android.widget.TextView;
 import android.widget.Toast;
-import android.accounts.Account;
-import android.accounts.AccountManager;
-import android.accounts.AccountManagerFuture;
-import android.accounts.AuthenticatorException;
-import android.accounts.OperationCanceledException;
-import android.accounts.AccountManagerCallback;
-
-import com.android.browser.search.SearchEngine;
-import com.android.common.Search;
-import com.android.common.speech.LoggingEvents;
 
 import java.io.ByteArrayOutputStream;
 import java.io.File;
 import java.io.IOException;
 import java.io.InputStream;
 import java.net.MalformedURLException;
-import java.net.URI;
 import java.net.URISyntaxException;
 import java.net.URL;
 import java.net.URLEncoder;
-import java.text.ParseException;
+import java.util.Calendar;
 import java.util.Date;
 import java.util.HashMap;
-import java.util.HashSet;
 import java.util.Iterator;
-import java.util.List;
 import java.util.Map;
-import java.util.Set;
+import java.util.Vector;
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
 public class BrowserActivity extends Activity
-    implements View.OnCreateContextMenuListener, DownloadListener {
+        implements View.OnCreateContextMenuListener, DownloadListener,
+        BookmarksHistoryCallbacks {
 
     /* Define some aliases to make these debugging flags easier to refer to.
      * This file imports android.provider.Browser, so we can't just refer to "Browser.DEBUG".
@@ -166,6 +159,13 @@
      */
     private FrameLayout mBrowserFrameLayout;
 
+    private CombinedBookmarkHistoryView mComboView;
+
+    private boolean mXLargeScreenSize;
+
+    private Boolean mIsProviderPresent = null;
+    private Uri mRlzUri = null;
+
     @Override
     public void onCreate(Bundle icicle) {
         if (LOGV_ENABLED) {
@@ -181,7 +181,11 @@
             BitmapFactory.setDefaultConfig(Bitmap.Config.ARGB_8888);
         }
 
-        setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
+        if (((AccessibilityManager) getSystemService(ACCESSIBILITY_SERVICE)).isEnabled()) {
+            setDefaultKeyMode(DEFAULT_KEYS_DISABLE);
+        } else {
+            setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
+        }
 
         mResolver = getContentResolver();
 
@@ -195,13 +199,18 @@
             return;
         }
 
-        mSecLockIcon = Resources.getSystem().getDrawable(
-                android.R.drawable.ic_secure);
-        mMixLockIcon = Resources.getSystem().getDrawable(
-                android.R.drawable.ic_partial_secure);
+        mSecLockIcon = getResources().getDrawable(R.drawable.ic_secure);
+        mMixLockIcon = getResources().getDrawable(R.drawable.ic_partial_secure);
+
+        // Create the tab control and our initial tab
+        mTabControl = new TabControl(this);
+
+        mXLargeScreenSize = (getResources().getConfiguration().screenLayout
+                & Configuration.SCREENLAYOUT_SIZE_MASK)
+                == Configuration.SCREENLAYOUT_SIZE_XLARGE;
 
         FrameLayout frameLayout = (FrameLayout) getWindow().getDecorView()
-                .findViewById(com.android.internal.R.id.content);
+                .findViewById(android.R.id.content);
         mBrowserFrameLayout = (FrameLayout) LayoutInflater.from(this)
                 .inflate(R.layout.custom_screen, null);
         mContentView = (FrameLayout) mBrowserFrameLayout.findViewById(
@@ -211,13 +220,23 @@
         mCustomViewContainer = (FrameLayout) mBrowserFrameLayout
                 .findViewById(R.id.fullscreen_custom_content);
         frameLayout.addView(mBrowserFrameLayout, COVER_SCREEN_PARAMS);
-        mTitleBar = new TitleBar(this);
-        // mTitleBar will be always shown in the fully loaded mode
-        mTitleBar.setProgress(100);
-        mFakeTitleBar = new TitleBar(this);
 
-        // Create the tab control and our initial tab
-        mTabControl = new TabControl(this);
+        if (mXLargeScreenSize) {
+            mTitleBar = new TitleBarXLarge(this);
+            mTitleBar.setProgress(100);
+            mFakeTitleBar = new TitleBarXLarge(this);
+            ActionBar actionBar = getActionBar();
+            mTabBar = new TabBar(this, mTabControl, (TitleBarXLarge) mFakeTitleBar);
+            actionBar.setCustomNavigationMode(mTabBar);
+            // disable built in zoom controls
+            mTabControl.setDisplayZoomControls(false);
+        } else {
+            mTitleBar = new TitleBar(this);
+            // mTitleBar will be always be shown in the fully loaded mode on
+            // phone
+            mTitleBar.setProgress(100);
+            mFakeTitleBar = new TitleBar(this);
+        }
 
         // Open the icon database and retain all the bookmark urls for favicons
         retainIconsOnStartup();
@@ -258,59 +277,19 @@
                 }
             };
 
-        IntentFilter filter = new IntentFilter(Intent.ACTION_PACKAGE_ADDED);
-        filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
-        filter.addDataScheme("package");
-        mPackageInstallationReceiver = new BroadcastReceiver() {
-            @Override
-            public void onReceive(Context context, Intent intent) {
-                final String action = intent.getAction();
-                final String packageName = intent.getData()
-                        .getSchemeSpecificPart();
-                final boolean replacing = intent.getBooleanExtra(
-                        Intent.EXTRA_REPLACING, false);
-                if (Intent.ACTION_PACKAGE_REMOVED.equals(action) && replacing) {
-                    // if it is replacing, refreshPlugins() when adding
-                    return;
-                }
+        // Unless the last browser usage was within 24 hours, destroy any
+        // remaining incognito tabs.
 
-                if (sGoogleApps.contains(packageName)) {
-                    BrowserActivity.this.packageChanged(packageName,
-                            Intent.ACTION_PACKAGE_ADDED.equals(action));
-                }
+        Calendar lastActiveDate = icicle != null ? (Calendar) icicle.getSerializable("lastActiveDate") : null;
+        Calendar today = Calendar.getInstance();
+        Calendar yesterday = Calendar.getInstance();
+        yesterday.add(Calendar.DATE, -1);
 
-                PackageManager pm = BrowserActivity.this.getPackageManager();
-                PackageInfo pkgInfo = null;
-                try {
-                    pkgInfo = pm.getPackageInfo(packageName,
-                            PackageManager.GET_PERMISSIONS);
-                } catch (PackageManager.NameNotFoundException e) {
-                    return;
-                }
-                if (pkgInfo != null) {
-                    String permissions[] = pkgInfo.requestedPermissions;
-                    if (permissions == null) {
-                        return;
-                    }
-                    boolean permissionOk = false;
-                    for (String permit : permissions) {
-                        if (PluginManager.PLUGIN_PERMISSION.equals(permit)) {
-                            permissionOk = true;
-                            break;
-                        }
-                    }
-                    if (permissionOk) {
-                        PluginManager.getInstance(BrowserActivity.this)
-                                .refreshPlugins(
-                                        Intent.ACTION_PACKAGE_ADDED
-                                                .equals(action));
-                    }
-                }
-            }
-        };
-        registerReceiver(mPackageInstallationReceiver, filter);
+        boolean dontRestoreIncognitoTabs = lastActiveDate == null
+            || lastActiveDate.before(yesterday)
+            || lastActiveDate.after(today);
 
-        if (!mTabControl.restoreState(icicle)) {
+        if (!mTabControl.restoreState(icicle, dontRestoreIncognitoTabs)) {
             // clear up the thumbnail directory if we can't restore the state as
             // none of the files in the directory are referenced any more.
             new ClearThumbnails().execute(
@@ -318,6 +297,8 @@
             // there is no quit on Android. But if we can't restore the state,
             // we can treat it as a new Browser, remove the old session cookies.
             CookieManager.getInstance().removeSessionCookie();
+            // remove any incognito files
+            WebView.cleanupPrivateBrowsingFiles(this);
             final Intent intent = getIntent();
             final Bundle extra = intent.getExtras();
             // Create an initial tab.
@@ -332,7 +313,8 @@
                     intent.getData() != null)
                     || RecognizerResultsIntent.ACTION_VOICE_SEARCH_RESULTS
                     .equals(action),
-                    intent.getStringExtra(Browser.EXTRA_APPLICATION_ID), urlData.mUrl);
+                    intent.getStringExtra(Browser.EXTRA_APPLICATION_ID),
+                    urlData.mUrl, false);
             mTabControl.setCurrentTab(t);
             attachTabToContentView(t);
             WebView webView = t.getWebView();
@@ -349,6 +331,10 @@
                 loadUrlDataIn(t, urlData);
             }
         } else {
+            if (dontRestoreIncognitoTabs) {
+                WebView.cleanupPrivateBrowsingFiles(this);
+            }
+
             // TabControl.restoreState() will create a new tab even if
             // restoring the state fails.
             attachTabToContentView(mTabControl.getCurrentTab());
@@ -368,8 +354,6 @@
         if (jsFlags.trim().length() != 0) {
             mTabControl.getCurrentWebView().setJsFlags(jsFlags);
         }
-        // Work out which packages are installed on the system.
-        getInstalledPackages();
 
         // Start watching the default geolocation permissions
         mSystemAllowGeolocationOrigins
@@ -377,6 +361,10 @@
         mSystemAllowGeolocationOrigins.start();
     }
 
+    ScrollListener getScrollListener() {
+        return mTabBar;
+    }
+
     /**
      * Feed the previously stored results strings to the BrowserProvider so that
      * the SearchDialog will show them instead of the standard searches.
@@ -530,13 +518,6 @@
                         current.getWebView().dumpRenderTree(true);
                     } else if ("about:debug.display".equals(urlData.mUrl)) {
                         current.getWebView().dumpDisplayTree();
-                    } else if (urlData.mUrl.startsWith("about:debug.drag")) {
-                        int index = urlData.mUrl.codePointAt(16) - '0';
-                        if (index <= 0 || index > 9) {
-                            current.getWebView().setDragTracker(null);
-                        } else {
-                            current.getWebView().setDragTracker(new MeshTracker(index));
-                        }
                     } else {
                         mSettings.toggleDebugSettings();
                     }
@@ -600,13 +581,16 @@
 
         final ContentResolver cr = mResolver;
         final String newUrl = url;
-        new AsyncTask<Void, Void, Void>() {
-            protected Void doInBackground(Void... unused) {
-                Browser.updateVisitedHistory(cr, newUrl, false);
-                Browser.addSearchUrl(cr, newUrl);
-                return null;
-            }
-        }.execute();
+        if (mTabControl == null || !mTabControl.getCurrentWebView().isPrivateBrowsingEnabled()) {
+            new AsyncTask<Void, Void, Void>() {
+                @Override
+                protected Void doInBackground(Void... unused) {
+                        Browser.updateVisitedHistory(cr, newUrl, false);
+                        Browser.addSearchUrl(cr, newUrl);
+                    return null;
+                }
+            }.execute();
+        }
 
         SearchEngine searchEngine = mSettings.getSearchEngine();
         if (searchEngine == null) return false;
@@ -653,12 +637,17 @@
                     url = smartUrlFilter(url);
                     final ContentResolver cr = mResolver;
                     final String newUrl = url;
-                    new AsyncTask<Void, Void, Void>() {
-                        protected Void doInBackground(Void... unused) {
-                            Browser.updateVisitedHistory(cr, newUrl, false);
-                            return null;
-                        }
-                    }.execute();
+                    if (mTabControl == null
+                            || mTabControl.getCurrentWebView() == null
+                            || !mTabControl.getCurrentWebView().isPrivateBrowsingEnabled()) {
+                        new AsyncTask<Void, Void, Void>() {
+                            @Override
+                            protected Void doInBackground(Void... unused) {
+                                Browser.updateVisitedHistory(cr, newUrl, false);
+                                return null;
+                            }
+                        }.execute();
+                    }
                     String searchSource = "&source=android-" + GOOGLE_SEARCH_SOURCE_SUGGEST + "&";
                     if (url.contains(searchSource)) {
                         String source = null;
@@ -678,16 +667,14 @@
     }
     /* package */ void showVoiceTitleBar(String title) {
         mTitleBar.setInVoiceMode(true);
-        mFakeTitleBar.setInVoiceMode(true);
-
         mTitleBar.setDisplayTitle(title);
+        mFakeTitleBar.setInVoiceMode(true);
         mFakeTitleBar.setDisplayTitle(title);
     }
     /* package */ void revertVoiceTitleBar() {
         mTitleBar.setInVoiceMode(false);
-        mFakeTitleBar.setInVoiceMode(false);
-
         mTitleBar.setDisplayTitle(mUrl);
+        mFakeTitleBar.setInVoiceMode(false);
         mFakeTitleBar.setDisplayTitle(mUrl);
     }
     /* package */ static String fixUrl(String inUrl) {
@@ -751,7 +738,7 @@
      * would change its appearance, use a different TitleBar to show overlayed
      * at the top of the screen, when the menu is open or the page is loading.
      */
-    private TitleBar mFakeTitleBar;
+    private TitleBarBase mFakeTitleBar;
 
     /**
      * Keeps track of whether the options menu is open.  This is important in
@@ -807,9 +794,8 @@
         return true;
     }
 
-    private void showFakeTitleBar() {
-        if (mFakeTitleBar.getParent() == null && mActiveTabsPage == null
-                && !mActivityInPause) {
+    void showFakeTitleBar() {
+        if (!isFakeTitleBarShowing() && mActiveTabsPage == null && !mActivityInPause) {
             WebView mainView = mTabControl.getCurrentWebView();
             // if there is no current WebView, don't show the faked title bar;
             if (mainView == null) {
@@ -817,28 +803,31 @@
             }
             // Do not need to check for null, since the current tab will have
             // at least a main WebView, or we would have returned above.
-            if (dialogIsUp()) {
-                // Do not show the fake title bar, which would cover up the
-                // find or select dialog.
+            if (isInCustomActionMode()) {
+                // Do not show the fake title bar, while a custom ActionMode
+                // (i.e. find or select) is showing.
                 return;
             }
+            if (mXLargeScreenSize) {
+                mContentView.addView(mFakeTitleBar);
+                mTabBar.onShowTitleBar();
+            } else {
+                WindowManager manager = (WindowManager) getSystemService(Context.WINDOW_SERVICE);
 
-            WindowManager manager
-                    = (WindowManager) getSystemService(Context.WINDOW_SERVICE);
-
-            // Add the title bar to the window manager so it can receive touches
-            // while the menu is up
-            WindowManager.LayoutParams params
-                    = new WindowManager.LayoutParams(
-                    ViewGroup.LayoutParams.MATCH_PARENT,
-                    ViewGroup.LayoutParams.WRAP_CONTENT,
-                    WindowManager.LayoutParams.TYPE_APPLICATION,
-                    WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
-                    PixelFormat.TRANSLUCENT);
-            params.gravity = Gravity.TOP;
-            boolean atTop = mainView.getScrollY() == 0;
-            params.windowAnimations = atTop ? 0 : R.style.TitleBar;
-            manager.addView(mFakeTitleBar, params);
+                // Add the title bar to the window manager so it can receive
+                // touches
+                // while the menu is up
+                WindowManager.LayoutParams params =
+                        new WindowManager.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
+                                ViewGroup.LayoutParams.WRAP_CONTENT,
+                                WindowManager.LayoutParams.TYPE_APPLICATION,
+                                WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
+                                PixelFormat.TRANSLUCENT);
+                params.gravity = Gravity.TOP;
+                boolean atTop = mainView.getScrollY() == 0;
+                params.windowAnimations = atTop ? 0 : R.style.TitleBar;
+                manager.addView(mFakeTitleBar, params);
+            }
         }
     }
 
@@ -855,21 +844,34 @@
         }
     }
 
-    private void hideFakeTitleBar() {
-        if (mFakeTitleBar.getParent() == null) return;
-        WindowManager.LayoutParams params = (WindowManager.LayoutParams)
-                mFakeTitleBar.getLayoutParams();
-        WebView mainView = mTabControl.getCurrentWebView();
-        // Although we decided whether or not to animate based on the current
-        // scroll position, the scroll position may have changed since the
-        // fake title bar was displayed.  Make sure it has the appropriate
-        // animation/lack thereof before removing.
-        params.windowAnimations = mainView != null && mainView.getScrollY() == 0
-                ? 0 : R.style.TitleBar;
-        WindowManager manager
-                    = (WindowManager) getSystemService(Context.WINDOW_SERVICE);
-        manager.updateViewLayout(mFakeTitleBar, params);
-        manager.removeView(mFakeTitleBar);
+    void stopScrolling() {
+        ((ScrollWebView) mTabControl.getCurrentWebView()).stopScroll();
+    }
+
+    void hideFakeTitleBar() {
+        if (!isFakeTitleBarShowing()) return;
+        if (mXLargeScreenSize) {
+            mContentView.removeView(mFakeTitleBar);
+            mTabBar.onHideTitleBar();
+        } else {
+            WindowManager.LayoutParams params =
+                    (WindowManager.LayoutParams) mFakeTitleBar.getLayoutParams();
+            WebView mainView = mTabControl.getCurrentWebView();
+            // Although we decided whether or not to animate based on the
+            // current
+            // scroll position, the scroll position may have changed since the
+            // fake title bar was displayed. Make sure it has the appropriate
+            // animation/lack thereof before removing.
+            params.windowAnimations =
+                    mainView != null && mainView.getScrollY() == 0 ? 0 : R.style.TitleBar;
+            WindowManager manager = (WindowManager) getSystemService(Context.WINDOW_SERVICE);
+            manager.updateViewLayout(mFakeTitleBar, params);
+            manager.removeView(mFakeTitleBar);
+        }
+    }
+
+    boolean isFakeTitleBarShowing() {
+        return (mFakeTitleBar.getParent() != null);
     }
 
     /**
@@ -910,6 +912,9 @@
 
         // Save all the tabs
         mTabControl.saveState(outState);
+
+        // Save time so that we know how old incognito tabs (if any) are.
+        outState.putSerializable("lastActiveDate", Calendar.getInstance());
     }
 
     @Override
@@ -971,8 +976,6 @@
         mTabControl.destroy();
         WebIconDatabase.getInstance().close();
 
-        unregisterReceiver(mPackageInstallationReceiver);
-
         // Stop watching the default geolocation permissions
         mSystemAllowGeolocationOrigins.stop();
         mSystemAllowGeolocationOrigins = null;
@@ -1002,18 +1005,7 @@
                 mSSLCertificateOnErrorError);
         }
         if (mHttpAuthenticationDialog != null) {
-            String title = ((TextView) mHttpAuthenticationDialog
-                    .findViewById(com.android.internal.R.id.alertTitle)).getText()
-                    .toString();
-            String name = ((TextView) mHttpAuthenticationDialog
-                    .findViewById(R.id.username_edit)).getText().toString();
-            String password = ((TextView) mHttpAuthenticationDialog
-                    .findViewById(R.id.password_edit)).getText().toString();
-            int focusId = mHttpAuthenticationDialog.getCurrentFocus()
-                    .getId();
-            mHttpAuthenticationDialog.dismiss();
-            showHttpAuthentication(mHttpAuthHandler, null, null, title,
-                    name, password, focusId);
+            mHttpAuthenticationDialog.reshow();
         }
     }
 
@@ -1101,12 +1093,14 @@
         if (mMenu == null) {
             return;
         }
+        MenuItem dest = mMenu.findItem(R.id.stop_reload_menu_id);
         MenuItem src = mInLoad ?
                 mMenu.findItem(R.id.stop_menu_id):
-                    mMenu.findItem(R.id.reload_menu_id);
-        MenuItem dest = mMenu.findItem(R.id.stop_reload_menu_id);
-        dest.setIcon(src.getIcon());
-        dest.setTitle(src.getTitle());
+                mMenu.findItem(R.id.reload_menu_id);
+        if (src != null) {
+            dest.setIcon(src.getIcon());
+            dest.setTitle(src.getTitle());
+        }
     }
 
     @Override
@@ -1133,7 +1127,6 @@
                 break;
             // -- Browser context menu
             case R.id.open_context_menu_id:
-            case R.id.open_newtab_context_menu_id:
             case R.id.bookmark_context_menu_id:
             case R.id.save_link_context_menu_id:
             case R.id.share_link_context_menu_id:
@@ -1257,6 +1250,7 @@
      */
     /* package */ void removeActiveTabPage(boolean needToAttach) {
         mContentView.removeView(mActiveTabsPage);
+        mTitleBar.setVisibility(View.VISIBLE);
         mActiveTabsPage = null;
         mMenuState = R.id.MAIN_MENU;
         if (needToAttach) {
@@ -1265,23 +1259,27 @@
         getTopWindow().requestFocus();
     }
 
-    private WebView showDialog(WebDialog dialog) {
-        Tab tab = mTabControl.getCurrentTab();
-        if (tab.getSubWebView() == null) {
-            // If the find or select is being performed on the main webview,
-            // remove the embedded title bar.
-            WebView mainView = tab.getWebView();
-            if (mainView != null) {
-                mainView.setEmbeddedTitleBar(null);
-            }
-        }
+    @Override
+    public ActionMode onStartActionMode(ActionMode.Callback callback) {
+        mActionMode = super.onStartActionMode(callback);
         hideFakeTitleBar();
-        mMenuState = EMPTY_MENU;
-        return tab.showDialog(dialog);
+        // Would like to change the MENU, but onEndActionMode may not be called
+        return mActionMode;
     }
 
     @Override
     public boolean onOptionsItemSelected(MenuItem item) {
+        if (item.getGroupId() != R.id.CONTEXT_MENU) {
+            // menu remains active, so ensure comboview is dismissed
+            // if main menu option is selected
+            removeComboView();
+        }
+        // check the action bar button before mCanChord check, as the prepare call
+        // doesn't come for action bar buttons
+        if (item.getItemId() == R.id.newtab) {
+            openTabToHomePage();
+            return true;
+        }
         if (!mCanChord) {
             // The user has already fired a shortcut with this hold down of the
             // menu key.
@@ -1303,6 +1301,10 @@
                 openTabToHomePage();
                 break;
 
+            case R.id.incognito_menu_id:
+                openIncognitoTab();
+                break;
+
             case R.id.goto_menu_id:
                 editUrl();
                 break;
@@ -1314,6 +1316,7 @@
             case R.id.active_tabs_menu_id:
                 mActiveTabsPage = new ActiveTabsPage(this, mTabControl);
                 removeTabFromContentView(mTabControl.getCurrentTab());
+                mTitleBar.setVisibility(View.GONE);
                 hideFakeTitleBar();
                 mContentView.addView(mActiveTabsPage, COVER_SCREEN_PARAMS);
                 mActiveTabsPage.requestFocus();
@@ -1321,14 +1324,7 @@
                 break;
 
             case R.id.add_bookmark_menu_id:
-                Intent i = new Intent(BrowserActivity.this,
-                        AddBookmarkPage.class);
-                WebView w = getTopWindow();
-                i.putExtra("url", w.getUrl());
-                i.putExtra("title", w.getTitle());
-                i.putExtra("touch_icon_url", w.getTouchIconUrl());
-                i.putExtra("thumbnail", createScreenshot(w));
-                startActivity(i);
+                bookmarkCurrentPage(AddBookmarkPage.DEFAULT_FOLDER_ID);
                 break;
 
             case R.id.stop_reload_menu_id:
@@ -1373,17 +1369,39 @@
                 break;
 
             case R.id.find_menu_id:
-                showFindDialog();
+                getTopWindow().showFindDialog(null);
                 break;
 
-            case R.id.select_text_id:
-                if (true) {
-                    Tab currentTab = mTabControl.getCurrentTab();
-                    if (currentTab != null) {
-                        currentTab.getWebView().setUpSelect();
+            case R.id.save_webarchive_menu_id:
+                if (LOGD_ENABLED) {
+                    Log.d(LOGTAG, "Save as Web Archive");
+                }
+                String state = Environment.getExternalStorageState();
+                if (Environment.MEDIA_MOUNTED.equals(state)) {
+                    String directory = Environment.getExternalStoragePublicDirectory(
+                            Environment.DIRECTORY_DOWNLOADS).getAbsolutePath() + File.separator;
+                    File dir = new File(directory);
+                    if (!dir.exists() && !dir.mkdirs()) {
+                      Log.e(LOGTAG, "Save as Web Archive: mkdirs for " + directory + " failed!");
+                      Toast.makeText(BrowserActivity.this, R.string.webarchive_failed,
+                          Toast.LENGTH_SHORT).show();
+                      break;
                     }
+                    getTopWindow().saveWebArchive(directory, true, new ValueCallback<String>() {
+                        @Override
+                        public void onReceiveValue(String value) {
+                            if (value != null) {
+                                Toast.makeText(BrowserActivity.this, R.string.webarchive_saved,
+                                        Toast.LENGTH_SHORT).show();
+                            } else {
+                                Toast.makeText(BrowserActivity.this, R.string.webarchive_failed,
+                                        Toast.LENGTH_SHORT).show();
+                            }
+                        }
+                    });
                 } else {
-                    showSelectDialog();
+                    Toast.makeText(BrowserActivity.this, R.string.webarchive_failed,
+                            Toast.LENGTH_SHORT).show();
                 }
                 break;
 
@@ -1405,7 +1423,8 @@
                 currentTab.populatePickerData();
                 sharePage(this, currentTab.getTitle(),
                         currentTab.getUrl(), currentTab.getFavicon(),
-                        createScreenshot(currentTab.getWebView()));
+                        createScreenshot(currentTab.getWebView(), getDesiredThumbnailWidth(this),
+                                getDesiredThumbnailHeight(this)));
                 break;
 
             case R.id.dump_nav_menu_id:
@@ -1461,60 +1480,75 @@
         return true;
     }
 
-    private boolean dialogIsUp() {
-        return null != mFindDialog && mFindDialog.isVisible() ||
-            null != mSelectDialog && mSelectDialog.isVisible();
-    }
-
-    private boolean closeDialog(WebDialog dialog) {
-        if (null == dialog || !dialog.isVisible()) return false;
-        Tab currentTab = mTabControl.getCurrentTab();
-        currentTab.closeDialog(dialog);
-        dialog.dismiss();
-        return true;
+    /**
+     * add the current page as a bookmark to the given folder id
+     * @param folderId use -1 for the default folder
+     */
+    /* package */ void bookmarkCurrentPage(long folderId) {
+        Intent i = new Intent(BrowserActivity.this,
+                AddBookmarkPage.class);
+        WebView w = getTopWindow();
+        i.putExtra(BrowserContract.Bookmarks.URL, w.getUrl());
+        i.putExtra(BrowserContract.Bookmarks.TITLE, w.getTitle());
+        String touchIconUrl = w.getTouchIconUrl();
+        if (touchIconUrl != null) {
+            i.putExtra(AddBookmarkPage.TOUCH_ICON_URL, touchIconUrl);
+            WebSettings settings = w.getSettings();
+            if (settings != null) {
+                i.putExtra(AddBookmarkPage.USER_AGENT,
+                        settings.getUserAgentString());
+            }
+        }
+        i.putExtra(BrowserContract.Bookmarks.THUMBNAIL,
+                createScreenshot(w, getDesiredThumbnailWidth(this),
+                getDesiredThumbnailHeight(this)));
+        i.putExtra(BrowserContract.Bookmarks.FAVICON, w.getFavicon());
+        i.putExtra(BrowserContract.Bookmarks.PARENT,
+                folderId);
+        // Put the dialog at the upper right of the screen, covering the
+        // star on the title bar.
+        i.putExtra("gravity", Gravity.RIGHT | Gravity.TOP);
+        startActivity(i);
     }
 
     /*
-     * Remove the find dialog or select dialog.
+     * True if a custom ActionMode (i.e. find or select) is in use.
      */
-    public void closeDialogs() {
-        if (!(closeDialog(mFindDialog) || closeDialog(mSelectDialog))) return;
-        // If the Find was being performed in the main WebView, replace the
-        // embedded title bar.
-        Tab currentTab = mTabControl.getCurrentTab();
-        if (currentTab.getSubWebView() == null) {
-            WebView mainView = currentTab.getWebView();
-            if (mainView != null) {
-                mainView.setEmbeddedTitleBar(mTitleBar);
-            }
+    private boolean isInCustomActionMode() {
+        return mActionMode != null;
+    }
+
+    /*
+     * End the current ActionMode.
+     */
+    void endActionMode() {
+        if (mActionMode != null) {
+            ActionMode mode = mActionMode;
+            onEndActionMode();
+            mode.finish();
         }
-        mMenuState = R.id.MAIN_MENU;
+    }
+
+    /*
+     * Called by find and select when they are finished.  Replace title bars
+     * as necessary.
+     */
+    public void onEndActionMode() {
+        if (!isInCustomActionMode()) return;
         if (mInLoad) {
             // The title bar was hidden, because otherwise it would cover up the
-            // find or select dialog.  Now that the dialog has been removed,
+            // find or select dialog. Now that the dialog has been removed,
             // show the fake title bar once again.
             showFakeTitleBar();
         }
+        // Would like to return the menu state to normal, but this does not
+        // necessarily get called.
+        mActionMode = null;
     }
 
-    public void showFindDialog() {
-        if (null == mFindDialog) {
-            mFindDialog = new FindDialog(this);
-        }
-        showDialog(mFindDialog).setFindIsUp(true);
-    }
-
-    public void setFindDialogText(String text) {
-        mFindDialog.setText(text);
-    }
-
-    public void showSelectDialog() {
-        if (null == mSelectDialog) {
-            mSelectDialog = new SelectDialog(this);
-        }
-        showDialog(mSelectDialog).setUpSelect();
-        mSelectDialog.hideSoftInput();
-    }
+    // For select and find, we keep track of the ActionMode so that
+    // finish() can be called as desired.
+    private ActionMode mActionMode;
 
     @Override
     public boolean onPrepareOptionsMenu(Menu menu) {
@@ -1554,12 +1588,13 @@
                 final MenuItem home = menu.findItem(R.id.homepage_menu_id);
                 home.setEnabled(!isHome);
 
-                menu.findItem(R.id.forward_menu_id)
-                        .setEnabled(canGoForward);
+                final MenuItem forward = menu.findItem(R.id.forward_menu_id);
+                forward.setEnabled(canGoForward);
 
-                menu.findItem(R.id.new_tab_menu_id).setEnabled(
-                        mTabControl.canCreateNewTab());
-
+                if (!mXLargeScreenSize) {
+                    final MenuItem newtab = menu.findItem(R.id.new_tab_menu_id);
+                    newtab.setEnabled(mTabControl.canCreateNewTab());
+                }
                 // decide whether to show the share link option
                 PackageManager pm = getPackageManager();
                 Intent send = new Intent(Intent.ACTION_SEND);
@@ -1586,7 +1621,10 @@
     @Override
     public void onCreateContextMenu(ContextMenu menu, View v,
             ContextMenuInfo menuInfo) {
-        if (v instanceof TitleBar) {
+        if (v instanceof TitleBarBase) {
+            return;
+        }
+        if (!(v instanceof WebView)) {
             return;
         }
         WebView webview = (WebView) v;
@@ -1613,7 +1651,7 @@
         inflater.inflate(R.menu.browsercontext, menu);
 
         // Show the correct menu group
-        String extra = result.getExtra();
+        final String extra = result.getExtra();
         menu.setGroupVisible(R.id.PHONE_MENU,
                 type == WebView.HitTestResult.PHONE_TYPE);
         menu.setGroupVisible(R.id.EMAIL_MENU,
@@ -1670,8 +1708,23 @@
                 titleView.setText(extra);
                 menu.setHeaderView(titleView);
                 // decide whether to show the open link in new tab option
-                menu.findItem(R.id.open_newtab_context_menu_id).setVisible(
-                        mTabControl.canCreateNewTab());
+                boolean showNewTab = mTabControl.canCreateNewTab();
+                MenuItem newTabItem
+                        = menu.findItem(R.id.open_newtab_context_menu_id);
+                newTabItem.setVisible(showNewTab);
+                if (showNewTab) {
+                    newTabItem.setOnMenuItemClickListener(
+                            new MenuItem.OnMenuItemClickListener() {
+                                public boolean onMenuItemClick(MenuItem item) {
+                                    final Tab parent = mTabControl.getCurrentTab();
+                                    final Tab newTab = openTab(extra, false);
+                                    if (newTab != parent) {
+                                        parent.addChildTab(newTab);
+                                    }
+                                    return true;
+                                }
+                            });
+                }
                 menu.findItem(R.id.bookmark_context_menu_id).setVisible(
                         Bookmarks.urlHasAcceptableScheme(extra));
                 PackageManager pm = getPackageManager();
@@ -1731,6 +1784,9 @@
         }
         // Request focus on the top window.
         t.getTopWindow().requestFocus();
+        if (mTabControl.getTabChangeListener() != null) {
+            mTabControl.getTabChangeListener().onCurrentTab(t);
+        }
     }
 
     // Attach a sub window to the main WebView of the given tab.
@@ -1778,7 +1834,7 @@
         final Tab currentTab = mTabControl.getCurrentTab();
         if (mTabControl.canCreateNewTab()) {
             final Tab tab = mTabControl.createNewTab(closeOnExit, appId,
-                    urlData.mUrl);
+                    urlData.mUrl, false);
             WebView webview = tab.getWebView();
             // If the last tab was removed from the active tabs page, currentTab
             // will be null.
@@ -1804,8 +1860,8 @@
         }
     }
 
-    private Tab openTab(String url) {
-        if (mSettings.openInBackground()) {
+    private Tab openTab(String url, boolean forceForeground) {
+        if (mSettings.openInBackground() && !forceForeground) {
             Tab t = mTabControl.createNewTab();
             if (t != null) {
                 WebView view = t.getWebView();
@@ -1817,6 +1873,20 @@
         }
     }
 
+    /* package */ Tab openIncognitoTab() {
+        if (mTabControl.canCreateNewTab()) {
+            Tab currentTab = mTabControl.getCurrentTab();
+            Tab tab = mTabControl.createNewTab(false, null, null, true);
+            if (currentTab != null) {
+                removeTabFromContentView(currentTab);
+            }
+            mTabControl.setCurrentTab(tab);
+            attachTabToContentView(tab);
+            return tab;
+        }
+        return null;
+    }
+
     private class Copy implements OnMenuItemClickListener {
         private CharSequence mText;
 
@@ -1877,6 +1947,7 @@
             return true;
         }
 
+        @Override
         public void run() {
             Drawable oldWallpaper = BrowserActivity.this.getWallpaper();
             try {
@@ -1920,14 +1991,8 @@
     }
 
     private void copy(CharSequence text) {
-        try {
-            IClipboard clip = IClipboard.Stub.asInterface(ServiceManager.getService("clipboard"));
-            if (clip != null) {
-                clip.setClipboardText(text);
-            }
-        } catch (android.os.RemoteException e) {
-            Log.e(LOGTAG, "Copy failed", e);
-        }
+        ClipboardManager cm = (ClipboardManager)getSystemService(Context.CLIPBOARD_SERVICE);
+        cm.setText(text);
     }
 
     /**
@@ -2040,6 +2105,11 @@
         }
         mTabControl.setCurrentTab(mTabControl.getTab(currentIndex));
         resetTitleIconAndProgress();
+        updateLockIconToLatest();
+
+        if (!mTabControl.hasAnyOpenIncognitoTabs()) {
+            WebView.cleanupPrivateBrowsingFiles(this);
+        }
     }
 
     /* package */ void goBackOnePageOrQuit() {
@@ -2137,6 +2207,7 @@
                     event.startTracking();
                     return true;
                 } else if (mCustomView == null && mActiveTabsPage == null
+                        && mComboView == null
                         && event.isLongPress()) {
                     bookmarksOrHistoryPicker(true);
                     return true;
@@ -2161,6 +2232,10 @@
                     } else if (mActiveTabsPage != null) {
                         // if tab page is showing, hide it
                         removeActiveTabPage(true);
+                    } else if (mComboView != null) {
+                        if (!mComboView.onBackPressed()) {
+                            removeComboView();
+                        }
                     } else {
                         WebView subwindow = mTabControl.getCurrentSubWindow();
                         if (subwindow != null) {
@@ -2231,11 +2306,17 @@
 
     static final int UPDATE_BOOKMARK_THUMBNAIL       = 108;
 
+    private static final int OPEN_BOOKMARKS = 201;
+
     // Private handler for handling javascript and saving passwords
     private Handler mHandler = new Handler() {
 
+        @Override
         public void handleMessage(Message msg) {
             switch (msg.what) {
+                case OPEN_BOOKMARKS:
+                    bookmarksOrHistoryPicker(false);
+                    break;
                 case FOCUS_NODE_HREF:
                 {
                     String url = (String) msg.getData().get("url");
@@ -2254,65 +2335,17 @@
                         case R.id.view_image_context_menu_id:
                             loadUrlFromContext(getTopWindow(), url);
                             break;
-                        case R.id.open_newtab_context_menu_id:
-                            final Tab parent = mTabControl.getCurrentTab();
-                            final Tab newTab = openTab(url);
-                            if (newTab != parent) {
-                                parent.addChildTab(newTab);
-                            }
-                            break;
                         case R.id.bookmark_context_menu_id:
                             Intent intent = new Intent(BrowserActivity.this,
                                     AddBookmarkPage.class);
-                            intent.putExtra("url", url);
-                            intent.putExtra("title", title);
+                            intent.putExtra(BrowserContract.Bookmarks.URL, url);
+                            intent.putExtra(BrowserContract.Bookmarks.TITLE,
+                                    title);
                             startActivity(intent);
                             break;
                         case R.id.share_link_context_menu_id:
-                            // See if this site has been visited before
-                            StringBuilder sb = new StringBuilder(
-                                    Browser.BookmarkColumns.URL + " = ");
-                            DatabaseUtils.appendEscapedSQLString(sb, url);
-                            Cursor c = null;
-                            try {
-                                c = mResolver.query(Browser.BOOKMARKS_URI,
-                                        Browser.HISTORY_PROJECTION,
-                                        sb.toString(),
-                                        null,
-                                        null);
-                                if (c.moveToFirst()) {
-                                    // The site has been visited before, so grab the
-                                    // info from the database.
-                                    Bitmap favicon = null;
-                                    Bitmap thumbnail = null;
-                                    String linkTitle = c.getString(Browser.
-                                            HISTORY_PROJECTION_TITLE_INDEX);
-                                    byte[] data = c.getBlob(Browser.
-                                            HISTORY_PROJECTION_FAVICON_INDEX);
-                                    if (data != null) {
-                                        favicon = BitmapFactory.decodeByteArray(
-                                                data, 0, data.length);
-                                    }
-                                    data = c.getBlob(Browser.
-                                            HISTORY_PROJECTION_THUMBNAIL_INDEX);
-                                    if (data != null) {
-                                        thumbnail = BitmapFactory.decodeByteArray(
-                                                data, 0, data.length);
-                                    }
-                                    sharePage(BrowserActivity.this,
-                                            linkTitle, url, favicon, thumbnail);
-                                } else {
-                                    Browser.sendString(BrowserActivity.this, url,
-                                            getString(
-                                            R.string.choosertitle_sharevia));
-                                }
-                            } finally {
-                                if (c != null) c.close();
-                            }
-                            // close the cursor after its used
-                            if (c != null) {
-                                c.close();
-                            }
+                            sharePage(BrowserActivity.this, title, url, null,
+                                    null);
                             break;
                         case R.id.copy_link_context_menu_id:
                             copy(url);
@@ -2389,7 +2422,8 @@
         // draw, but the API for that (WebViewCore.pictureReady()) is not
         // currently accessible here.
 
-        final Bitmap bm = createScreenshot(view);
+        final Bitmap bm = createScreenshot(view, getDesiredThumbnailWidth(this),
+                getDesiredThumbnailHeight(this));
         if (bm == null) {
             return;
         }
@@ -2401,29 +2435,25 @@
         new AsyncTask<Void, Void, Void>() {
             @Override
             protected Void doInBackground(Void... unused) {
-                Cursor c = null;
+                Cursor cursor = null;
                 try {
-                    c = BrowserBookmarksAdapter.queryBookmarksForUrl(
-                            cr, originalUrl, url, true);
-                    if (c != null) {
-                        if (c.moveToFirst()) {
-                            ContentValues values = new ContentValues();
-                            final ByteArrayOutputStream os
-                                    = new ByteArrayOutputStream();
-                            bm.compress(Bitmap.CompressFormat.PNG, 100, os);
-                            values.put(Browser.BookmarkColumns.THUMBNAIL,
-                                    os.toByteArray());
-                            do {
-                                cr.update(ContentUris.withAppendedId(
-                                        Browser.BOOKMARKS_URI, c.getInt(0)),
-                                        values, null, null);
-                            } while (c.moveToNext());
-                        }
+                    cursor = Bookmarks.queryCombinedForUrl(cr, originalUrl, url);
+                    if (cursor != null && cursor.moveToFirst()) {
+                        final ByteArrayOutputStream os = new ByteArrayOutputStream();
+                        bm.compress(Bitmap.CompressFormat.PNG, 100, os);
+
+                        ContentValues values = new ContentValues();
+                        values.put(Images.THUMBNAIL, os.toByteArray());
+                        values.put(Images.URL, cursor.getString(0));
+
+                        do {
+                            cr.update(Images.CONTENT_URI, values, null, null);
+                        } while (cursor.moveToNext());
                     }
                 } catch (IllegalStateException e) {
                     // Ignore
                 } finally {
-                    if (c != null) c.close();
+                    if (cursor != null) cursor.close();
                 }
                 return null;
             }
@@ -2431,47 +2461,31 @@
     }
 
     /**
-     * Values for the size of the thumbnail created when taking a screenshot.
-     * Lazily initialized.  Instead of using these directly, use
-     * getDesiredThumbnailWidth() or getDesiredThumbnailHeight().
-     */
-    private static int THUMBNAIL_WIDTH = 0;
-    private static int THUMBNAIL_HEIGHT = 0;
-
-    /**
      * Return the desired width for thumbnail screenshots, which are stored in
      * the database, and used on the bookmarks screen.
      * @param context Context for finding out the density of the screen.
-     * @return int desired width for thumbnail screenshot.
+     * @return desired width for thumbnail screenshot.
      */
     /* package */ static int getDesiredThumbnailWidth(Context context) {
-        if (THUMBNAIL_WIDTH == 0) {
-            float density = context.getResources().getDisplayMetrics().density;
-            THUMBNAIL_WIDTH = (int) (90 * density);
-            THUMBNAIL_HEIGHT = (int) (80 * density);
-        }
-        return THUMBNAIL_WIDTH;
+        return context.getResources().getDimensionPixelOffset(R.dimen.bookmarkThumbnailWidth);
     }
 
     /**
      * Return the desired height for thumbnail screenshots, which are stored in
      * the database, and used on the bookmarks screen.
      * @param context Context for finding out the density of the screen.
-     * @return int desired height for thumbnail screenshot.
+     * @return desired height for thumbnail screenshot.
      */
     /* package */ static int getDesiredThumbnailHeight(Context context) {
-        // To ensure that they are both initialized.
-        getDesiredThumbnailWidth(context);
-        return THUMBNAIL_HEIGHT;
+        return context.getResources().getDimensionPixelOffset(R.dimen.bookmarkThumbnailHeight);
     }
 
-    private Bitmap createScreenshot(WebView view) {
+    private Bitmap createScreenshot(WebView view, int width, int height) {
         Picture thumbnail = view.capturePicture();
         if (thumbnail == null) {
             return null;
         }
-        Bitmap bm = Bitmap.createBitmap(getDesiredThumbnailWidth(this),
-                getDesiredThumbnailHeight(this), Bitmap.Config.RGB_565);
+        Bitmap bm = Bitmap.createBitmap(width, height, Bitmap.Config.RGB_565);
         Canvas canvas = new Canvas(bm);
         // May need to tweak these values to determine what is the
         // best scale factor
@@ -2480,8 +2494,7 @@
         float scaleFactorX = 1.0f;
         float scaleFactorY = 1.0f;
         if (thumbnailWidth > 0) {
-            scaleFactorX = (float) getDesiredThumbnailWidth(this) /
-                    (float)thumbnailWidth;
+            scaleFactorX = (float) width / (float)thumbnailWidth;
         } else {
             return null;
         }
@@ -2491,8 +2504,7 @@
             // If the device is in landscape and the page is shorter
             // than the height of the view, stretch the thumbnail to fill the
             // space.
-            scaleFactorY = (float) getDesiredThumbnailHeight(this) /
-                    (float)thumbnailHeight;
+            scaleFactorY = (float) height / (float)thumbnailHeight;
         } else {
             // In the portrait case, this looks nice.
             scaleFactorY = scaleFactorX;
@@ -2533,12 +2545,12 @@
         onProgressChanged(view, INITIAL_PROGRESS);
         mDidStopLoad = false;
         if (!mIsNetworkUp) createAndShowNetworkDialog();
-        closeDialogs();
+        endActionMode();
         if (mSettings.isTracing()) {
             String host;
             try {
                 WebAddress uri = new WebAddress(url);
-                host = uri.mHost;
+                host = uri.getHost();
             } catch (android.net.ParseException ex) {
                 host = "browser";
             }
@@ -2631,7 +2643,25 @@
         }
     }
 
+    private void closeEmptyChildTab() {
+        Tab current = mTabControl.getCurrentTab();
+        if (current != null
+                && current.getWebView().copyBackForwardList().getSize() == 0) {
+            Tab parent = current.getParentTab();
+            if (parent != null) {
+                switchToTab(mTabControl.getTabIndex(parent));
+                closeTab(current);
+            }
+        }
+    }
+
     boolean shouldOverrideUrlLoading(WebView view, String url) {
+        if (view.isPrivateBrowsingEnabled()) {
+            // Don't allow urls to leave the browser app when in private browsing mode
+            loadUrl(view, url);
+            return true;
+        }
+
         if (url.startsWith(SCHEME_WTAI)) {
             // wtai://wp/mc;number
             // number=string(phone-number)
@@ -2640,6 +2670,11 @@
                         Uri.parse(WebView.SCHEME_TEL +
                         url.substring(SCHEME_WTAI_MC.length())));
                 startActivity(intent);
+                // before leaving BrowserActivity, close the empty child tab.
+                // If a new tab is created through JavaScript open to load this
+                // url, we would like to close it as we will load this url in a
+                // different Activity.
+                closeEmptyChildTab();
                 return true;
             }
             // wtai://wp/sd;dtmf
@@ -2663,6 +2698,29 @@
             return false;
         }
 
+        // If this is a Google search, attempt to add an RLZ string (if one isn't already present).
+        if (rlzProviderPresent()) {
+            Uri siteUri = Uri.parse(url);
+            if (needsRlzString(siteUri)) {
+                String rlz = null;
+                Cursor cur = null;
+                try {
+                    cur = getContentResolver().query(getRlzUri(), null, null, null, null);
+                    if (cur != null && cur.moveToFirst() && !cur.isNull(0)) {
+                        url = siteUri.buildUpon()
+                                     .appendQueryParameter("rlz", cur.getString(0))
+                                     .build().toString();
+                    }
+                } finally {
+                    if (cur != null) {
+                        cur.close();
+                    }
+                }
+                loadUrl(view, url);
+                return true;
+            }
+        }
+
         Intent intent;
         // perform generic parsing of the URI to turn it into an Intent.
         try {
@@ -2681,6 +2739,11 @@
                         .parse("market://search?q=pname:" + packagename));
                 intent.addCategory(Intent.CATEGORY_BROWSABLE);
                 startActivity(intent);
+                // before leaving BrowserActivity, close the empty child tab.
+                // If a new tab is created through JavaScript open to load this
+                // url, we would like to close it as we will load this url in a
+                // different Activity.
+                closeEmptyChildTab();
                 return true;
             } else {
                 return false;
@@ -2693,6 +2756,11 @@
         intent.setComponent(null);
         try {
             if (startActivityIfNeeded(intent, -1)) {
+                // before leaving BrowserActivity, close the empty child tab.
+                // If a new tab is created through JavaScript open to load this
+                // url, we would like to close it as we will load this url in a
+                // different Activity.
+                closeEmptyChildTab();
                 return true;
             }
         } catch (ActivityNotFoundException ex) {
@@ -2701,18 +2769,78 @@
         }
 
         if (mMenuIsDown) {
-            openTab(url);
+            openTab(url, false);
             closeOptionsMenu();
             return true;
         }
         return false;
     }
 
+    // Determine whether the RLZ provider is present on the system.
+    private boolean rlzProviderPresent() {
+        if (mIsProviderPresent == null) {
+            PackageManager pm = getPackageManager();
+            mIsProviderPresent = pm.resolveContentProvider(BrowserSettings.RLZ_PROVIDER, 0) != null;
+        }
+        return mIsProviderPresent;
+    }
+
+    // Retrieve the RLZ access point string and cache the URI used to retrieve RLZ values.
+    private Uri getRlzUri() {
+        if (mRlzUri == null) {
+            String ap = getResources().getString(R.string.rlz_access_point);
+            mRlzUri = Uri.withAppendedPath(BrowserSettings.RLZ_PROVIDER_URI, ap);
+        }
+        return mRlzUri;
+    }
+
+    // Determine if this URI appears to be for a Google search and does not have an RLZ parameter.
+    // Taken largely from Chrome source, src/chrome/browser/google_url_tracker.cc
+    private static boolean needsRlzString(Uri uri) {
+        String scheme = uri.getScheme();
+        if (("http".equals(scheme) || "https".equals(scheme)) &&
+            (uri.getQueryParameter("q") != null) && (uri.getQueryParameter("rlz") == null)) {
+            String host = uri.getHost();
+            if (host == null) {
+                return false;
+            }
+            String[] hostComponents = host.split("\\.");
+
+            if (hostComponents.length < 2) {
+                return false;
+            }
+            int googleComponent = hostComponents.length - 2;
+            String component = hostComponents[googleComponent];
+            if (!"google".equals(component)) {
+                if (hostComponents.length < 3 ||
+                        (!"co".equals(component) && !"com".equals(component))) {
+                    return false;
+                }
+                googleComponent = hostComponents.length - 3;
+                if (!"google".equals(hostComponents[googleComponent])) {
+                    return false;
+                }
+            }
+
+            // Google corp network handling.
+            if (googleComponent > 0 && "corp".equals(hostComponents[googleComponent - 1])) {
+                return false;
+            }
+
+            return true;
+        }
+        return false;
+    }
+
     // -------------------------------------------------------------------------
     // Helper function for WebChromeClient
     // -------------------------------------------------------------------------
 
     void onProgressChanged(WebView view, int newProgress) {
+
+        // On the phone, the fake title bar will always cover up the
+        // regular title bar (or the regular one is offscreen), so only the
+        // fake title bar needs to change its progress
         mFakeTitleBar.setProgress(newProgress);
 
         if (newProgress == 100) {
@@ -2814,15 +2942,138 @@
      * The Object used to inform the WebView of the file to upload.
      */
     private ValueCallback<Uri> mUploadMessage;
+    private String mCameraFilePath;
 
-    void openFileChooser(ValueCallback<Uri> uploadMsg) {
-        if (mUploadMessage != null) return;
+    void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType) {
+
+        final String imageMimeType = "image/*";
+        final String videoMimeType = "video/*";
+        final String audioMimeType = "audio/*";
+        final String mediaSourceKey = "capture";
+        final String mediaSourceValueCamera = "camera";
+        final String mediaSourceValueFileSystem = "filesystem";
+        final String mediaSourceValueCamcorder = "camcorder";
+        final String mediaSourceValueMicrophone = "microphone";
+
+        // media source can be 'filesystem' or 'camera' or 'camcorder' or 'microphone'.
+        String mediaSource = "";
+
+        // We add the camera intent if there was no accept type (or '*/*' or 'image/*').
+        boolean addCameraIntent = true;
+        // We add the camcorder intent if there was no accept type (or '*/*' or 'video/*').
+        boolean addCamcorderIntent = true;
+
+        if (mUploadMessage != null) {
+            // Already a file picker operation in progress.
+            return;
+        }
+
         mUploadMessage = uploadMsg;
+
+        // Parse the accept type.
+        String params[] = acceptType.split(";");
+        String mimeType = params[0];
+
+        for (String p : params) {
+            String[] keyValue = p.split("=");
+            if (keyValue.length == 2) {
+                // Process key=value parameters.
+                if (mediaSourceKey.equals(keyValue[0])) {
+                    mediaSource = keyValue[1];
+                }
+            }
+        }
+
+        // This intent will display the standard OPENABLE file picker.
         Intent i = new Intent(Intent.ACTION_GET_CONTENT);
         i.addCategory(Intent.CATEGORY_OPENABLE);
-        i.setType("*/*");
-        BrowserActivity.this.startActivityForResult(Intent.createChooser(i,
-                getString(R.string.choose_upload)), FILE_SELECTED);
+
+        // Create an intent to add to the standard file picker that will
+        // capture an image from the camera. We'll combine this intent with
+        // the standard OPENABLE picker unless the web developer specifically
+        // requested the camera or gallery be opened by passing a parameter
+        // in the accept type.
+        Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
+        File externalDataDir = Environment.getExternalStoragePublicDirectory(
+                Environment.DIRECTORY_DCIM);
+        File cameraDataDir = new File(externalDataDir.getAbsolutePath() +
+                File.separator + "browser-photos");
+        cameraDataDir.mkdirs();
+        mCameraFilePath = cameraDataDir.getAbsolutePath() + File.separator +
+                System.currentTimeMillis() + ".jpg";
+        cameraIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(new File(mCameraFilePath)));
+
+        Intent camcorderIntent = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);
+
+        Intent soundRecIntent = new Intent(MediaStore.Audio.Media.RECORD_SOUND_ACTION);
+
+        if (mimeType.equals(imageMimeType)) {
+            i.setType(imageMimeType);
+            addCamcorderIntent = false;
+            if (mediaSource.equals(mediaSourceValueCamera)) {
+                // Specified 'image/*' and requested the camera, so go ahead and launch the camera
+                // directly.
+                BrowserActivity.this.startActivityForResult(cameraIntent, FILE_SELECTED);
+                return;
+            } else if (mediaSource.equals(mediaSourceValueFileSystem)) {
+                // Specified filesytem as the source, so don't want to consider the camera.
+                addCameraIntent = false;
+            }
+        } else if (mimeType.equals(videoMimeType)) {
+            i.setType(videoMimeType);
+            addCameraIntent = false;
+            // The camcorder saves it's own file and returns it to us in the intent, so
+            // we don't need to generate one here.
+            mCameraFilePath = null;
+
+            if (mediaSource.equals(mediaSourceValueCamcorder)) {
+                // Specified 'video/*' and requested the camcorder, so go ahead and launch the
+                // camcorder directly.
+                BrowserActivity.this.startActivityForResult(camcorderIntent, FILE_SELECTED);
+                return;
+            } else if (mediaSource.equals(mediaSourceValueFileSystem)) {
+                // Specified filesystem as the source, so don't want to consider the camcorder.
+                addCamcorderIntent = false;
+            }
+        } else if (mimeType.equals(audioMimeType)) {
+            i.setType(audioMimeType);
+            addCameraIntent = false;
+            addCamcorderIntent = false;
+            if (mediaSource.equals(mediaSourceValueMicrophone)) {
+                // Specified 'audio/*' and requested microphone, so go ahead and launch the sound
+                // recorder.
+                BrowserActivity.this.startActivityForResult(soundRecIntent, FILE_SELECTED);
+                return;
+            }
+            // On a default system, there is no single option to open an audio "gallery". Both the
+            // sound recorder and music browser respond to the OPENABLE/audio/* intent unlike the
+            // image/* and video/* OPENABLE intents where the image / video gallery are the only
+            // respondants (and so the user is not prompted by default).
+        } else {
+            i.setType("*/*");
+        }
+
+        // Combine the chooser and the extra choices (like camera or camcorder)
+        Intent chooser = new Intent(Intent.ACTION_CHOOSER);
+        chooser.putExtra(Intent.EXTRA_INTENT, i);
+
+        Vector<Intent> extraInitialIntents = new Vector<Intent>(0);
+
+        if (addCameraIntent) {
+            extraInitialIntents.add(cameraIntent);
+        }
+
+        if (addCamcorderIntent) {
+            extraInitialIntents.add(camcorderIntent);
+        }
+
+        if (extraInitialIntents.size() > 0) {
+            Intent[] extraIntents = new Intent[extraInitialIntents.size()];
+            chooser.putExtra(Intent.EXTRA_INITIAL_INTENTS, extraInitialIntents.toArray(extraIntents));
+        }
+
+        chooser.putExtra(Intent.EXTRA_TITLE, getString(R.string.choose_upload));
+        BrowserActivity.this.startActivityForResult(chooser, FILE_SELECTED);
     }
 
     // -------------------------------------------------------------------------
@@ -2953,7 +3204,7 @@
         WebAddress webAddress;
         try {
             webAddress = new WebAddress(url);
-            webAddress.mPath = encodePath(webAddress.mPath);
+            webAddress.setPath(encodePath(webAddress.getPath()));
         } catch (Exception e) {
             // This only happens for very bad urls, we want to chatch the
             // exception here
@@ -2961,33 +3212,29 @@
             return;
         }
 
-        // XXX: Have to use the old url since the cookies were stored using the
-        // old percent-encoded url.
+        String addressString = webAddress.toString(); 
+        Uri uri = Uri.parse(addressString);
+        DownloadManager.Request request = new DownloadManager.Request(uri);
+        request.setMimeType(mimetype);
+        request.setDestinationInExternalFilesDir(this, null, filename);
+        request.setDescription(webAddress.getHost());
         String cookies = CookieManager.getInstance().getCookie(url);
-
-        ContentValues values = new ContentValues();
-        values.put(Downloads.Impl.COLUMN_URI, webAddress.toString());
-        values.put(Downloads.Impl.COLUMN_COOKIE_DATA, cookies);
-        values.put(Downloads.Impl.COLUMN_USER_AGENT, userAgent);
-        values.put(Downloads.Impl.COLUMN_NOTIFICATION_PACKAGE,
-                getPackageName());
-        values.put(Downloads.Impl.COLUMN_NOTIFICATION_CLASS,
-                OpenDownloadReceiver.class.getCanonicalName());
-        values.put(Downloads.Impl.COLUMN_VISIBILITY,
-                Downloads.Impl.VISIBILITY_VISIBLE_NOTIFY_COMPLETED);
-        values.put(Downloads.Impl.COLUMN_MIME_TYPE, mimetype);
-        values.put(Downloads.Impl.COLUMN_FILE_NAME_HINT, filename);
-        values.put(Downloads.Impl.COLUMN_DESCRIPTION, webAddress.mHost);
-        if (contentLength > 0) {
-            values.put(Downloads.Impl.COLUMN_TOTAL_BYTES, contentLength);
-        }
+        request.addRequestHeader("cookie", cookies);
         if (mimetype == null) {
+            ContentValues values = new ContentValues();
+            values.put(FetchUrlMimeType.URI, addressString);
+            // XXX: Have to use the old url since the cookies were stored using the
+            // old percent-encoded url.
+            values.put(FetchUrlMimeType.COOKIE_DATA, cookies);
+            values.put(FetchUrlMimeType.USER_AGENT, userAgent);
+
             // We must have long pressed on a link or image to download it. We
             // are not sure of the mimetype in this case, so do a head request
-            new FetchUrlMimeType(this).execute(values);
+            new FetchUrlMimeType(this, request).execute(values);
         } else {
-            final Uri contentUri =
-                    getContentResolver().insert(Downloads.Impl.CONTENT_URI, values);
+            DownloadManager manager
+                    = (DownloadManager) getSystemService(Context.DOWNLOAD_SERVICE);
+            manager.enqueue(request);
         }
         Toast.makeText(this, R.string.download_pending, Toast.LENGTH_SHORT)
                 .show();
@@ -3009,7 +3256,10 @@
      * Update the lock icon to correspond to our latest state.
      */
     private void updateLockIconToLatest() {
-        updateLockIconImage(mTabControl.getCurrentTab().getLockIconType());
+        Tab t = mTabControl.getCurrentTab();
+        if (t != null) {
+            updateLockIconImage(t.getLockIconType());
+        }
     }
 
     /**
@@ -3366,73 +3616,23 @@
     /**
      * Displays an http-authentication dialog.
      */
-    void showHttpAuthentication(final HttpAuthHandler handler,
-            final String host, final String realm, final String title,
-            final String name, final String password, int focusId) {
-        LayoutInflater factory = LayoutInflater.from(this);
-        final View v = factory
-                .inflate(R.layout.http_authentication, null);
-        if (name != null) {
-            ((EditText) v.findViewById(R.id.username_edit)).setText(name);
-        }
-        if (password != null) {
-            ((EditText) v.findViewById(R.id.password_edit)).setText(password);
-        }
-
-        String titleText = title;
-        if (titleText == null) {
-            titleText = getText(R.string.sign_in_to).toString().replace(
-                    "%s1", host).replace("%s2", realm);
-        }
-
-        mHttpAuthHandler = handler;
-        AlertDialog dialog = new AlertDialog.Builder(this)
-                .setTitle(titleText)
-                .setIcon(android.R.drawable.ic_dialog_alert)
-                .setView(v)
-                .setPositiveButton(R.string.action,
-                        new DialogInterface.OnClickListener() {
-                             public void onClick(DialogInterface dialog,
-                                     int whichButton) {
-                                String nm = ((EditText) v
-                                        .findViewById(R.id.username_edit))
-                                        .getText().toString();
-                                String pw = ((EditText) v
-                                        .findViewById(R.id.password_edit))
-                                        .getText().toString();
-                                BrowserActivity.this.setHttpAuthUsernamePassword
-                                        (host, realm, nm, pw);
-                                handler.proceed(nm, pw);
-                                mHttpAuthenticationDialog = null;
-                                mHttpAuthHandler = null;
-                            }})
-                .setNegativeButton(R.string.cancel,
-                        new DialogInterface.OnClickListener() {
-                            public void onClick(DialogInterface dialog,
-                                    int whichButton) {
-                                handler.cancel();
-                                BrowserActivity.this.resetTitleAndRevertLockIcon();
-                                mHttpAuthenticationDialog = null;
-                                mHttpAuthHandler = null;
-                            }})
-                .setOnCancelListener(new DialogInterface.OnCancelListener() {
-                        public void onCancel(DialogInterface dialog) {
-                            handler.cancel();
-                            BrowserActivity.this.resetTitleAndRevertLockIcon();
-                            mHttpAuthenticationDialog = null;
-                            mHttpAuthHandler = null;
-                        }})
-                .create();
-        // Make the IME appear when the dialog is displayed if applicable.
-        dialog.getWindow().setSoftInputMode(
-                WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE);
-        dialog.show();
-        if (focusId != 0) {
-            dialog.findViewById(focusId).requestFocus();
-        } else {
-            v.findViewById(R.id.username_edit).requestFocus();
-        }
-        mHttpAuthenticationDialog = dialog;
+    void showHttpAuthentication(final HttpAuthHandler handler, String host, String realm) {
+        mHttpAuthenticationDialog = new HttpAuthenticationDialog(this, host, realm);
+        mHttpAuthenticationDialog.setOkListener(new HttpAuthenticationDialog.OkListener() {
+            public void onOk(String host, String realm, String username, String password) {
+                BrowserActivity.this.setHttpAuthUsernamePassword(host, realm, username, password);
+                handler.proceed(username, password);
+                mHttpAuthenticationDialog = null;
+            }
+        });
+        mHttpAuthenticationDialog.setCancelListener(new HttpAuthenticationDialog.CancelListener() {
+            public void onCancel() {
+                handler.cancel();
+                BrowserActivity.this.resetTitleAndRevertLockIcon();
+                mHttpAuthenticationDialog = null;
+            }
+        });
+        mHttpAuthenticationDialog.show();
     }
 
     public int getProgress() {
@@ -3503,29 +3703,57 @@
         }
     }
 
+    /**
+     * callback from ComboPage when bookmark/history selection
+     */
+    @Override
+    public void onUrlSelected(String url, boolean newTab) {
+        removeComboView();
+        if (!TextUtils.isEmpty(url)) {
+            if (newTab) {
+                openTab(url, false);
+            } else {
+                final Tab currentTab = mTabControl.getCurrentTab();
+                dismissSubWindow(currentTab);
+                loadUrl(getTopWindow(), url);
+            }
+        }
+    }
+
+    /**
+     * callback from ComboPage when dismissed
+     */
+    @Override
+    public void onComboCanceled() {
+        removeComboView();
+    }
+
+    /**
+     * dismiss the ComboPage
+     */
+    /* package */ void removeComboView() {
+        if (mComboView != null) {
+            mContentView.removeView(mComboView);
+            mTitleBar.setVisibility(View.VISIBLE);
+            mMenuState = R.id.MAIN_MENU;
+            attachTabToContentView(mTabControl.getCurrentTab());
+            getTopWindow().requestFocus();
+            mComboView = null;
+        }
+    }
+
+    /**
+     * callback from ComboPage when clear history is requested
+     */
+    public void onRemoveParentChildRelationships() {
+        mTabControl.removeParentChildRelationShips();
+    }
+
     @Override
     protected void onActivityResult(int requestCode, int resultCode,
                                     Intent intent) {
         if (getTopWindow() == null) return;
-
         switch (requestCode) {
-            case COMBO_PAGE:
-                if (resultCode == RESULT_OK && intent != null) {
-                    String data = intent.getAction();
-                    Bundle extras = intent.getExtras();
-                    if (extras != null && extras.getBoolean("new_window", false)) {
-                        openTab(data);
-                    } else {
-                        final Tab currentTab =
-                                mTabControl.getCurrentTab();
-                        dismissSubWindow(currentTab);
-                        if (data != null && data.length() != 0) {
-                            loadUrl(getTopWindow(), data);
-                        }
-                    }
-                }
-                // Deliberately fall through to PREFERENCES_PAGE, since the
-                // same extra may be attached to the COMBO_PAGE
             case PREFERENCES_PAGE:
                 if (resultCode == RESULT_OK && intent != null) {
                     String action = intent.getStringExtra(Intent.EXTRA_TEXT);
@@ -3539,8 +3767,25 @@
                 if (null == mUploadMessage) break;
                 Uri result = intent == null || resultCode != RESULT_OK ? null
                         : intent.getData();
+
+                // As we ask the camera to save the result of the user taking
+                // a picture, the camera application does not return anything other
+                // than RESULT_OK. So we need to check whether the file we expected
+                // was written to disk in the in the case that we
+                // did not get an intent returned but did get a RESULT_OK. If it was,
+                // we assume that this result has came back from the camera.
+                if (result == null && intent == null && resultCode == RESULT_OK) {
+                    File cameraFile = new File(mCameraFilePath);
+                    if (cameraFile.exists()) {
+                        result = Uri.fromFile(cameraFile);
+                        // Broadcast to the media scanner that we have a new photo
+                        // so it will be added into the gallery for the user.
+                        sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, result));
+                    }
+                }
                 mUploadMessage.onReceiveValue(result);
                 mUploadMessage = null;
+                mCameraFilePath = null;
                 break;
             default:
                 break;
@@ -3564,40 +3809,22 @@
      *                         Otherwise, start with the bookmarks tab.
      */
     /* package */ void bookmarksOrHistoryPicker(boolean startWithHistory) {
-        WebView current = mTabControl.getCurrentWebView();
-        if (current == null) {
+        if (mTabControl.getCurrentWebView() == null) {
             return;
         }
-        Intent intent = new Intent(this,
-                CombinedBookmarkHistoryActivity.class);
-        String title = current.getTitle();
-        String url = current.getUrl();
-        Bitmap thumbnail = createScreenshot(current);
-
-        // Just in case the user opens bookmarks before a page finishes loading
-        // so the current history item, and therefore the page, is null.
-        if (null == url) {
-            url = mLastEnteredUrl;
-            // This can happen.
-            if (null == url) {
-                url = mSettings.getHomePage();
-            }
-        }
-        // In case the web page has not yet received its associated title.
-        if (title == null) {
-            title = url;
-        }
-        intent.putExtra("title", title);
-        intent.putExtra("url", url);
-        intent.putExtra("thumbnail", thumbnail);
+        Bundle extras = new Bundle();
         // Disable opening in a new window if we have maxed out the windows
-        intent.putExtra("disable_new_window", !mTabControl.canCreateNewTab());
-        intent.putExtra("touch_icon_url", current.getTouchIconUrl());
-        if (startWithHistory) {
-            intent.putExtra(CombinedBookmarkHistoryActivity.STARTING_TAB,
-                    CombinedBookmarkHistoryActivity.HISTORY_TAB);
-        }
-        startActivityForResult(intent, COMBO_PAGE);
+        extras.putBoolean(BrowserBookmarksPage.EXTRA_DISABLE_WINDOW,
+                !mTabControl.canCreateNewTab());
+
+        mComboView = new CombinedBookmarkHistoryView(this,
+                startWithHistory ? CombinedBookmarkHistoryView.FRAGMENT_ID_HISTORY
+                        : CombinedBookmarkHistoryView.FRAGMENT_ID_BOOKMARKS,
+                extras);
+        removeTabFromContentView(mTabControl.getCurrentTab());
+        mTitleBar.setVisibility(View.GONE);
+        hideFakeTitleBar();
+        mContentView.addView(mComboView, COVER_SCREEN_PARAMS);
     }
 
     // Called when loading from context menu or LOAD_URL message
@@ -3757,54 +3984,6 @@
         }
     }
 
-    private void packageChanged(String packageName, boolean wasAdded) {
-        WebView w = mTabControl.getCurrentWebView();
-        if (w == null) {
-            return;
-        }
-
-        if (wasAdded) {
-            w.addPackageName(packageName);
-        } else {
-            w.removePackageName(packageName);
-        }
-    }
-
-    private void addPackageNames(Set<String> packageNames) {
-        WebView w = mTabControl.getCurrentWebView();
-        if (w == null) {
-            return;
-        }
-
-        w.addPackageNames(packageNames);
-    }
-
-    private void getInstalledPackages() {
-        AsyncTask<Void, Void, Set<String> > task =
-            new AsyncTask<Void, Void, Set<String> >() {
-            protected Set<String> doInBackground(Void... unused) {
-                Set<String> installedPackages = new HashSet<String>();
-                PackageManager pm = BrowserActivity.this.getPackageManager();
-                if (pm != null) {
-                    List<PackageInfo> packages = pm.getInstalledPackages(0);
-                    for (PackageInfo p : packages) {
-                        if (BrowserActivity.this.sGoogleApps.contains(p.packageName)) {
-                            installedPackages.add(p.packageName);
-                        }
-                    }
-                }
-
-                return installedPackages;
-            }
-
-            // Executes on the UI thread
-            protected void onPostExecute(Set<String> installedPackages) {
-                addPackageNames(installedPackages);
-            }
-        };
-        task.execute();
-    }
-
     final static int LOCK_ICON_UNSECURE = 0;
     final static int LOCK_ICON_SECURE   = 1;
     final static int LOCK_ICON_MIXED    = 2;
@@ -3825,8 +4004,6 @@
     private static final int EMPTY_MENU = -1;
     private Menu mMenu;
 
-    private FindDialog mFindDialog;
-    private SelectDialog mSelectDialog;
     // Used to prevent chording to result in firing two shortcuts immediately
     // one after another.  Fixes bug 1211714.
     boolean mCanChord;
@@ -3897,8 +4074,7 @@
 
     // as HttpAuthentication has different style for landscape / portrait, we
     // have to re-open it when configuration changed
-    private AlertDialog mHttpAuthenticationDialog;
-    private HttpAuthHandler mHttpAuthHandler;
+    private HttpAuthenticationDialog mHttpAuthenticationDialog;
 
     /*package*/ static final FrameLayout.LayoutParams COVER_SCREEN_PARAMS =
                                             new FrameLayout.LayoutParams(
@@ -3934,7 +4110,8 @@
 
     private Toast mStopToast;
 
-    private TitleBar mTitleBar;
+    private TitleBarBase mTitleBar;
+    private TabBar mTabBar;
 
     private LinearLayout mErrorConsoleContainer = null;
     private boolean mShouldShowErrorConsole = false;
@@ -3950,12 +4127,9 @@
     private IntentFilter mNetworkStateChangedFilter;
     private BroadcastReceiver mNetworkStateIntentReceiver;
 
-    private BroadcastReceiver mPackageInstallationReceiver;
-
     private SystemAllowGeolocationOrigins mSystemAllowGeolocationOrigins;
 
     // activity requestCode
-    final static int COMBO_PAGE                 = 1;
     final static int PREFERENCES_PAGE           = 3;
     final static int FILE_SELECTED              = 4;
 
@@ -3964,14 +4138,6 @@
     // the video progress view
     private View mVideoProgressView;
 
-    // The Google packages we monitor for the navigator.isApplicationInstalled()
-    // API. Add as needed.
-    private static Set<String> sGoogleApps;
-    static {
-        sGoogleApps = new HashSet<String>();
-        sGoogleApps.add("com.google.android.youtube");
-    }
-
     /**
      * A UrlData class to abstract how the content will be set to WebView.
      * This base class uses loadUrl to show the content.
diff --git a/src/com/android/browser/BrowserBackupAgent.java b/src/com/android/browser/BrowserBackupAgent.java
index c968ce5..9c5d65b 100644
--- a/src/com/android/browser/BrowserBackupAgent.java
+++ b/src/com/android/browser/BrowserBackupAgent.java
@@ -166,8 +166,11 @@
                                 if (DEBUG) Log.v(TAG, "Did not see url: " + mark.url);
                                 // Right now we do not reconstruct the db entry in its
                                 // entirety; we just add a new bookmark with the same data
-                                Bookmarks.addBookmark(null, getContentResolver(),
-                                        mark.url, mark.title, null, false);
+                                // FIXME: This file needs to be reworked
+                                // anyway For now, add the bookmark at
+                                // the root level.
+                                Bookmarks.addBookmark(this, false,
+                                        mark.url, mark.title, null, false, 0);
                                 nUnique++;
                             } else {
                                 if (DEBUG) Log.v(TAG, "Skipping extant url: " + mark.url);
diff --git a/src/com/android/browser/BrowserBookmarksAdapter.java b/src/com/android/browser/BrowserBookmarksAdapter.java
index 241b33b..a5d51dd 100644
--- a/src/com/android/browser/BrowserBookmarksAdapter.java
+++ b/src/com/android/browser/BrowserBookmarksAdapter.java
@@ -16,567 +16,46 @@
 
 package com.android.browser;
 
-import android.content.ContentResolver;
-import android.content.ContentUris;
-import android.content.ContentValues;
-import android.database.ContentObserver;
+import android.content.Context;
 import android.database.Cursor;
-import android.database.DataSetObserver;
 import android.graphics.Bitmap;
 import android.graphics.BitmapFactory;
-import android.net.Uri;
-import android.os.AsyncTask;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Looper;
-import android.provider.Browser;
-import android.provider.Browser.BookmarkColumns;
-import android.view.KeyEvent;
-import android.view.LayoutInflater;
 import android.view.View;
-import android.view.ViewGroup;
-import android.webkit.WebIconDatabase;
-import android.webkit.WebView;
-import android.widget.BaseAdapter;
 import android.widget.ImageView;
+import android.widget.ResourceCursorAdapter;
 import android.widget.TextView;
 
-import java.io.ByteArrayOutputStream;
-
-class BrowserBookmarksAdapter extends BaseAdapter {
-
-    private String                  mCurrentPage;
-    private String                  mCurrentTitle;
-    private Bitmap                  mCurrentThumbnail;
-    private Cursor                  mCursor;
-    private int                     mCount;
-    private BrowserBookmarksPage    mBookmarksPage;
-    private ContentResolver         mContentResolver;
-    private boolean                 mDataValid;
-    private BookmarkViewMode        mViewMode;
-    private boolean                 mMostVisited;
-    private boolean                 mNeedsOffset;
-    private int                     mExtraOffset;
-
+class BrowserBookmarksAdapter extends ResourceCursorAdapter {
     /**
      *  Create a new BrowserBookmarksAdapter.
-     *  @param b        BrowserBookmarksPage that instantiated this.
-     *                  Necessary so it will adjust its focus
-     *                  appropriately after a search.
      */
-    public BrowserBookmarksAdapter(BrowserBookmarksPage b, String curPage,
-            String curTitle, Bitmap curThumbnail, boolean createShortcut,
-            boolean mostVisited) {
-        mNeedsOffset = !(createShortcut || mostVisited);
-        mMostVisited = mostVisited;
-        mExtraOffset = mNeedsOffset ? 1 : 0;
-        mBookmarksPage = b;
-        mCurrentPage = b.getResources().getString(R.string.current_page)
-                + curPage;
-        mCurrentTitle = curTitle;
-        mCurrentThumbnail = curThumbnail;
-        mContentResolver = b.getContentResolver();
-        mViewMode = BookmarkViewMode.LIST;
+    public BrowserBookmarksAdapter(Context context) {
+        // Make sure to tell the CursorAdapter to avoid the observer and auto-requery
+        // since the Loader will do that for us.
+        super(context, R.layout.bookmark_thumbnail, null);
+    }
 
-        String whereClause;
-        // FIXME: Should have a default sort order that the user selects.
-        String orderBy = Browser.BookmarkColumns.VISITS + " DESC";
-        if (mostVisited) {
-            whereClause = Browser.BookmarkColumns.VISITS + " != 0";
+    @Override
+    public void bindView(View view, Context context, Cursor cursor) {
+        ImageView thumb = (ImageView) view.findViewById(R.id.thumb);
+        TextView tv = (TextView) view.findViewById(R.id.label);
+
+        tv.setText(cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE));
+        Bitmap thumbnail = null;
+        if (cursor.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) != 0) {
+            // folder
+            thumb.setImageResource(R.drawable.ic_folder);
         } else {
-            whereClause = Browser.BookmarkColumns.BOOKMARK + " = 1";
-        }
-        mCursor = b.managedQuery(Browser.BOOKMARKS_URI,
-                Browser.HISTORY_PROJECTION, whereClause, null, orderBy);
-        mCursor.registerContentObserver(new ChangeObserver());
-        mCursor.registerDataSetObserver(new MyDataSetObserver());
-
-        mDataValid = true;
-        notifyDataSetChanged();
-
-        mCount = mCursor.getCount() + mExtraOffset;
-    }
-    
-    /**
-     *  Return a hashmap with one row's Title, Url, and favicon.
-     *  @param position  Position in the list.
-     *  @return Bundle  Stores title, url of row position, favicon, and id
-     *                   for the url.  Return a blank map if position is out of
-     *                   range.
-     */
-    public Bundle getRow(int position) {
-        Bundle map = new Bundle();
-        if (position < mExtraOffset || position >= mCount) {
-            return map;
-        }
-        mCursor.moveToPosition(position- mExtraOffset);
-        String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
-        map.putString(Browser.BookmarkColumns.TITLE, 
-                mCursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX));
-        map.putString(Browser.BookmarkColumns.URL, url);
-        byte[] data = mCursor.getBlob(Browser.HISTORY_PROJECTION_FAVICON_INDEX);
-        if (data != null) {
-            map.putParcelable(Browser.BookmarkColumns.FAVICON,
-                    BitmapFactory.decodeByteArray(data, 0, data.length));
-        }
-        map.putInt("id", mCursor.getInt(Browser.HISTORY_PROJECTION_ID_INDEX));
-        return map;
-    }
-
-    /**
-     *  Update a row in the database with new information. 
-     *  Requeries the database if the information has changed.
-     *  @param map  Bundle storing id, title and url of new information
-     */
-    public void updateRow(Bundle map) {
-
-        // Find the record
-        int id = map.getInt("id");
-        int position = -1;
-        for (mCursor.moveToFirst(); !mCursor.isAfterLast(); mCursor.moveToNext()) {
-            if (mCursor.getInt(Browser.HISTORY_PROJECTION_ID_INDEX) == id) {
-                position = mCursor.getPosition();
-                break;
+            byte[] data = cursor.getBlob(BookmarksLoader.COLUMN_INDEX_THUMBNAIL);
+            if (data != null) {
+                thumbnail = BitmapFactory.decodeByteArray(data, 0, data.length);
             }
-        }
-        if (position < 0) {
-            return;
-        }
 
-        mCursor.moveToPosition(position);
-        ContentValues values = new ContentValues();
-        String title = map.getString(Browser.BookmarkColumns.TITLE);
-        if (!title.equals(mCursor
-                .getString(Browser.HISTORY_PROJECTION_TITLE_INDEX))) {
-            values.put(Browser.BookmarkColumns.TITLE, title);
-        }
-        String url = map.getString(Browser.BookmarkColumns.URL);
-        if (!url.equals(mCursor.
-                getString(Browser.HISTORY_PROJECTION_URL_INDEX))) {
-            values.put(Browser.BookmarkColumns.URL, url);
-        }
-
-        if (map.getBoolean("invalidateThumbnail") == true) {
-            values.put(Browser.BookmarkColumns.THUMBNAIL, new byte[0]);
-        }
-        if (values.size() > 0
-                && mContentResolver.update(Browser.BOOKMARKS_URI, values,
-                        "_id = " + id, null) != -1) {
-            refreshList();
-        }
-    }
-
-    /**
-     *  Delete a row from the database.  Requeries the database.  
-     *  Does nothing if the provided position is out of range.
-     *  @param position Position in the list.
-     */
-    public void deleteRow(int position) {
-        if (position < mExtraOffset || position >= getCount()) {
-            return;
-        }
-        mCursor.moveToPosition(position- mExtraOffset);
-        String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
-        String title = mCursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX);
-        Bookmarks.removeFromBookmarks(null, mContentResolver, url, title);
-        refreshList();
-    }
-    
-    /**
-     *  Delete all bookmarks from the db. Requeries the database.  
-     *  All bookmarks with become visited URLs or if never visited 
-     *  are removed
-     */
-    public void deleteAllRows() {
-        StringBuilder deleteIds = null;
-        StringBuilder convertIds = null;
-        
-        for (mCursor.moveToFirst(); !mCursor.isAfterLast(); mCursor.moveToNext()) {
-            String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
-            WebIconDatabase.getInstance().releaseIconForPageUrl(url);
-            int id = mCursor.getInt(Browser.HISTORY_PROJECTION_ID_INDEX);
-            int numVisits = mCursor.getInt(Browser.HISTORY_PROJECTION_VISITS_INDEX);
-            if (0 == numVisits) {
-                if (deleteIds == null) {
-                    deleteIds = new StringBuilder();
-                    deleteIds.append("( ");
-                } else {
-                    deleteIds.append(" OR ( ");
-                }
-                deleteIds.append(BookmarkColumns._ID);
-                deleteIds.append(" = ");
-                deleteIds.append(id);
-                deleteIds.append(" )");
-            } else {
-                // It is no longer a bookmark, but it is still a visited site.
-                if (convertIds == null) {
-                    convertIds = new StringBuilder();
-                    convertIds.append("( ");
-                } else {
-                    convertIds.append(" OR ( ");
-                }
-                convertIds.append(BookmarkColumns._ID);
-                convertIds.append(" = ");
-                convertIds.append(id);
-                convertIds.append(" )");
-            }
-        }
-        
-        if (deleteIds != null) {
-            mContentResolver.delete(Browser.BOOKMARKS_URI, deleteIds.toString(), 
-                null);
-        }
-        if (convertIds != null) {
-            ContentValues values = new ContentValues();
-            values.put(Browser.BookmarkColumns.BOOKMARK, 0);
-            mContentResolver.update(Browser.BOOKMARKS_URI, values, 
-                    convertIds.toString(), null);
-        }
-        refreshList();
-    }
-
-    /**
-     *  Refresh list to recognize a change in the database.
-     */
-    public void refreshList() {
-        mCursor.requery();
-        mCount = mCursor.getCount() + mExtraOffset;
-        notifyDataSetChanged();
-    }
-
-    /**
-     * Update the bookmark's favicon. This is a convenience method for updating
-     * a bookmark favicon for the originalUrl and url of the passed in WebView.
-     * @param cr The ContentResolver to use.
-     * @param originalUrl The original url before any redirects.
-     * @param url The current url.
-     * @param favicon The favicon bitmap to write to the db.
-     */
-    /* package */ static void updateBookmarkFavicon(final ContentResolver cr,
-            final String originalUrl, final String url, final Bitmap favicon) {
-        new AsyncTask<Void, Void, Void>() {
-            protected Void doInBackground(Void... unused) {
-                final Cursor c =
-                        queryBookmarksForUrl(cr, originalUrl, url, true);
-                if (c == null) {
-                    return null;
-                }
-                if (c.moveToFirst()) {
-                    ContentValues values = new ContentValues();
-                    final ByteArrayOutputStream os =
-                            new ByteArrayOutputStream();
-                    favicon.compress(Bitmap.CompressFormat.PNG, 100, os);
-                    values.put(Browser.BookmarkColumns.FAVICON,
-                            os.toByteArray());
-                    do {
-                        cr.update(ContentUris.withAppendedId(
-                                Browser.BOOKMARKS_URI, c.getInt(0)),
-                                values, null, null);
-                    } while (c.moveToNext());
-                }
-                c.close();
-                return null;
-            }
-        }.execute();
-    }
-
-    /* package */ static Cursor queryBookmarksForUrl(ContentResolver cr,
-            String originalUrl, String url, boolean onlyBookmarks) {
-        if (cr == null || url == null) {
-            return null;
-        }
-
-        // If originalUrl is null, just set it to url.
-        if (originalUrl == null) {
-            originalUrl = url;
-        }
-
-        // Look for both the original url and the actual url. This takes in to
-        // account redirects.
-        String originalUrlNoQuery = removeQuery(originalUrl);
-        String urlNoQuery = removeQuery(url);
-        originalUrl = originalUrlNoQuery + '?';
-        url = urlNoQuery + '?';
-
-        // Use NoQuery to search for the base url (i.e. if the url is
-        // http://www.yahoo.com/?rs=1, search for http://www.yahoo.com)
-        // Use url to match the base url with other queries (i.e. if the url is
-        // http://www.google.com/m, search for
-        // http://www.google.com/m?some_query)
-        final String[] selArgs = new String[] {
-            originalUrlNoQuery, urlNoQuery, originalUrl, url };
-        String where = BookmarkColumns.URL + " == ? OR "
-                + BookmarkColumns.URL + " == ? OR "
-                + BookmarkColumns.URL + " LIKE ? || '%' OR "
-                + BookmarkColumns.URL + " LIKE ? || '%'";
-        if (onlyBookmarks) {
-            where = "(" + where + ") AND " + BookmarkColumns.BOOKMARK + " == 1";
-        }
-        final String[] projection =
-                new String[] { Browser.BookmarkColumns._ID };
-        return cr.query(Browser.BOOKMARKS_URI, projection, where, selArgs,
-                null);
-    }
-
-    // Strip the query from the given url.
-    private static String removeQuery(String url) {
-        if (url == null) {
-            return null;
-        }
-        int query = url.indexOf('?');
-        String noQuery = url;
-        if (query != -1) {
-            noQuery = url.substring(0, query);
-        }
-        return noQuery;
-    }
-
-    /**
-     * How many items should be displayed in the list.
-     * @return Count of items.
-     */
-    public int getCount() {
-        if (mDataValid) {
-            return mCount;
-        } else {
-            return 0;
-        }
-    }
-
-    public boolean areAllItemsEnabled() {
-        return true;
-    }
-
-    public boolean isEnabled(int position) {
-        return true;
-    }
-
-    /**
-     * Get the data associated with the specified position in the list.
-     * @param position Index of the item whose data we want.
-     * @return The data at the specified position.
-     */
-    public Object getItem(int position) {
-        return null;
-    }
-
-    /**
-     * Get the row id associated with the specified position in the list.
-     * @param position Index of the item whose row id we want.
-     * @return The id of the item at the specified position.
-     */
-    public long getItemId(int position) {
-        return position;
-    }
-
-    /* package */ void switchViewMode(BookmarkViewMode viewMode) {
-        mViewMode = viewMode;
-    }
-
-    /* package */ void populateBookmarkItem(BookmarkItem b, int position) {
-        mCursor.moveToPosition(position - mExtraOffset);
-        String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
-        b.setUrl(url);
-        b.setName(mCursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX));
-        byte[] data = mCursor.getBlob(Browser.HISTORY_PROJECTION_FAVICON_INDEX);
-        Bitmap bitmap = null;
-        if (data == null) {
-            bitmap = CombinedBookmarkHistoryActivity.getIconListenerSet()
-                    .getFavicon(url);
-        } else {
-            bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);
-        }
-        b.setFavicon(bitmap);
-    }
-
-    /**
-     * Get a View that displays the data at the specified position
-     * in the list.
-     * @param position Index of the item whose view we want.
-     * @return A View corresponding to the data at the specified position.
-     */
-    public View getView(int position, View convertView, ViewGroup parent) {
-        if (!mDataValid) {
-            throw new IllegalStateException(
-                    "this should only be called when the cursor is valid");
-        }
-        if (position < 0 || position > mCount) {
-            throw new AssertionError(
-                    "BrowserBookmarksAdapter tried to get a view out of range");
-        }
-        if (mViewMode == BookmarkViewMode.GRID) {
-            if (convertView == null || convertView instanceof AddNewBookmark
-                    || convertView instanceof BookmarkItem) {
-                LayoutInflater factory = LayoutInflater.from(mBookmarksPage);
-                convertView
-                        = factory.inflate(R.layout.bookmark_thumbnail, null);
-            }
-            View holder = convertView.findViewById(R.id.holder);
-            ImageView thumb = (ImageView) convertView.findViewById(R.id.thumb);
-            TextView tv = (TextView) convertView.findViewById(R.id.label);
-
-            if (0 == position && mNeedsOffset) {
-                // This is to create a bookmark for the current page.
-                holder.setVisibility(View.VISIBLE);
-                tv.setText(mCurrentTitle);
-
-                if (mCurrentThumbnail != null) {
-                    thumb.setImageBitmap(mCurrentThumbnail);
-                } else {
-                    thumb.setImageResource(
-                            R.drawable.browser_thumbnail);
-                }
-                return convertView;
-            }
-            holder.setVisibility(View.GONE);
-            mCursor.moveToPosition(position - mExtraOffset);
-            tv.setText(mCursor.getString(
-                    Browser.HISTORY_PROJECTION_TITLE_INDEX));
-            Bitmap thumbnail = getScreenshot(position);
             if (thumbnail == null) {
                 thumb.setImageResource(R.drawable.browser_thumbnail);
             } else {
                 thumb.setImageBitmap(thumbnail);
             }
-
-            return convertView;
-
-        }
-        if (position == 0 && mNeedsOffset) {
-            AddNewBookmark b;
-            if (convertView instanceof AddNewBookmark) {
-                b = (AddNewBookmark) convertView;
-            } else {
-                b = new AddNewBookmark(mBookmarksPage);
-            }
-            b.setUrl(mCurrentPage);
-            return b;
-        }
-        if (mMostVisited) {
-            if (convertView == null || !(convertView instanceof HistoryItem)) {
-                convertView = new HistoryItem(mBookmarksPage);
-            }
-        } else {
-            if (convertView == null || !(convertView instanceof BookmarkItem)) {
-                convertView = new BookmarkItem(mBookmarksPage);
-            }
-        }
-        bind((BookmarkItem) convertView, position);
-        if (mMostVisited) {
-            ((HistoryItem) convertView).setIsBookmark(
-                    getIsBookmark(position));
-        }
-        return convertView;
-    }
-
-    /**
-     *  Return the title for this item in the list.
-     */
-    public String getTitle(int position) {
-        return getString(Browser.HISTORY_PROJECTION_TITLE_INDEX, position);
-    }
-
-    /**
-     *  Return the Url for this item in the list.
-     */
-    public String getUrl(int position) {
-        return getString(Browser.HISTORY_PROJECTION_URL_INDEX, position);
-    }
-
-    /**
-     * Return the screenshot for this item in the list.
-     */
-    public Bitmap getScreenshot(int position) {
-        return getBitmap(Browser.HISTORY_PROJECTION_THUMBNAIL_INDEX, position);
-    }
-
-    /**
-     * Return the favicon for this item in the list.
-     */
-    public Bitmap getFavicon(int position) {
-        return getBitmap(Browser.HISTORY_PROJECTION_FAVICON_INDEX, position);
-    }
-
-    public Bitmap getTouchIcon(int position) {
-        return getBitmap(Browser.HISTORY_PROJECTION_TOUCH_ICON_INDEX, position);
-    }
-
-    private Bitmap getBitmap(int cursorIndex, int position) {
-        if (position < mExtraOffset || position > mCount) {
-            return null;
-        }
-        mCursor.moveToPosition(position - mExtraOffset);
-        byte[] data = mCursor.getBlob(cursorIndex);
-        if (data == null) {
-            return null;
-        }
-        return BitmapFactory.decodeByteArray(data, 0, data.length);
-    }
-
-    /**
-     * Return whether or not this item represents a bookmarked site.
-     */
-    public boolean getIsBookmark(int position) {
-        if (position < mExtraOffset || position > mCount) {
-            return false;
-        }
-        mCursor.moveToPosition(position - mExtraOffset);
-        return (1 == mCursor.getInt(Browser.HISTORY_PROJECTION_BOOKMARK_INDEX));
-    }
-
-    /**
-     * Private helper function to return the title or url.
-     */
-    private String getString(int cursorIndex, int position) {
-        if (position < mExtraOffset || position > mCount) {
-            return "";
-        }
-        mCursor.moveToPosition(position- mExtraOffset);
-        return mCursor.getString(cursorIndex);
-    }
-
-    private void bind(BookmarkItem b, int position) {
-        mCursor.moveToPosition(position- mExtraOffset);
-
-        b.setName(mCursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX));
-        String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
-        b.setUrl(url);
-        byte[] data = mCursor.getBlob(Browser.HISTORY_PROJECTION_FAVICON_INDEX);
-        if (data != null) {
-            b.setFavicon(BitmapFactory.decodeByteArray(data, 0, data.length));
-        } else {
-            b.setFavicon(CombinedBookmarkHistoryActivity.getIconListenerSet()
-                    .getFavicon(url));
-        }
-    }
-
-    private class ChangeObserver extends ContentObserver {
-        public ChangeObserver() {
-            super(new Handler(Looper.getMainLooper()));
-        }
-
-        @Override
-        public boolean deliverSelfNotifications() {
-            return true;
-        }
-
-        @Override
-        public void onChange(boolean selfChange) {
-            refreshList();
-        }
-    }
-    
-    private class MyDataSetObserver extends DataSetObserver {
-        @Override
-        public void onChanged() {
-            mDataValid = true;
-            notifyDataSetChanged();
-        }
-
-        @Override
-        public void onInvalidated() {
-            mDataValid = false;
-            notifyDataSetInvalidated();
         }
     }
 }
diff --git a/src/com/android/browser/BrowserBookmarksPage.java b/src/com/android/browser/BrowserBookmarksPage.java
index dd01009..4a3ae1f 100644
--- a/src/com/android/browser/BrowserBookmarksPage.java
+++ b/src/com/android/browser/BrowserBookmarksPage.java
@@ -18,73 +18,227 @@
 
 import android.app.Activity;
 import android.app.AlertDialog;
+import android.app.Fragment;
+import android.app.LoaderManager;
+import android.content.ClipData;
+import android.content.ClipboardManager;
+import android.content.ContentResolver;
+import android.content.ContentUris;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.CursorLoader;
 import android.content.DialogInterface;
 import android.content.Intent;
+import android.content.Loader;
 import android.content.SharedPreferences;
-import android.content.SharedPreferences.Editor;
+import android.database.Cursor;
 import android.graphics.Bitmap;
 import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.PorterDuff;
-import android.graphics.PorterDuffXfermode;
-import android.graphics.Rect;
-import android.graphics.RectF;
 import android.net.Uri;
-import android.os.AsyncTask;
 import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
-import android.os.ServiceManager;
-import android.provider.Browser;
-import android.text.IClipboard;
-import android.util.Log;
+import android.preference.PreferenceManager;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Accounts;
+import android.text.TextUtils;
 import android.view.ContextMenu;
-import android.view.Menu;
+import android.view.ContextMenu.ContextMenuInfo;
+import android.view.LayoutInflater;
 import android.view.MenuInflater;
 import android.view.MenuItem;
 import android.view.View;
 import android.view.ViewGroup;
-import android.view.ContextMenu.ContextMenuInfo;
 import android.webkit.WebIconDatabase.IconListener;
+import android.widget.Adapter;
 import android.widget.AdapterView;
+import android.widget.AdapterView.OnItemClickListener;
+import android.widget.AdapterView.OnItemSelectedListener;
 import android.widget.GridView;
-import android.widget.ListView;
 import android.widget.Toast;
 
-/*package*/ enum BookmarkViewMode { NONE, GRID, LIST }
 /**
  *  View showing the user's bookmarks in the browser.
  */
-public class BrowserBookmarksPage extends Activity implements
-        View.OnCreateContextMenuListener {
+public class BrowserBookmarksPage extends Fragment implements View.OnCreateContextMenuListener,
+        LoaderManager.LoaderCallbacks<Cursor>, OnItemClickListener, IconListener,
+        OnItemSelectedListener {
 
-    private BookmarkViewMode        mViewMode = BookmarkViewMode.NONE;
-    private GridView                mGridPage;
-    private ListView                mVerticalList;
-    private BrowserBookmarksAdapter mBookmarksAdapter;
-    private static final int        BOOKMARKS_SAVE = 1;
-    private boolean                 mDisableNewWindow;
-    private BookmarkItem            mContextHeader;
-    private AddNewBookmark          mAddHeader;
-    private boolean                 mCanceled = false;
-    private boolean                 mCreateShortcut;
-    private boolean                 mMostVisited;
-    private View                    mEmptyView;
-    private int                     mIconSize;
-    // XXX: There is no public string defining this intent so if Home changes
-    // the value, we have to update this string.
-    private static final String     INSTALL_SHORTCUT =
-            "com.android.launcher.action.INSTALL_SHORTCUT";
+    static final int BOOKMARKS_SAVE = 1;
+    static final String LOGTAG = "browser";
 
-    private final static String LOGTAG = "browser";
-    private final static String PREF_BOOKMARK_VIEW_MODE = "pref_bookmark_view_mode";
-    private final static String PREF_MOST_VISITED_VIEW_MODE = "pref_most_visited_view_mode";
+    static final int LOADER_BOOKMARKS = 1;
+    static final int LOADER_ACCOUNTS_THEN_BOOKMARKS = 2;
+
+    static final String EXTRA_SHORTCUT = "create_shortcut";
+    static final String EXTRA_DISABLE_WINDOW = "disable_new_window";
+
+    static final String ACCOUNT_NAME_UNSYNCED = "Unsynced";
+
+    public static final String PREF_ACCOUNT_TYPE = "acct_type";
+    public static final String PREF_ACCOUNT_NAME = "acct_name";
+
+    static final String DEFAULT_ACCOUNT = "local";
+
+    BookmarksHistoryCallbacks mCallbacks;
+    GridView mGrid;
+    BrowserBookmarksAdapter mAdapter;
+    boolean mDisableNewWindow;
+    BookmarkItem mContextHeader;
+    boolean mCanceled = false;
+    boolean mCreateShortcut;
+    View mEmptyView;
+
+    BreadCrumbView mCrumbs;
+
+    static BrowserBookmarksPage newInstance(BookmarksHistoryCallbacks cb,
+            BreadCrumbView crumbs, Bundle args) {
+        BrowserBookmarksPage bbp = new BrowserBookmarksPage();
+        bbp.mCallbacks = cb;
+        bbp.setArguments(args);
+        bbp.mCrumbs = crumbs;
+        return bbp;
+    }
+
+    @Override
+    public Loader<Cursor> onCreateLoader(int id, Bundle args) {
+        switch (id) {
+            case LOADER_BOOKMARKS: {
+                String accountType = null;
+                String accountName = null;
+                if (args != null) {
+                    accountType = args.getString(BookmarksLoader.ARG_ACCOUNT_TYPE);
+                    accountName = args.getString(BookmarksLoader.ARG_ACCOUNT_NAME);
+                }
+                BookmarksLoader bl = new BookmarksLoader(getActivity(), accountType, accountName);
+                if (mCrumbs != null) {
+                    Uri uri = (Uri) mCrumbs.getTopData();
+                    if (uri != null) {
+                        bl.setUri(uri);
+                    }
+                }
+                return bl;
+            }
+            case LOADER_ACCOUNTS_THEN_BOOKMARKS: {
+                return new CursorLoader(getActivity(), Accounts.CONTENT_URI,
+                        new String[] { Accounts.ACCOUNT_TYPE, Accounts.ACCOUNT_NAME }, null, null,
+                        null);
+            }
+        }
+        throw new UnsupportedOperationException("Unknown loader id " + id);
+    }
+
+    @Override
+    public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
+        switch (loader.getId()) {
+            case LOADER_BOOKMARKS: {
+                // Set the visibility of the empty vs. content views
+                if (cursor == null || cursor.getCount() == 0) {
+                    mEmptyView.setVisibility(View.VISIBLE);
+                    mGrid.setVisibility(View.GONE);
+                } else {
+                    mEmptyView.setVisibility(View.GONE);
+                    mGrid.setVisibility(View.VISIBLE);
+                }
+
+                // Give the new data to the adapter
+                mAdapter.changeCursor(cursor);
+                break;
+            }
+
+            case LOADER_ACCOUNTS_THEN_BOOKMARKS: {
+                SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(
+                        getActivity());
+                String storedAccountType = prefs.getString(PREF_ACCOUNT_TYPE, null);
+                String storedAccountName = prefs.getString(PREF_ACCOUNT_NAME, null);
+                String accountType =
+                        TextUtils.isEmpty(storedAccountType) ? DEFAULT_ACCOUNT : storedAccountType;
+                String accountName =
+                        TextUtils.isEmpty(storedAccountName) ? DEFAULT_ACCOUNT : storedAccountName;
+
+                Bundle args = null;
+                if (cursor == null || !cursor.moveToFirst()) {
+                    // No accounts, set the prefs to the default
+                    accountType = DEFAULT_ACCOUNT;
+                    accountName = DEFAULT_ACCOUNT;
+                } else {
+                    int accountPosition = -1;
+
+                    if (!DEFAULT_ACCOUNT.equals(accountType) &&
+                            !DEFAULT_ACCOUNT.equals(accountName)) {
+                        // Check to see if the account in prefs still exists
+                        cursor.moveToFirst();
+                        do {
+                            if (accountType.equals(cursor.getString(0))
+                                    && accountName.equals(cursor.getString(1))) {
+                                accountPosition = cursor.getPosition();
+                                break;
+                            }
+                        } while (cursor.moveToNext());
+                    }
+
+                    if (accountPosition == -1) {
+                        if (!(DEFAULT_ACCOUNT.equals(accountType)
+                                && DEFAULT_ACCOUNT.equals(accountName))) {
+                            // No account is set in prefs and there is at least one,
+                            // so pick the first one as the default
+                            cursor.moveToFirst();
+                            accountType = cursor.getString(0);
+                            accountName = cursor.getString(1);
+                        }
+                    }
+
+                    args = new Bundle();
+                    args.putString(BookmarksLoader.ARG_ACCOUNT_TYPE, accountType);
+                    args.putString(BookmarksLoader.ARG_ACCOUNT_NAME, accountName);
+                }
+
+                // The stored account name wasn't found, update the stored account with a valid one
+                if (!accountType.equals(storedAccountType)
+                        || !accountName.equals(storedAccountName)) {
+                    prefs.edit()
+                            .putString(PREF_ACCOUNT_TYPE, accountType)
+                            .putString(PREF_ACCOUNT_NAME, accountName)
+                            .apply();
+                }
+                getLoaderManager().initLoader(LOADER_BOOKMARKS, args, this);
+
+                break;
+            }
+        }
+    }
+
+    long getFolderId() {
+        LoaderManager manager = getLoaderManager();
+        BookmarksLoader loader =
+                (BookmarksLoader) ((Loader)(manager.getLoader(LOADER_BOOKMARKS)));
+
+        Uri uri = loader.getUri();
+        if (uri != null) {
+            try {
+                return ContentUris.parseId(uri);
+            } catch (NumberFormatException nfx) {
+                return -1;
+            }
+        }
+        return -1;
+    }
+
+    public void onFolderChange(int level, Object data) {
+        Uri uri = (Uri) data;
+        if (uri == null) {
+            // top level
+            uri = BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER;
+        }
+        LoaderManager manager = getLoaderManager();
+        BookmarksLoader loader =
+                (BookmarksLoader) ((Loader) manager.getLoader(LOADER_BOOKMARKS));
+        loader.setUri(uri);
+        loader.forceLoad();
+
+    }
 
     @Override
     public boolean onContextItemSelected(MenuItem item) {
+        final Activity activity = getActivity();
         // It is possible that the view has been canceled when we get to
         // this point as back has a higher priority
         if (mCanceled) {
@@ -98,9 +252,6 @@
         }
 
         switch (item.getItemId()) {
-        case R.id.new_context_menu_id:
-            saveCurrentPage();
-            break;
         case R.id.open_context_menu_id:
             loadUrl(i.position);
             break;
@@ -108,652 +259,354 @@
             editBookmark(i.position);
             break;
         case R.id.shortcut_context_menu_id:
-            final Intent send = createShortcutIntent(i.position);
-            send.setAction(INSTALL_SHORTCUT);
-            sendBroadcast(send);
+            activity.sendBroadcast(createShortcutIntent(i.position));
             break;
         case R.id.delete_context_menu_id:
-            if (mMostVisited) {
-                Browser.deleteFromHistory(getContentResolver(),
-                        getUrl(i.position));
-                refreshList();
-            } else {
-                displayRemoveBookmarkDialog(i.position);
-            }
+            displayRemoveBookmarkDialog(i.position);
             break;
         case R.id.new_window_context_menu_id:
             openInNewWindow(i.position);
             break;
-        case R.id.share_link_context_menu_id:
-            BrowserActivity.sharePage(BrowserBookmarksPage.this,
-                    mBookmarksAdapter.getTitle(i.position), getUrl(i.position),
-                    getFavicon(i.position),
-                    mBookmarksAdapter.getScreenshot(i.position));
+        case R.id.share_link_context_menu_id: {
+            Cursor cursor = (Cursor) mAdapter.getItem(i.position);
+            BrowserActivity.sharePage(activity,
+                    cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE),
+                    cursor.getString(BookmarksLoader.COLUMN_INDEX_URL),
+                    getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_FAVICON),
+                    getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_THUMBNAIL));
             break;
+        }
         case R.id.copy_url_context_menu_id:
             copy(getUrl(i.position));
             break;
-        case R.id.homepage_context_menu_id:
-            BrowserSettings.getInstance().setHomePage(this,
-                    getUrl(i.position));
-            Toast.makeText(this, R.string.homepage_set,
-                    Toast.LENGTH_LONG).show();
+        case R.id.homepage_context_menu_id: {
+            BrowserSettings.getInstance().setHomePage(activity, getUrl(i.position));
+            Toast.makeText(activity, R.string.homepage_set, Toast.LENGTH_LONG).show();
             break;
+        }
         // Only for the Most visited page
-        case R.id.save_to_bookmarks_menu_id:
-            boolean isBookmark;
-            String name;
-            String url;
-            if (mViewMode == BookmarkViewMode.GRID) {
-                isBookmark = mBookmarksAdapter.getIsBookmark(i.position);
-                name = mBookmarksAdapter.getTitle(i.position);
-                url = mBookmarksAdapter.getUrl(i.position);
-            } else {
-                HistoryItem historyItem = ((HistoryItem) i.targetView);
-                isBookmark = historyItem.isBookmark();
-                name = historyItem.getName();
-                url = historyItem.getUrl();
-            }
+        case R.id.save_to_bookmarks_menu_id: {
+            Cursor cursor = (Cursor) mAdapter.getItem(i.position);
+            String name = cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE);
+            String url = cursor.getString(BookmarksLoader.COLUMN_INDEX_URL);
             // If the site is bookmarked, the item becomes remove from
             // bookmarks.
-            if (isBookmark) {
-                Bookmarks.removeFromBookmarks(this, getContentResolver(), url, name);
-            } else {
-                Browser.saveBookmark(this, name, url);
-            }
+            Bookmarks.removeFromBookmarks(activity, activity.getContentResolver(), url, name);
             break;
+        }
         default:
             return super.onContextItemSelected(item);
         }
         return true;
     }
 
-    @Override
-    public void onCreateContextMenu(ContextMenu menu, View v,
-                ContextMenuInfo menuInfo) {
-            AdapterView.AdapterContextMenuInfo i =
-                    (AdapterView.AdapterContextMenuInfo) menuInfo;
-
-            MenuInflater inflater = getMenuInflater();
-            if (mMostVisited) {
-                inflater.inflate(R.menu.historycontext, menu);
-            } else {
-                inflater.inflate(R.menu.bookmarkscontext, menu);
-            }
-
-            if (0 == i.position && !mMostVisited) {
-                menu.setGroupVisible(R.id.CONTEXT_MENU, false);
-                if (mAddHeader == null) {
-                    mAddHeader = new AddNewBookmark(BrowserBookmarksPage.this);
-                } else if (mAddHeader.getParent() != null) {
-                    ((ViewGroup) mAddHeader.getParent()).
-                            removeView(mAddHeader);
-                }
-                mAddHeader.setUrl(getIntent().getStringExtra("url"));
-                menu.setHeaderView(mAddHeader);
-                return;
-            }
-            if (mMostVisited) {
-                if ((mViewMode == BookmarkViewMode.LIST
-                        && ((HistoryItem) i.targetView).isBookmark())
-                        || mBookmarksAdapter.getIsBookmark(i.position)) {
-                    MenuItem item = menu.findItem(
-                            R.id.save_to_bookmarks_menu_id);
-                    item.setTitle(R.string.remove_from_bookmarks);
-                }
-            } else {
-                // The historycontext menu has no ADD_MENU group.
-                menu.setGroupVisible(R.id.ADD_MENU, false);
-            }
-            if (mDisableNewWindow) {
-                menu.findItem(R.id.new_window_context_menu_id).setVisible(
-                        false);
-            }
-            if (mContextHeader == null) {
-                mContextHeader = new BookmarkItem(BrowserBookmarksPage.this);
-            } else if (mContextHeader.getParent() != null) {
-                ((ViewGroup) mContextHeader.getParent()).
-                        removeView(mContextHeader);
-            }
-            if (mViewMode == BookmarkViewMode.GRID) {
-                mBookmarksAdapter.populateBookmarkItem(mContextHeader,
-                        i.position);
-            } else {
-                BookmarkItem b = (BookmarkItem) i.targetView;
-                b.copyTo(mContextHeader);
-            }
-            menu.setHeaderView(mContextHeader);
+    Bitmap getBitmap(Cursor cursor, int columnIndex) {
+        byte[] data = cursor.getBlob(columnIndex);
+        if (data == null) {
+            return null;
         }
+        return BitmapFactory.decodeByteArray(data, 0, data.length);
+    }
+
+    @Override
+    public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
+        AdapterView.AdapterContextMenuInfo info = (AdapterView.AdapterContextMenuInfo) menuInfo;
+        Cursor cursor = (Cursor) mAdapter.getItem(info.position);
+        boolean isFolder
+                = cursor.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) != 0;
+        if (isFolder) return;
+
+        final Activity activity = getActivity();
+        MenuInflater inflater = activity.getMenuInflater();
+        inflater.inflate(R.menu.bookmarkscontext, menu);
+
+        if (mDisableNewWindow) {
+            menu.findItem(R.id.new_window_context_menu_id).setVisible(false);
+        }
+
+        if (mContextHeader == null) {
+            mContextHeader = new BookmarkItem(activity);
+        } else if (mContextHeader.getParent() != null) {
+            ((ViewGroup) mContextHeader.getParent()).removeView(mContextHeader);
+        }
+
+        populateBookmarkItem(cursor, mContextHeader);
+
+        menu.setHeaderView(mContextHeader);
+    }
+
+    private void populateBookmarkItem(Cursor cursor, BookmarkItem item) {
+        String url = cursor.getString(BookmarksLoader.COLUMN_INDEX_URL);
+        item.setUrl(url);
+        item.setName(cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE));
+        Bitmap bitmap = getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_FAVICON);
+        if (bitmap == null) {
+            bitmap = CombinedBookmarkHistoryView.getIconListenerSet().getFavicon(url);
+        }
+        item.setFavicon(bitmap);
+    }
 
     /**
      *  Create a new BrowserBookmarksPage.
      */
     @Override
-    protected void onCreate(Bundle icicle) {
+    public void onCreate(Bundle icicle) {
         super.onCreate(icicle);
 
-        // Grab the app icon size as a resource.
-        mIconSize = getResources().getDimensionPixelSize(
-                android.R.dimen.app_icon_size);
-
-        Intent intent = getIntent();
-        if (Intent.ACTION_CREATE_SHORTCUT.equals(intent.getAction())) {
-            mCreateShortcut = true;
-        }
-        mDisableNewWindow = intent.getBooleanExtra("disable_new_window",
-                false);
-        mMostVisited = intent.getBooleanExtra("mostVisited", false);
-
-        if (mCreateShortcut) {
-            setTitle(R.string.browser_bookmarks_page_bookmarks_text);
-        }
-
-        setContentView(R.layout.empty_history);
-        mEmptyView = findViewById(R.id.empty_view);
-        mEmptyView.setVisibility(View.GONE);
-
-        SharedPreferences p = getPreferences(MODE_PRIVATE);
-
-        // See if the user has set a preference for the view mode of their
-        // bookmarks. Otherwise default to grid mode.
-        BookmarkViewMode preference = BookmarkViewMode.NONE;
-        if (mMostVisited) {
-            // For the most visited page, only use list mode.
-            preference = BookmarkViewMode.LIST;
-        } else {
-            preference = BookmarkViewMode.values()[p.getInt(
-                    PREF_BOOKMARK_VIEW_MODE, BookmarkViewMode.GRID.ordinal())];
-        }
-        switchViewMode(preference);
-
-        final boolean createShortcut = mCreateShortcut;
-        final boolean mostVisited = mMostVisited;
-        final String url = intent.getStringExtra("url");
-        final String title = intent.getStringExtra("title");
-        final Bitmap thumbnail =
-                (Bitmap) intent.getParcelableExtra("thumbnail");
-        new AsyncTask<Void, Void, Void>() {
-            @Override
-            protected Void doInBackground(Void... unused) {
-                BrowserBookmarksAdapter adapter = new BrowserBookmarksAdapter(
-                        BrowserBookmarksPage.this,
-                        url,
-                        title,
-                        thumbnail,
-                        createShortcut,
-                        mostVisited);
-                mHandler.obtainMessage(ADAPTER_CREATED, adapter).sendToTarget();
-                return null;
-            }
-        }.execute();
+        Bundle args = getArguments();
+        mCreateShortcut = args == null ? false : args.getBoolean(EXTRA_SHORTCUT, false);
+        mDisableNewWindow = args == null ? false : args.getBoolean(EXTRA_DISABLE_WINDOW, false);
     }
 
     @Override
-    protected void onDestroy() {
-        mHandler.removeCallbacksAndMessages(null);
-        super.onDestroy();
+    public View onCreateView(LayoutInflater inflater, ViewGroup container,
+            Bundle savedInstanceState) {
+        Context context = getActivity();
+
+        View root = inflater.inflate(R.layout.bookmarks, container, false);
+        mEmptyView = root.findViewById(android.R.id.empty);
+
+        mGrid = (GridView) root.findViewById(R.id.grid);
+        mGrid.setOnItemClickListener(this);
+        mGrid.setColumnWidth(BrowserActivity.getDesiredThumbnailWidth(getActivity()));
+        if (!mCreateShortcut) {
+            mGrid.setOnCreateContextMenuListener(this);
+        }
+
+        mAdapter = new BrowserBookmarksAdapter(getActivity());
+        mGrid.setAdapter(mAdapter);
+
+        // Start the loaders
+        LoaderManager lm = getLoaderManager();
+        SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
+        String accountType = prefs.getString(PREF_ACCOUNT_TYPE, DEFAULT_ACCOUNT);
+        String accountName = prefs.getString(PREF_ACCOUNT_NAME, DEFAULT_ACCOUNT);
+        if (!TextUtils.isEmpty(accountType) && !TextUtils.isEmpty(accountName)) {
+            // There is an account set, load up that one
+            Bundle args = null;
+            if (!DEFAULT_ACCOUNT.equals(accountType) && !DEFAULT_ACCOUNT.equals(accountName)) {
+                args = new Bundle();
+                args.putString(BookmarksLoader.ARG_ACCOUNT_TYPE, accountType);
+                args.putString(BookmarksLoader.ARG_ACCOUNT_NAME, accountName);
+            }
+            lm.restartLoader(LOADER_BOOKMARKS, args, this);
+        } else {
+            // No account set, load the account list first
+            lm.restartLoader(LOADER_ACCOUNTS_THEN_BOOKMARKS, null, this);
+        }
+
+        // Add our own listener in case there are favicons that have yet to be loaded.
+        CombinedBookmarkHistoryView.getIconListenerSet().addListener(this);
+
+        return root;
     }
 
-    /**
-     *  Set the ContentView to be either the grid of thumbnails or the vertical
-     *  list.
-     */
-    private void switchViewMode(BookmarkViewMode viewMode) {
-        if (mViewMode == viewMode) {
+    @Override
+    public void onReceivedIcon(String url, Bitmap icon) {
+        // A new favicon has been loaded, so let anything attached to the adapter know about it
+        // so new icons will be loaded.
+        mAdapter.notifyDataSetChanged();
+    }
+
+    @Override
+    public void onItemClick(AdapterView parent, View v, int position, long id) {
+        // It is possible that the view has been canceled when we get to
+        // this point as back has a higher priority
+        if (mCanceled) {
+            android.util.Log.e(LOGTAG, "item clicked when dismissing");
             return;
         }
 
-        mViewMode = viewMode;
-
-        // Update the preferences to make the new view mode sticky.
-        Editor ed = getPreferences(MODE_PRIVATE).edit();
-        if (mMostVisited) {
-            ed.putInt(PREF_MOST_VISITED_VIEW_MODE, mViewMode.ordinal());
-        } else {
-            ed.putInt(PREF_BOOKMARK_VIEW_MODE, mViewMode.ordinal());
+        if (mCreateShortcut) {
+            Intent intent = createShortcutIntent(position);
+            // the activity handles the intent in startActivityFromFragment
+            startActivity(intent);
+            return;
         }
-        ed.apply();
 
-        if (mBookmarksAdapter != null) {
-            mBookmarksAdapter.switchViewMode(viewMode);
-        }
-        if (mViewMode == BookmarkViewMode.GRID) {
-            if (mGridPage == null) {
-                mGridPage = new GridView(this);
-                if (mBookmarksAdapter != null) {
-                    mGridPage.setAdapter(mBookmarksAdapter);
-                }
-                mGridPage.setOnItemClickListener(mListener);
-                mGridPage.setNumColumns(GridView.AUTO_FIT);
-                mGridPage.setColumnWidth(
-                        BrowserActivity.getDesiredThumbnailWidth(this));
-                mGridPage.setFocusable(true);
-                mGridPage.setFocusableInTouchMode(true);
-                mGridPage.setSelector(android.R.drawable.gallery_thumb);
-                float density = getResources().getDisplayMetrics().density;
-                mGridPage.setVerticalSpacing((int) (14 * density));
-                mGridPage.setHorizontalSpacing((int) (8 * density));
-                mGridPage.setStretchMode(GridView.STRETCH_SPACING);
-                mGridPage.setScrollBarStyle(View.SCROLLBARS_INSIDE_INSET);
-                mGridPage.setDrawSelectorOnTop(true);
-                if (mMostVisited) {
-                    mGridPage.setEmptyView(mEmptyView);
-                }
-                if (!mCreateShortcut) {
-                    mGridPage.setOnCreateContextMenuListener(this);
-                }
-            }
-            addContentView(mGridPage, FULL_SCREEN_PARAMS);
-            if (mVerticalList != null) {
-                ViewGroup parent = (ViewGroup) mVerticalList.getParent();
-                if (parent != null) {
-                    parent.removeView(mVerticalList);
-                }
-            }
+        Cursor cursor = (Cursor) mAdapter.getItem(position);
+        boolean isFolder = cursor.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) != 0;
+        if (!isFolder) {
+            mCallbacks.onUrlSelected(getUrl(position), false);
         } else {
-            if (null == mVerticalList) {
-                ListView listView = new ListView(this);
-                if (mBookmarksAdapter != null) {
-                    listView.setAdapter(mBookmarksAdapter);
-                }
-                listView.setDrawSelectorOnTop(false);
-                listView.setVerticalScrollBarEnabled(true);
-                listView.setOnItemClickListener(mListener);
-                if (mMostVisited) {
-                    listView.setEmptyView(mEmptyView);
-                }
-                if (!mCreateShortcut) {
-                    listView.setOnCreateContextMenuListener(this);
-                }
-                mVerticalList = listView;
+            String title = cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE);
+            LoaderManager manager = getLoaderManager();
+            BookmarksLoader loader =
+                    (BookmarksLoader) ((Loader) manager.getLoader(LOADER_BOOKMARKS));
+            Uri uri = ContentUris.withAppendedId(
+                    BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER, id);
+            if (mCrumbs != null) {
+                // update crumbs
+                mCrumbs.pushView(title, uri);
             }
-            addContentView(mVerticalList, FULL_SCREEN_PARAMS);
-            if (mGridPage != null) {
-                ViewGroup parent = (ViewGroup) mGridPage.getParent();
-                if (parent != null) {
-                    parent.removeView(mGridPage);
-                }
-            }
+            loader.setUri(uri);
+            loader.forceLoad();
         }
     }
 
-    private static final ViewGroup.LayoutParams FULL_SCREEN_PARAMS
-            = new ViewGroup.LayoutParams(
-            ViewGroup.LayoutParams.MATCH_PARENT,
-            ViewGroup.LayoutParams.MATCH_PARENT);
+    @Override
+    public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
+        Adapter adapter = parent.getAdapter();
+        String accountType = "com.google";
+        String accountName = adapter.getItem(position).toString();
 
-    private static final int SAVE_CURRENT_PAGE = 1000;
-    private static final int ADAPTER_CREATED = 1001;
-    private final Handler mHandler = new Handler() {
-        @Override
-        public void handleMessage(Message msg) {
-            switch (msg.what) {
-                case SAVE_CURRENT_PAGE:
-                    saveCurrentPage();
-                    break;
-                case ADAPTER_CREATED:
-                    mBookmarksAdapter = (BrowserBookmarksAdapter) msg.obj;
-                    mBookmarksAdapter.switchViewMode(mViewMode);
-                    if (mGridPage != null) {
-                        mGridPage.setAdapter(mBookmarksAdapter);
-                    }
-                    if (mVerticalList != null) {
-                        mVerticalList.setAdapter(mBookmarksAdapter);
-                    }
-                    // Add our own listener in case there are favicons that
-                    // have yet to be loaded.
-                    if (mMostVisited) {
-                        IconListener listener = new IconListener() {
-                            public void onReceivedIcon(String url,
-                                    Bitmap icon) {
-                                if (mGridPage != null) {
-                                    mGridPage.setAdapter(mBookmarksAdapter);
-                                }
-                                if (mVerticalList != null) {
-                                    mVerticalList.setAdapter(mBookmarksAdapter);
-                                }
-                            }
-                        };
-                        CombinedBookmarkHistoryActivity.getIconListenerSet()
-                                .addListener(listener);
-                    }
-                    break;
-            }
+        Bundle args = null;
+        if (ACCOUNT_NAME_UNSYNCED.equals(accountName)) {
+            accountType = DEFAULT_ACCOUNT;
+            accountName = DEFAULT_ACCOUNT;
+        } else {
+            args = new Bundle();
+            args.putString(BookmarksLoader.ARG_ACCOUNT_TYPE, accountType);
+            args.putString(BookmarksLoader.ARG_ACCOUNT_NAME, accountName);
         }
-    };
 
-    private AdapterView.OnItemClickListener mListener = new AdapterView.OnItemClickListener() {
-        public void onItemClick(AdapterView parent, View v, int position, long id) {
-            // It is possible that the view has been canceled when we get to
-            // this point as back has a higher priority
-            if (mCanceled) {
-                android.util.Log.e(LOGTAG, "item clicked when dismissing");
-                return;
-            }
-            if (!mCreateShortcut) {
-                if (0 == position && !mMostVisited) {
-                    // XXX: Work-around for a framework issue.
-                    mHandler.sendEmptyMessage(SAVE_CURRENT_PAGE);
-                } else {
-                    loadUrl(position);
-                }
-            } else {
-                final Intent intent = createShortcutIntent(position);
-                setResultToParent(RESULT_OK, intent);
-                finish();
-            }
-        }
-    };
+        // Remember the selection for later
+        PreferenceManager.getDefaultSharedPreferences(getActivity()).edit()
+                .putString(PREF_ACCOUNT_TYPE, accountType)
+                .putString(PREF_ACCOUNT_NAME, accountName)
+                .apply();
+
+        getLoaderManager().restartLoader(LOADER_BOOKMARKS, args, this);
+    }
+
+    @Override
+    public void onNothingSelected(AdapterView<?> parent) {
+        // Do nothing
+    }
 
     private Intent createShortcutIntent(int position) {
-        String url = getUrl(position);
-        String title = getBookmarkTitle(position);
-        Bitmap touchIcon = getTouchIcon(position);
-
-        final Intent i = new Intent();
-        final Intent shortcutIntent = new Intent(Intent.ACTION_VIEW,
-                Uri.parse(url));
-        long urlHash = url.hashCode();
-        long uniqueId = (urlHash << 32) | shortcutIntent.hashCode();
-        shortcutIntent.putExtra(Browser.EXTRA_APPLICATION_ID,
-                Long.toString(uniqueId));
-        i.putExtra(Intent.EXTRA_SHORTCUT_INTENT, shortcutIntent);
-        i.putExtra(Intent.EXTRA_SHORTCUT_NAME, title);
-        // Use the apple-touch-icon if available
-        if (touchIcon != null) {
-            // Make a copy so we can modify the pixels.  We can't use
-            // createScaledBitmap or copy since they will preserve the config
-            // and lose the ability to add alpha.
-            Bitmap bm = Bitmap.createBitmap(mIconSize, mIconSize,
-                    Bitmap.Config.ARGB_8888);
-            Canvas canvas = new Canvas(bm);
-            Rect src = new Rect(0, 0, touchIcon.getWidth(),
-                                touchIcon.getHeight());
-            Rect dest = new Rect(0, 0, bm.getWidth(), bm.getHeight());
-
-            // Paint used for scaling the bitmap and drawing the rounded rect.
-            Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
-            paint.setFilterBitmap(true);
-            canvas.drawBitmap(touchIcon, src, dest, paint);
-
-            // Construct a path from a round rect. This will allow drawing with
-            // an inverse fill so we can punch a hole using the round rect.
-            Path path = new Path();
-            path.setFillType(Path.FillType.INVERSE_WINDING);
-            RectF rect = new RectF(0, 0, bm.getWidth(), bm.getHeight());
-            rect.inset(1, 1);
-            path.addRoundRect(rect, 8f, 8f, Path.Direction.CW);
-
-            // Reuse the paint and clear the outside of the rectangle.
-            paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
-            canvas.drawPath(path, paint);
-
-            i.putExtra(Intent.EXTRA_SHORTCUT_ICON, bm);
-        } else {
-            Bitmap favicon = getFavicon(position);
-            if (favicon == null) {
-                i.putExtra(Intent.EXTRA_SHORTCUT_ICON_RESOURCE,
-                        Intent.ShortcutIconResource.fromContext(
-                                BrowserBookmarksPage.this,
-                                R.drawable.ic_launcher_shortcut_browser_bookmark));
-            } else {
-                Bitmap icon = BitmapFactory.decodeResource(getResources(),
-                        R.drawable.ic_launcher_shortcut_browser_bookmark_icon);
-
-                // Make a copy of the regular icon so we can modify the pixels.
-                Bitmap copy = icon.copy(Bitmap.Config.ARGB_8888, true);
-                Canvas canvas = new Canvas(copy);
-
-                // Make a Paint for the white background rectangle and for
-                // filtering the favicon.
-                Paint p = new Paint(Paint.ANTI_ALIAS_FLAG
-                        | Paint.FILTER_BITMAP_FLAG);
-                p.setStyle(Paint.Style.FILL_AND_STROKE);
-                p.setColor(Color.WHITE);
-
-                final float density =
-                        getResources().getDisplayMetrics().density;
-                // Create a rectangle that is slightly wider than the favicon
-                final float iconSize = 16 * density; // 16x16 favicon
-                final float padding = 2 * density; // white padding around icon
-                final float rectSize = iconSize + 2 * padding;
-
-                final Rect iconBounds =
-                        new Rect(0, 0, icon.getWidth(), icon.getHeight());
-                final float x = iconBounds.exactCenterX() - (rectSize / 2);
-                // Note: Subtract 2 dip from the y position since the box is
-                // slightly higher than center. Use padding since it is already
-                // 2 * density.
-                final float y = iconBounds.exactCenterY() - (rectSize / 2)
-                        - padding;
-                RectF r = new RectF(x, y, x + rectSize, y + rectSize);
-
-                // Draw a white rounded rectangle behind the favicon
-                canvas.drawRoundRect(r, 2, 2, p);
-
-                // Draw the favicon in the same rectangle as the rounded
-                // rectangle but inset by the padding
-                // (results in a 16x16 favicon).
-                r.inset(padding, padding);
-                canvas.drawBitmap(favicon, null, r, p);
-                i.putExtra(Intent.EXTRA_SHORTCUT_ICON, copy);
-            }
-        }
-        // Do not allow duplicate items
-        i.putExtra("duplicate", false);
-        return i;
-    }
-
-    private void saveCurrentPage() {
-        Intent i = new Intent(BrowserBookmarksPage.this,
-                AddBookmarkPage.class);
-        i.putExtras(getIntent());
-        startActivityForResult(i, BOOKMARKS_SAVE);
+        Cursor cursor = (Cursor) mAdapter.getItem(position);
+        String url = cursor.getString(BookmarksLoader.COLUMN_INDEX_URL);
+        String title = cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE);
+        Bitmap touchIcon = getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_TOUCH_ICON);
+        Bitmap favicon = getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_FAVICON);
+        return BookmarkUtils.createAddToHomeIntent(getActivity(), url, title, touchIcon, favicon);
     }
 
     private void loadUrl(int position) {
-        Intent intent = (new Intent()).setAction(getUrl(position));
-        setResultToParent(RESULT_OK, intent);
-        finish();
-    }
-
-    @Override
-    public boolean onCreateOptionsMenu(Menu menu) {
-        boolean result = super.onCreateOptionsMenu(menu);
-        if (!mCreateShortcut && !mMostVisited) {
-            MenuInflater inflater = getMenuInflater();
-            inflater.inflate(R.menu.bookmarks, menu);
-            return true;
-        }
-        return result;
-    }
-
-    @Override
-    public boolean onPrepareOptionsMenu(Menu menu) {
-        boolean result = super.onPrepareOptionsMenu(menu);
-        if (mCreateShortcut || mMostVisited || mBookmarksAdapter == null
-                || mBookmarksAdapter.getCount() == 0) {
-            // No need to show the menu if there are no items.
-            return result;
-        }
-        MenuItem switchItem = menu.findItem(R.id.switch_mode_menu_id);
-        int titleResId;
-        int iconResId;
-        if (mViewMode == BookmarkViewMode.GRID) {
-            titleResId = R.string.switch_to_list;
-            iconResId = R.drawable.ic_menu_list;
-        } else {
-            titleResId = R.string.switch_to_thumbnails;
-            iconResId = R.drawable.ic_menu_thumbnail;
-        }
-        switchItem.setTitle(titleResId);
-        switchItem.setIcon(iconResId);
-        return true;
-    }
-
-    @Override
-    public boolean onOptionsItemSelected(MenuItem item) {
-        switch (item.getItemId()) {
-        case R.id.new_context_menu_id:
-            saveCurrentPage();
-            break;
-
-        case R.id.switch_mode_menu_id:
-            if (mViewMode == BookmarkViewMode.GRID) {
-                switchViewMode(BookmarkViewMode.LIST);
-            } else {
-                switchViewMode(BookmarkViewMode.GRID);
-            }
-            break;
-
-        default:
-            return super.onOptionsItemSelected(item);
-        }
-        return true;
+        mCallbacks.onUrlSelected(getUrl(position), false);
     }
 
     private void openInNewWindow(int position) {
-        Bundle b = new Bundle();
-        b.putBoolean("new_window", true);
-        setResultToParent(RESULT_OK,
-                (new Intent()).setAction(getUrl(position)).putExtras(b));
-
-        finish();
+        mCallbacks.onUrlSelected(getUrl(position), true);
     }
 
-
     private void editBookmark(int position) {
-        Intent intent = new Intent(BrowserBookmarksPage.this,
-            AddBookmarkPage.class);
-        intent.putExtra("bookmark", getRow(position));
+        Intent intent = new Intent(getActivity(), AddBookmarkPage.class);
+        Cursor cursor = (Cursor) mAdapter.getItem(position);
+        Bundle item = new Bundle();
+        item.putString(BrowserContract.Bookmarks.TITLE,
+                cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE));
+        item.putString(BrowserContract.Bookmarks.URL,
+                cursor.getString(BookmarksLoader.COLUMN_INDEX_URL));
+        byte[] data = cursor.getBlob(BookmarksLoader.COLUMN_INDEX_FAVICON);
+        if (data != null) {
+            item.putParcelable(BrowserContract.Bookmarks.FAVICON,
+                    BitmapFactory.decodeByteArray(data, 0, data.length));
+        }
+        item.putInt("id", cursor.getInt(BookmarksLoader.COLUMN_INDEX_ID));
+        item.putLong(BrowserContract.Bookmarks.PARENT,
+                cursor.getLong(BookmarksLoader.COLUMN_INDEX_PARENT));
+        intent.putExtra("bookmark", item);
         startActivityForResult(intent, BOOKMARKS_SAVE);
     }
 
     @Override
-    protected void onActivityResult(int requestCode, int resultCode,
-                                    Intent data) {
+    public void onActivityResult(int requestCode, int resultCode, Intent data) {
         switch(requestCode) {
             case BOOKMARKS_SAVE:
-                if (resultCode == RESULT_OK) {
+                if (resultCode == Activity.RESULT_OK) {
                     Bundle extras;
                     if (data != null && (extras = data.getExtras()) != null) {
                         // If there are extras, then we need to save
                         // the edited bookmark. This is done in updateRow()
-                        String title = extras.getString("title");
-                        String url = extras.getString("url");
+                        String title = extras.getString(BrowserContract.Bookmarks.TITLE);
+                        String url = extras.getString(BrowserContract.Bookmarks.URL);
                         if (title != null && url != null) {
-                            mBookmarksAdapter.updateRow(extras);
+                            updateRow(extras);
                         }
-                    } else {
-                        // extras == null then a new bookmark was added to
-                        // the database.
-                        refreshList();
                     }
                 }
                 break;
-            default:
-                break;
         }
     }
 
-    private void displayRemoveBookmarkDialog(int position) {
+    /**
+     *  Update a row in the database with new information.
+     *  @param map  Bundle storing id, title and url of new information
+     */
+    public void updateRow(Bundle map) {
+
+        // Find the record
+        int id = map.getInt("id");
+        int position = -1;
+        Cursor cursor = mAdapter.getCursor();
+        for (cursor.moveToFirst(); !cursor.isAfterLast(); cursor.moveToNext()) {
+            if (cursor.getInt(BookmarksLoader.COLUMN_INDEX_ID) == id) {
+                position = cursor.getPosition();
+                break;
+            }
+        }
+        if (position < 0) {
+            return;
+        }
+
+        cursor.moveToPosition(position);
+        ContentValues values = new ContentValues();
+        String title = map.getString(BrowserContract.Bookmarks.TITLE);
+        if (!title.equals(cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE))) {
+            values.put(BrowserContract.Bookmarks.TITLE, title);
+        }
+        String url = map.getString(BrowserContract.Bookmarks.URL);
+        if (!url.equals(cursor.getString(BookmarksLoader.COLUMN_INDEX_URL))) {
+            values.put(BrowserContract.Bookmarks.URL, url);
+        }
+
+        if (map.getBoolean(AddBookmarkPage.REMOVE_THUMBNAIL)) {
+            values.putNull(BrowserContract.Bookmarks.THUMBNAIL);
+        }
+
+        if (values.size() > 0) {
+            getActivity().getContentResolver().update(
+                    ContentUris.withAppendedId(BrowserContract.Bookmarks.CONTENT_URI, id),
+                    values, null, null);
+        }
+    }
+
+    private void displayRemoveBookmarkDialog(final int position) {
         // Put up a dialog asking if the user really wants to
         // delete the bookmark
-        final int deletePos = position;
-        new AlertDialog.Builder(this)
+        Cursor cursor = (Cursor) mAdapter.getItem(position);
+        Context context = getActivity();
+        final ContentResolver resolver = context.getContentResolver();
+        final Uri uri = ContentUris.withAppendedId(BrowserContract.Bookmarks.CONTENT_URI,
+                cursor.getLong(BookmarksLoader.COLUMN_INDEX_ID));
+
+        new AlertDialog.Builder(context)
                 .setTitle(R.string.delete_bookmark)
                 .setIcon(android.R.drawable.ic_dialog_alert)
-                .setMessage(getText(R.string.delete_bookmark_warning).toString().replace(
-                        "%s", getBookmarkTitle(deletePos)))
+                .setMessage(context.getString(R.string.delete_bookmark_warning,
+                        cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE)))
                 .setPositiveButton(R.string.ok,
                         new DialogInterface.OnClickListener() {
+                            @Override
                             public void onClick(DialogInterface dialog, int whichButton) {
-                                deleteBookmark(deletePos);
+                                resolver.delete(uri, null, null);
                             }
                         })
                 .setNegativeButton(R.string.cancel, null)
                 .show();
     }
 
-    /**
-     *  Refresh the shown list after the database has changed.
-     */
-    private void refreshList() {
-        if (mBookmarksAdapter == null) return;
-        mBookmarksAdapter.refreshList();
-    }
-
-    /**
-     *  Return a hashmap representing the currently highlighted row.
-     */
-    public Bundle getRow(int position) {
-        return mBookmarksAdapter == null ? null
-                : mBookmarksAdapter.getRow(position);
-    }
-
-    /**
-     *  Return the url of the currently highlighted row.
-     */
-    public String getUrl(int position) {
-        return mBookmarksAdapter == null ? null
-                : mBookmarksAdapter.getUrl(position);
-    }
-
-    /**
-     * Return the favicon of the currently highlighted row.
-     */
-    public Bitmap getFavicon(int position) {
-        return mBookmarksAdapter == null ? null
-                : mBookmarksAdapter.getFavicon(position);
-    }
-
-    private Bitmap getTouchIcon(int position) {
-        return mBookmarksAdapter == null ? null
-                : mBookmarksAdapter.getTouchIcon(position);
+    private String getUrl(int position) {
+        Cursor cursor = (Cursor) mAdapter.getItem(position);
+        return cursor.getString(BookmarksLoader.COLUMN_INDEX_URL);
     }
 
     private void copy(CharSequence text) {
-        try {
-            IClipboard clip = IClipboard.Stub.asInterface(ServiceManager.getService("clipboard"));
-            if (clip != null) {
-                clip.setClipboardText(text);
-            }
-        } catch (android.os.RemoteException e) {
-            Log.e(LOGTAG, "Copy failed", e);
-        }
+        ClipboardManager cm = (ClipboardManager) getActivity().getSystemService(
+                Context.CLIPBOARD_SERVICE);
+        cm.setPrimaryClip(ClipData.newRawUri(null, null, Uri.parse(text.toString())));
     }
 
-    public String getBookmarkTitle(int position) {
-        return mBookmarksAdapter == null ? null
-                : mBookmarksAdapter.getTitle(position);
-    }
-
-    /**
-     *  Delete the currently highlighted row.
-     */
-    public void deleteBookmark(int position) {
-        if (mBookmarksAdapter == null) return;
-        mBookmarksAdapter.deleteRow(position);
-    }
-
-    @Override
-    public void onBackPressed() {
-        setResultToParent(RESULT_CANCELED, null);
-        mCanceled = true;
-        super.onBackPressed();
-    }
-
-    // This Activity is generally a sub-Activity of
-    // CombinedBookmarkHistoryActivity. In that situation, we need to pass our
-    // result code up to our parent. However, if someone calls this Activity
-    // directly, then this has no parent, and it needs to set it on itself.
-    private void setResultToParent(int resultCode, Intent data) {
-        Activity parent = getParent();
-        if (parent == null) {
-            setResult(resultCode, data);
-        } else {
-            ((CombinedBookmarkHistoryActivity) parent).setResultFromChild(
-                    resultCode, data);
-        }
-    }
 }
diff --git a/src/com/android/browser/BrowserHistoryPage.java b/src/com/android/browser/BrowserHistoryPage.java
index 23080f8..61af0ce 100644
--- a/src/com/android/browser/BrowserHistoryPage.java
+++ b/src/com/android/browser/BrowserHistoryPage.java
@@ -17,198 +17,235 @@
 package com.android.browser;
 
 import android.app.Activity;
-import android.app.ExpandableListActivity;
+import android.app.AlertDialog;
+import android.app.Dialog;
+import android.app.Fragment;
+import android.app.LoaderManager.LoaderCallbacks;
+import android.content.ClipboardManager;
 import android.content.Context;
+import android.content.CursorLoader;
+import android.content.DialogInterface;
 import android.content.Intent;
+import android.content.Loader;
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.database.Cursor;
 import android.graphics.Bitmap;
 import android.graphics.BitmapFactory;
 import android.os.Bundle;
-import android.os.ServiceManager;
 import android.provider.Browser;
-import android.text.IClipboard;
-import android.util.Log;
+import android.provider.BrowserContract.History;
 import android.view.ContextMenu;
+import android.view.ContextMenu.ContextMenuInfo;
+import android.view.LayoutInflater;
 import android.view.Menu;
 import android.view.MenuInflater;
 import android.view.MenuItem;
 import android.view.View;
 import android.view.ViewGroup;
-import android.view.ViewGroup.LayoutParams;
-import android.view.ContextMenu.ContextMenuInfo;
-import android.view.ViewStub;
 import android.webkit.WebIconDatabase.IconListener;
-import android.widget.ExpandableListAdapter;
 import android.widget.ExpandableListView;
 import android.widget.ExpandableListView.ExpandableListContextMenuInfo;
+import android.widget.ExpandableListView.OnChildClickListener;
 import android.widget.Toast;
 
 /**
  * Activity for displaying the browser's history, divided into
  * days of viewing.
  */
-public class BrowserHistoryPage extends ExpandableListActivity {
-    private HistoryAdapter          mAdapter;
-    private boolean                 mDisableNewWindow;
-    private HistoryItem             mContextHeader;
+public class BrowserHistoryPage extends Fragment
+        implements LoaderCallbacks<Cursor>, OnChildClickListener {
 
-    private final static String LOGTAG = "browser";
+    static final int LOADER_HISTORY = 1;
+
+    BookmarksHistoryCallbacks mCallbacks;
+    ExpandableListView mList;
+    View mEmptyView;
+    HistoryAdapter mAdapter;
+    boolean mDisableNewWindow;
+    HistoryItem mContextHeader;
 
     // Implementation of WebIconDatabase.IconListener
-    private class IconReceiver implements IconListener {
+    class IconReceiver implements IconListener {
+        @Override
         public void onReceivedIcon(String url, Bitmap icon) {
-            setListAdapter(mAdapter);
+            mAdapter.notifyDataSetChanged();
         }
     }
-    // Instance of IconReceiver
-    private final IconReceiver mIconReceiver = new IconReceiver();
 
-    /**
-     * Report back to the calling activity to load a site.
-     * @param url   Site to load.
-     * @param newWindow True if the URL should be loaded in a new window
-     */
-    private void loadUrl(String url, boolean newWindow) {
-        Intent intent = new Intent().setAction(url);
-        if (newWindow) {
-            Bundle b = new Bundle();
-            b.putBoolean("new_window", true);
-            intent.putExtras(b);
-        }
-        setResultToParent(RESULT_OK, intent);
-        finish();
+    // Instance of IconReceiver
+    final IconReceiver mIconReceiver = new IconReceiver();
+
+    static interface HistoryQuery {
+        static final String[] PROJECTION = new String[] {
+                History._ID, // 0
+                History.DATE_LAST_VISITED, // 1
+                History.TITLE, // 2
+                History.URL, // 3
+                History.FAVICON, // 4
+        };
+
+        static final int INDEX_ID = 0;
+        static final int INDEX_DATE_LAST_VISITED = 1;
+        static final int INDEX_TITE = 2;
+        static final int INDEX_URL = 3;
+        static final int INDEX_FAVICON = 4;
     }
-    
+
     private void copy(CharSequence text) {
-        try {
-            IClipboard clip = IClipboard.Stub.asInterface(ServiceManager.getService("clipboard"));
-            if (clip != null) {
-                clip.setClipboardText(text);
+        ClipboardManager cm = (ClipboardManager) getActivity().getSystemService(
+                Context.CLIPBOARD_SERVICE);
+        cm.setText(text);
+    }
+
+    static BrowserHistoryPage newInstance(BookmarksHistoryCallbacks cb, Bundle args) {
+        BrowserHistoryPage bhp = new BrowserHistoryPage();
+        bhp.mCallbacks = cb;
+        bhp.setArguments(args);
+        return bhp;
+    }
+
+    @Override
+    public Loader<Cursor> onCreateLoader(int id, Bundle args) {
+        switch (id) {
+            case LOADER_HISTORY: {
+                CursorLoader loader = new CursorLoader(getActivity(), History.CONTENT_URI,
+                        HistoryQuery.PROJECTION, null, null, null);
+                return loader;
             }
-        } catch (android.os.RemoteException e) {
-            Log.e(LOGTAG, "Copy failed", e);
+
+            default: {
+                throw new IllegalArgumentException();
+            }
         }
     }
 
     @Override
-    protected void onCreate(Bundle icicle) {
-        super.onCreate(icicle);
-        setTitle(R.string.browser_history);
+    public void onLoadFinished(Loader<Cursor> loader, Cursor data) {
+        switch (loader.getId()) {
+            case LOADER_HISTORY: {
+                mAdapter.changeCursor(data);
 
-        final String whereClause = Browser.BookmarkColumns.VISITS + " > 0"
-                // In AddBookmarkPage, where we save new bookmarks, we add
-                // three visits to newly created bookmarks, so that
-                // bookmarks that have not been visited will show up in the
-                // most visited, and higher in the goto search box.
-                // However, this puts the site in the history, unless we
-                // ignore sites with a DATE of 0, which the next line does.
-                + " AND " + Browser.BookmarkColumns.DATE + " > 0";
-        final String orderBy = Browser.BookmarkColumns.DATE + " DESC";
+                // Add an empty view late, so it does not claim an empty
+                // history before the adapter is present
+                mList.setEmptyView(mEmptyView);
 
-        Cursor cursor = managedQuery(
-                Browser.BOOKMARKS_URI,
-                Browser.HISTORY_PROJECTION,
-                whereClause, null, orderBy);
-
-        mAdapter = new HistoryAdapter(this, cursor,
-                Browser.HISTORY_PROJECTION_DATE_INDEX);
-        setListAdapter(mAdapter);
-        final ExpandableListView list = getExpandableListView();
-        list.setOnCreateContextMenuListener(this);
-        View v = new ViewStub(this, R.layout.empty_history);
-        addContentView(v, new LayoutParams(LayoutParams.MATCH_PARENT,
-                LayoutParams.MATCH_PARENT));
-        list.setEmptyView(v);
-        // Do not post the runnable if there is nothing in the list.
-        if (list.getExpandableListAdapter().getGroupCount() > 0) {
-            list.post(new Runnable() {
-                public void run() {
-                    // In case the history gets cleared before this event
-                    // happens.
-                    if (list.getExpandableListAdapter().getGroupCount() > 0) {
-                        list.expandGroup(0);
-                    }
+                // Do not post the runnable if there is nothing in the list.
+                if (mList.getExpandableListAdapter().getGroupCount() > 0) {
+                    mList.post(new Runnable() {
+                        @Override
+                        public void run() {
+                            // In case the history gets cleared before this
+                            // event happens
+                            if (mList.getExpandableListAdapter().getGroupCount() > 0) {
+                                mList.expandGroup(0);
+                            }
+                        }
+                    });
                 }
-            });
+                break;
+            }
+
+            default: {
+                throw new IllegalArgumentException();
+            }
         }
-        mDisableNewWindow = getIntent().getBooleanExtra("disable_new_window",
-                false);
+    }
+
+    @Override
+    public void onCreate(Bundle icicle) {
+        super.onCreate(icicle);
+
+        setHasOptionsMenu(true);
+
+        Bundle args = getArguments();
+        mDisableNewWindow = args.getBoolean(BrowserBookmarksPage.EXTRA_DISABLE_WINDOW, false);
+    }
+
+    @Override
+    public View onCreateView(LayoutInflater inflater, ViewGroup container,
+            Bundle savedInstanceState) {
+        View root = inflater.inflate(R.layout.history, container, false);
+        mList = (ExpandableListView) root.findViewById(android.R.id.list);
+        mList.setCacheColorHint(0);
+        mList.setOnCreateContextMenuListener(this);
+        mList.setOnChildClickListener(this);
+        mAdapter = new HistoryAdapter(getActivity());
+        mList.setAdapter(mAdapter);
+
+        mEmptyView = root.findViewById(android.R.id.empty);
+
+        // Start the loader
+        getLoaderManager().initLoader(LOADER_HISTORY, null, this);
 
         // Register to receive icons in case they haven't all been loaded.
-        CombinedBookmarkHistoryActivity.getIconListenerSet()
-                .addListener(mIconReceiver);
-
-        Activity parent = getParent();
-        if (null == parent
-                || !(parent instanceof CombinedBookmarkHistoryActivity)) {
-            throw new AssertionError("history page can only be viewed as a tab"
-                    + "in CombinedBookmarkHistoryActivity");
-        }
-        // initialize the result to canceled, so that if the user just presses
-        // back then it will have the correct result
-        setResultToParent(RESULT_CANCELED, null);
+        CombinedBookmarkHistoryView.getIconListenerSet().addListener(mIconReceiver);
+        return root;
     }
 
     @Override
-    protected void onDestroy() {
+    public void onDestroy() {
         super.onDestroy();
-        CombinedBookmarkHistoryActivity.getIconListenerSet()
-                .removeListener(mIconReceiver);
+        CombinedBookmarkHistoryView.getIconListenerSet().removeListener(mIconReceiver);
     }
 
     @Override
-    public boolean onCreateOptionsMenu(Menu menu) {
-        super.onCreateOptionsMenu(menu);
-        MenuInflater inflater = getMenuInflater();
+    public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
         inflater.inflate(R.menu.history, menu);
-        return true;
     }
 
     @Override
-    public boolean onPrepareOptionsMenu(Menu menu) {
-        menu.findItem(R.id.clear_history_menu_id).setVisible(Browser.canClearHistory(this.getContentResolver()));
-        return true;
+    public void onPrepareOptionsMenu(Menu menu) {
+        menu.findItem(R.id.clear_history_menu_id).setVisible(
+                Browser.canClearHistory(getActivity().getContentResolver()));
     }
-    
+
     @Override
     public boolean onOptionsItemSelected(MenuItem item) {
         switch (item.getItemId()) {
             case R.id.clear_history_menu_id:
-                Browser.clearHistory(getContentResolver());
-                // BrowserHistoryPage is always a child of
-                // CombinedBookmarkHistoryActivity
-                ((CombinedBookmarkHistoryActivity) getParent())
-                        .removeParentChildRelationShips();
-                mAdapter.refreshData();
+                AlertDialog.Builder builder = new AlertDialog.Builder(getActivity())
+                        .setTitle(R.string.clear)
+                        .setMessage(R.string.pref_privacy_clear_history_dlg)
+                        .setIcon(android.R.drawable.ic_dialog_alert)
+                        .setNegativeButton(R.string.cancel, null)
+                        .setPositiveButton(R.string.ok, new DialogInterface.OnClickListener() {
+                             @Override
+                             public void onClick(DialogInterface dialog, int which) {
+                                 if (which == DialogInterface.BUTTON_POSITIVE) {
+                                     Browser.clearHistory(getActivity().getContentResolver());
+                                     mCallbacks.onRemoveParentChildRelationships();
+                                 }
+                             }
+                        });
+                final Dialog dialog = builder.create();
+                dialog.show();
                 return true;
-                
+
             default:
                 break;
-        }  
+        }
         return super.onOptionsItemSelected(item);
     }
 
     @Override
-    public void onCreateContextMenu(ContextMenu menu, View v,
-            ContextMenuInfo menuInfo) {
-        ExpandableListContextMenuInfo i = 
-            (ExpandableListContextMenuInfo) menuInfo;
+    public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
+        ExpandableListContextMenuInfo i = (ExpandableListContextMenuInfo) menuInfo;
         // Do not allow a context menu to come up from the group views.
         if (!(i.targetView instanceof HistoryItem)) {
             return;
         }
 
         // Inflate the menu
-        MenuInflater inflater = getMenuInflater();
+        Activity parent = getActivity();
+        MenuInflater inflater = parent.getMenuInflater();
         inflater.inflate(R.menu.historycontext, menu);
 
         HistoryItem historyItem = (HistoryItem) i.targetView;
 
         // Setup the header
         if (mContextHeader == null) {
-            mContextHeader = new HistoryItem(this);
+            mContextHeader = new HistoryItem(parent);
         } else if (mContextHeader.getParent() != null) {
             ((ViewGroup) mContextHeader.getParent()).removeView(mContextHeader);
         }
@@ -225,88 +262,79 @@
             item.setTitle(R.string.remove_from_bookmarks);
         }
         // decide whether to show the share link option
-        PackageManager pm = getPackageManager();
+        PackageManager pm = parent.getPackageManager();
         Intent send = new Intent(Intent.ACTION_SEND);
         send.setType("text/plain");
         ResolveInfo ri = pm.resolveActivity(send, PackageManager.MATCH_DEFAULT_ONLY);
         menu.findItem(R.id.share_link_context_menu_id).setVisible(ri != null);
-        
+
         super.onCreateContextMenu(menu, v, menuInfo);
     }
-    
+
     @Override
     public boolean onContextItemSelected(MenuItem item) {
-        ExpandableListContextMenuInfo i = 
+        ExpandableListContextMenuInfo i =
             (ExpandableListContextMenuInfo) item.getMenuInfo();
         HistoryItem historyItem = (HistoryItem) i.targetView;
         String url = historyItem.getUrl();
         String title = historyItem.getName();
+        Activity activity = getActivity();
         switch (item.getItemId()) {
             case R.id.open_context_menu_id:
-                loadUrl(url, false);
+                mCallbacks.onUrlSelected(url, false);
                 return true;
             case R.id.new_window_context_menu_id:
-                loadUrl(url, true);
+                mCallbacks.onUrlSelected(url, true);
                 return true;
             case R.id.save_to_bookmarks_menu_id:
                 if (historyItem.isBookmark()) {
-                    Bookmarks.removeFromBookmarks(this, getContentResolver(),
+                    Bookmarks.removeFromBookmarks(activity, activity.getContentResolver(),
                             url, title);
                 } else {
-                    Browser.saveBookmark(this, title, url);
+                    Browser.saveBookmark(activity, title, url);
                 }
                 return true;
             case R.id.share_link_context_menu_id:
-                Browser.sendString(this, url,
-                        getText(R.string.choosertitle_sharevia).toString());
+                Browser.sendString(activity, url,
+                        activity.getText(R.string.choosertitle_sharevia).toString());
                 return true;
             case R.id.copy_url_context_menu_id:
                 copy(url);
                 return true;
             case R.id.delete_context_menu_id:
-                Browser.deleteFromHistory(getContentResolver(), url);
-                mAdapter.refreshData();
+                Browser.deleteFromHistory(activity.getContentResolver(), url);
                 return true;
             case R.id.homepage_context_menu_id:
-                BrowserSettings.getInstance().setHomePage(this, url);
-                Toast.makeText(this, R.string.homepage_set,
-                    Toast.LENGTH_LONG).show();
+                BrowserSettings.getInstance().setHomePage(activity, url);
+                Toast.makeText(activity, R.string.homepage_set, Toast.LENGTH_LONG).show();
                 return true;
             default:
                 break;
         }
         return super.onContextItemSelected(item);
     }
-    
+
     @Override
     public boolean onChildClick(ExpandableListView parent, View v,
             int groupPosition, int childPosition, long id) {
         if (v instanceof HistoryItem) {
-            loadUrl(((HistoryItem) v).getUrl(), false);
+            mCallbacks.onUrlSelected(((HistoryItem) v).getUrl(), false);
             return true;
         }
         return false;
     }
 
-    // This Activity is always a sub-Activity of
-    // CombinedBookmarkHistoryActivity. Therefore, we need to pass our
-    // result code up to our parent.
-    private void setResultToParent(int resultCode, Intent data) {
-        ((CombinedBookmarkHistoryActivity) getParent()).setResultFromChild(
-                resultCode, data);
-    }
-
     private class HistoryAdapter extends DateSortedExpandableListAdapter {
-        HistoryAdapter(Context context, Cursor cursor, int index) {
-            super(context, cursor, index);
-            
+        HistoryAdapter(Context context) {
+            super(context, HistoryQuery.INDEX_DATE_LAST_VISITED);
         }
 
+        @Override
         public View getChildView(int groupPosition, int childPosition, boolean isLastChild,
                 View convertView, ViewGroup parent) {
             HistoryItem item;
             if (null == convertView || !(convertView instanceof HistoryItem)) {
-                item = new HistoryItem(BrowserHistoryPage.this);
+                item = new HistoryItem(getContext());
                 // Add padding on the left so it will be indented from the
                 // arrows on the group views.
                 item.setPadding(item.getPaddingLeft() + 10,
@@ -316,23 +344,23 @@
             } else {
                 item = (HistoryItem) convertView;
             }
+
             // Bail early if the Cursor is closed.
             if (!moveCursorToChildPosition(groupPosition, childPosition)) {
                 return item;
             }
-            item.setName(getString(Browser.HISTORY_PROJECTION_TITLE_INDEX));
-            String url = getString(Browser.HISTORY_PROJECTION_URL_INDEX);
+
+            item.setName(getString(HistoryQuery.INDEX_TITE));
+            String url = getString(HistoryQuery.INDEX_URL);
             item.setUrl(url);
-            byte[] data = getBlob(Browser.HISTORY_PROJECTION_FAVICON_INDEX);
+            byte[] data = getBlob(HistoryQuery.INDEX_FAVICON);
             if (data != null) {
                 item.setFavicon(BitmapFactory.decodeByteArray(data, 0,
                         data.length));
             } else {
-                item.setFavicon(CombinedBookmarkHistoryActivity
+                item.setFavicon(CombinedBookmarkHistoryView
                         .getIconListenerSet().getFavicon(url));
             }
-            item.setIsBookmark(1 ==
-                    getInt(Browser.HISTORY_PROJECTION_BOOKMARK_INDEX));
             return item;
         }
     }
diff --git a/src/com/android/browser/BrowserHomepagePreference.java b/src/com/android/browser/BrowserHomepagePreference.java
index 4f18bd5..fefe101 100644
--- a/src/com/android/browser/BrowserHomepagePreference.java
+++ b/src/com/android/browser/BrowserHomepagePreference.java
@@ -18,11 +18,13 @@
 
 import android.app.AlertDialog;
 import android.content.Context;
+import android.content.DialogInterface;
 import android.os.Bundle;
 import android.preference.EditTextPreference;
 import android.widget.Button;
 import android.widget.EditText;
 import android.widget.LinearLayout;
+import android.widget.Toast;
 import android.view.Gravity;
 import android.view.View;
 import android.view.ViewGroup;
@@ -32,18 +34,22 @@
 
 public class BrowserHomepagePreference extends EditTextPreference {
     private String mCurrentPage;
+    private AlertDialog mSetHomepageTo;
 
     public BrowserHomepagePreference(Context context, AttributeSet attrs,
             int defStyle) {
         super(context, attrs, defStyle);
+        createSetHomepageToDialog();
     }
 
     public BrowserHomepagePreference(Context context, AttributeSet attrs) {
         super(context, attrs);
+        createSetHomepageToDialog();
     }
 
     public BrowserHomepagePreference(Context context) {
         super(context);
+        createSetHomepageToDialog();
     }
 
     @Override
@@ -54,10 +60,10 @@
         // page.
         ViewGroup parent = (ViewGroup) editText.getParent();
         Button button = new Button(getContext());
-        button.setText(R.string.pref_use_current);
+        button.setText(R.string.pref_set_homepage_to);
         button.setOnClickListener(new View.OnClickListener() {
             public void onClick(View v) {
-                getEditText().setText(mCurrentPage);
+                mSetHomepageTo.show();
             }
         });
         if (parent instanceof LinearLayout) {
@@ -67,24 +73,46 @@
                 ViewGroup.LayoutParams.WRAP_CONTENT);
     }
 
+    private void createSetHomepageToDialog() {
+        Context context = getContext();
+        CharSequence[] setToChoices = new CharSequence[] {
+                context.getText(R.string.pref_use_current),
+                context.getText(R.string.pref_use_blank),
+                context.getText(R.string.pref_use_default),
+        };
+        AlertDialog.Builder builder = new AlertDialog.Builder(context);
+        builder.setTitle(R.string.pref_set_homepage_to);
+        builder.setItems(setToChoices, new DialogInterface.OnClickListener() {
+            @Override
+            public void onClick(DialogInterface dialog, int which) {
+                if (which == 0) {
+                    getEditText().setText(mCurrentPage);
+                } else if (which == 1) {
+                    getEditText().setText("about:blank");
+                } else if (which == 2) {
+                    getEditText().setText(BrowserSettings
+                            .getFactoryResetHomeUrl(getContext()));
+                }
+            }
+        });
+        mSetHomepageTo = builder.create();
+    }
+
     @Override
     protected void onDialogClosed(boolean positiveResult) {
         if (positiveResult) {
             String url = getEditText().getText().toString();
-            if (url.length() > 0
-                    && !BrowserActivity.ACCEPTED_URI_SCHEMA.matcher(url)
-                            .matches()) {
+            if (!BrowserActivity.ACCEPTED_URI_SCHEMA.matcher(url).matches()) {
                 int colon = url.indexOf(':');
                 int space = url.indexOf(' ');
-                if (colon == -1 && space == -1) {
+                if (colon == -1 && space == -1 && url.length() > 0) {
                     // if no colon, no space, add "http://" to make it a url
                     getEditText().setText("http://" + url);
                 } else {
-                    // show an error dialog and change the positiveResult to
+                    // show an error toast and change the positiveResult to
                     // false so that the bad url will not override the old url
-                    new AlertDialog.Builder(this.getContext()).setMessage(
-                            R.string.bookmark_url_not_valid).setPositiveButton(
-                            R.string.ok, null).show();
+                    Toast.makeText(getContext(), R.string.bookmark_url_not_valid,
+                            Toast.LENGTH_SHORT).show();
                     positiveResult = false;
                 }
             }
@@ -97,7 +125,7 @@
      * @param currentPage This String will replace the text in the EditText
      *          when the user clicks the "Use current page" button.
      */
-    /* package */ void setCurrentPage(String currentPage) {
+    public void setCurrentPage(String currentPage) {
         mCurrentPage = currentPage;
     }
 
diff --git a/src/com/android/browser/BrowserPreferencesPage.java b/src/com/android/browser/BrowserPreferencesPage.java
index 9af66f1..d93e70f 100644
--- a/src/com/android/browser/BrowserPreferencesPage.java
+++ b/src/com/android/browser/BrowserPreferencesPage.java
@@ -16,96 +16,30 @@
 
 package com.android.browser;
 
-import android.content.Intent;
-import android.net.Uri;
-import android.os.Bundle;
-import android.preference.EditTextPreference;
-import android.preference.Preference;
+import com.android.browser.preferences.DebugPreferencesFragment;
+
 import android.preference.PreferenceActivity;
-import android.preference.PreferenceScreen;
-import android.webkit.GeolocationPermissions;
-import android.webkit.ValueCallback;
-import android.webkit.WebStorage;
+import android.preference.PreferenceManager;
 
-import java.util.Map;
-import java.util.Set;
+import java.util.List;
 
-public class BrowserPreferencesPage extends PreferenceActivity
-        implements Preference.OnPreferenceChangeListener {
+public class BrowserPreferencesPage extends PreferenceActivity {
 
-    private String LOGTAG = "BrowserPreferencesPage";
-    /* package */ static final String CURRENT_PAGE = "currentPage";
+    public static final String CURRENT_PAGE = "currentPage";
 
-    @Override
-    protected void onCreate(Bundle savedInstanceState) {
-        super.onCreate(savedInstanceState);
-
-        // Load the XML preferences file
-        addPreferencesFromResource(R.xml.browser_preferences);
-
-        Preference e = findPreference(BrowserSettings.PREF_HOMEPAGE);
-        e.setOnPreferenceChangeListener(this);
-        e.setSummary(getPreferenceScreen().getSharedPreferences()
-                .getString(BrowserSettings.PREF_HOMEPAGE, null));
-        ((BrowserHomepagePreference) e).setCurrentPage(
-                getIntent().getStringExtra(CURRENT_PAGE));
-        
-        e = findPreference(BrowserSettings.PREF_EXTRAS_RESET_DEFAULTS);
-        e.setOnPreferenceChangeListener(this);
-        
-        e = findPreference(BrowserSettings.PREF_TEXT_SIZE);
-        e.setOnPreferenceChangeListener(this);
-        e.setSummary(getVisualTextSizeName(
-                getPreferenceScreen().getSharedPreferences()
-                .getString(BrowserSettings.PREF_TEXT_SIZE, null)) );
-        
-        e = findPreference(BrowserSettings.PREF_DEFAULT_ZOOM);
-        e.setOnPreferenceChangeListener(this);
-        e.setSummary(getVisualDefaultZoomName(
-                getPreferenceScreen().getSharedPreferences()
-                .getString(BrowserSettings.PREF_DEFAULT_ZOOM, null)) );
-
-        e = findPreference(BrowserSettings.PREF_DEFAULT_TEXT_ENCODING);
-        e.setOnPreferenceChangeListener(this);
-
-        e = findPreference(BrowserSettings.PREF_CLEAR_HISTORY);
-        e.setOnPreferenceChangeListener(this);
-
-        if (BrowserSettings.getInstance().showDebugSettings()) {
-            addPreferencesFromResource(R.xml.debug_preferences);
-        }
-
-        PreferenceScreen websiteSettings = (PreferenceScreen)
-            findPreference(BrowserSettings.PREF_WEBSITE_SETTINGS);
-        Intent intent = new Intent(this, WebsiteSettingsActivity.class);
-        websiteSettings.setIntent(intent);
-    }
-
-    /*
-     * We need to set the PreferenceScreen state in onResume(), as the number of
-     * origins with active features (WebStorage, Geolocation etc) could have
-     * changed after calling the WebsiteSettingsActivity.
+    /**
+     * Populate the activity with the top-level headers.
      */
     @Override
-    protected void onResume() {
-        super.onResume();
-        final PreferenceScreen websiteSettings = (PreferenceScreen)
-            findPreference(BrowserSettings.PREF_WEBSITE_SETTINGS);
-        websiteSettings.setEnabled(false);
-        WebStorage.getInstance().getOrigins(new ValueCallback<Map>() {
-            public void onReceiveValue(Map webStorageOrigins) {
-                if ((webStorageOrigins != null) && !webStorageOrigins.isEmpty()) {
-                    websiteSettings.setEnabled(true);
-                }
-            }
-        });
-        GeolocationPermissions.getInstance().getOrigins(new ValueCallback<Set<String> >() {
-            public void onReceiveValue(Set<String> geolocationOrigins) {
-                if ((geolocationOrigins != null) && !geolocationOrigins.isEmpty()) {
-                    websiteSettings.setEnabled(true);
-                }
-            }
-        });
+    public void onBuildHeaders(List<Header> target) {
+        loadHeadersFromResource(R.xml.preference_headers, target);
+
+        if (BrowserSettings.getInstance().showDebugSettings()) {
+            Header debug = new Header();
+            debug.title = getText(R.string.pref_development_title);
+            debug.fragment = DebugPreferencesFragment.class.getName();
+            target.add(debug);
+        }
     }
 
     @Override
@@ -115,98 +49,6 @@
         // sync the shared preferences back to BrowserSettings
         BrowserSettings.getInstance().syncSharedPreferences(
                 getApplicationContext(),
-                getPreferenceScreen().getSharedPreferences());
-    }
-
-    public boolean onPreferenceChange(Preference pref, Object objValue) {
-        if (pref.getKey().equals(BrowserSettings.PREF_EXTRAS_RESET_DEFAULTS)) {
-            Boolean value = (Boolean) objValue;
-            if (value.booleanValue() == true) {
-                finish();
-            }
-        } else if (pref.getKey().equals(BrowserSettings.PREF_HOMEPAGE)) {
-            String value = (String) objValue;
-            boolean needUpdate = value.indexOf(' ') != -1;
-            if (needUpdate) {
-                value = value.trim().replace(" ", "%20");
-            }
-            if (value.length() != 0 && Uri.parse(value).getScheme() == null) {
-                value = "http://" + value;
-                needUpdate = true;
-            }
-            // Set the summary value.
-            pref.setSummary(value);
-            if (needUpdate) {
-                // Update through the EditText control as it has a cached copy
-                // of the string and it will handle persisting the value
-                ((EditTextPreference) pref).setText(value);
-
-                // as we update the value above, we need to return false
-                // here so that setText() is not called by EditTextPref
-                // with the old value.
-                return false;
-            } else {
-                return true;
-            }
-        } else if (pref.getKey().equals(BrowserSettings.PREF_TEXT_SIZE)) {
-            pref.setSummary(getVisualTextSizeName((String) objValue));
-            return true;
-        } else if (pref.getKey().equals(BrowserSettings.PREF_DEFAULT_ZOOM)) {
-            pref.setSummary(getVisualDefaultZoomName((String) objValue));
-            return true;
-        } else if (pref.getKey().equals(
-                BrowserSettings.PREF_DEFAULT_TEXT_ENCODING)) {
-            pref.setSummary((String) objValue);
-            return true;
-        } else if (pref.getKey().equals(BrowserSettings.PREF_CLEAR_HISTORY)
-                && ((Boolean) objValue).booleanValue() == true) {
-            // Need to tell the browser to remove the parent/child relationship
-            // between tabs
-            setResult(RESULT_OK, (new Intent()).putExtra(Intent.EXTRA_TEXT,
-                    pref.getKey()));
-            return true;
-        }
-        
-        return false;
-    }
-
-    private CharSequence getVisualTextSizeName(String enumName) {
-        CharSequence[] visualNames = getResources().getTextArray(
-                R.array.pref_text_size_choices);
-        CharSequence[] enumNames = getResources().getTextArray(
-                R.array.pref_text_size_values);
-
-        // Sanity check
-        if (visualNames.length != enumNames.length) {
-            return "";
-        }
-
-        for (int i = 0; i < enumNames.length; i++) {
-            if (enumNames[i].equals(enumName)) {
-                return visualNames[i];
-            }
-        }
-
-        return "";
-    }
-
-    private CharSequence getVisualDefaultZoomName(String enumName) {
-        CharSequence[] visualNames = getResources().getTextArray(
-                R.array.pref_default_zoom_choices);
-        CharSequence[] enumNames = getResources().getTextArray(
-                R.array.pref_default_zoom_values);
-
-        // Sanity check
-        if (visualNames.length != enumNames.length) {
-            return "";
-        }
-
-        for (int i = 0; i < enumNames.length; i++) {
-            if (enumNames[i].equals(enumName)) {
-                return visualNames[i];
-            }
-        }
-
-        return "";
+                PreferenceManager.getDefaultSharedPreferences(this));
     }
 }
diff --git a/src/com/android/browser/BrowserProvider.java b/src/com/android/browser/BrowserProvider.java
index 72ec819..cba16a0 100644
--- a/src/com/android/browser/BrowserProvider.java
+++ b/src/com/android/browser/BrowserProvider.java
@@ -29,8 +29,10 @@
 import android.content.SharedPreferences;
 import android.content.SharedPreferences.Editor;
 import android.content.UriMatcher;
+import android.content.res.Configuration;
 import android.database.AbstractCursor;
 import android.database.Cursor;
+import android.database.DatabaseUtils;
 import android.database.sqlite.SQLiteDatabase;
 import android.database.sqlite.SQLiteOpenHelper;
 import android.net.Uri;
@@ -38,6 +40,7 @@
 import android.preference.PreferenceManager;
 import android.provider.Browser;
 import android.provider.Browser.BookmarkColumns;
+import android.provider.Settings;
 import android.speech.RecognizerResultsIntent;
 import android.text.TextUtils;
 import android.util.Log;
@@ -84,6 +87,17 @@
     private static final int SUGGEST_COLUMN_QUERY_ID = 8;
     private static final int SUGGEST_COLUMN_INTENT_EXTRA_DATA = 9;
 
+    // how many suggestions will be shown in dropdown
+    // 0..SHORT: filled by browser db
+    private static final int MAX_SUGGEST_SHORT_SMALL = 3;
+    // SHORT..LONG: filled by search suggestions
+    private static final int MAX_SUGGEST_LONG_SMALL = 6;
+
+    // large screen size shows more
+    private static final int MAX_SUGGEST_SHORT_LARGE = 6;
+    private static final int MAX_SUGGEST_LONG_LARGE = 9;
+
+
     // shared suggestion columns
     private static final String[] COLUMNS = new String[] {
             "_id",
@@ -97,10 +111,6 @@
             SearchManager.SUGGEST_COLUMN_QUERY,
             SearchManager.SUGGEST_COLUMN_INTENT_EXTRA_DATA};
 
-    private static final int MAX_SUGGESTION_SHORT_ENTRIES = 3;
-    private static final int MAX_SUGGESTION_LONG_ENTRIES = 6;
-    private static final String MAX_SUGGESTION_LONG_ENTRIES_STRING =
-            Integer.valueOf(MAX_SUGGESTION_LONG_ENTRIES).toString();
 
     // make sure that these match the index of TABLE_NAMES
     private static final int URI_MATCH_BOOKMARKS = 0;
@@ -161,6 +171,9 @@
 
     private BrowserSettings mSettings;
 
+    private int mMaxSuggestionShortSize;
+    private int mMaxSuggestionLongSize;
+
     public BrowserProvider() {
     }
 
@@ -365,6 +378,20 @@
     @Override
     public boolean onCreate() {
         final Context context = getContext();
+        boolean xlargeScreenSize = (context.getResources().getConfiguration().screenLayout
+                & Configuration.SCREENLAYOUT_SIZE_MASK)
+                == Configuration.SCREENLAYOUT_SIZE_XLARGE;
+        boolean isPortrait = (context.getResources().getConfiguration().orientation
+                == Configuration.ORIENTATION_PORTRAIT);
+
+
+        if (xlargeScreenSize && isPortrait) {
+            mMaxSuggestionLongSize = MAX_SUGGEST_LONG_LARGE;
+            mMaxSuggestionShortSize = MAX_SUGGEST_SHORT_LARGE;
+        } else {
+            mMaxSuggestionLongSize = MAX_SUGGEST_LONG_SMALL;
+            mMaxSuggestionShortSize = MAX_SUGGEST_SHORT_SMALL;
+        }
         mOpenHelper = new DatabaseHelper(context);
         mBackupManager = new BackupManager(context);
         // we added "picasa web album" into default bookmarks for version 19.
@@ -431,10 +458,10 @@
         public MySuggestionCursor(Cursor hc, Cursor sc, String string) {
             mHistoryCursor = hc;
             mSuggestCursor = sc;
-            mHistoryCount = hc.getCount();
+            mHistoryCount = hc != null ? hc.getCount() : 0;
             mSuggestionCount = sc != null ? sc.getCount() : 0;
-            if (mSuggestionCount > (MAX_SUGGESTION_LONG_ENTRIES - mHistoryCount)) {
-                mSuggestionCount = MAX_SUGGESTION_LONG_ENTRIES - mHistoryCount;
+            if (mSuggestionCount > (mMaxSuggestionLongSize - mHistoryCount)) {
+                mSuggestionCount = mMaxSuggestionLongSize - mHistoryCount;
             }
             mString = string;
             mIncludeWebSearch = string.length() > 0;
@@ -648,6 +675,7 @@
         }
 
         // TODO Temporary change, finalize after jq's changes go in
+        @Override
         public void deactivate() {
             if (mHistoryCursor != null) {
                 mHistoryCursor.deactivate();
@@ -658,12 +686,14 @@
             super.deactivate();
         }
 
+        @Override
         public boolean requery() {
             return (mHistoryCursor != null ? mHistoryCursor.requery() : false) |
                     (mSuggestCursor != null ? mSuggestCursor.requery() : false);
         }
 
         // TODO Temporary change, finalize after jq's changes go in
+        @Override
         public void close() {
             super.close();
             if (mHistoryCursor != null) {
@@ -728,12 +758,15 @@
         public ResultsCursor(ArrayList<String> results) {
             mResults = results;
         }
+        @Override
         public int getCount() { return mResults.size(); }
 
+        @Override
         public String[] getColumnNames() {
             return RESULTS_COLUMNS;
         }
 
+        @Override
         public String getString(int column) {
             switch (column) {
                 case RESULT_ACTION_ID:
@@ -755,30 +788,39 @@
                     return null;
             }
         }
+        @Override
         public short getShort(int column) {
             throw new UnsupportedOperationException();
         }
+        @Override
         public int getInt(int column) {
             throw new UnsupportedOperationException();
         }
+        @Override
         public long getLong(int column) {
             if ((mPos != -1) && column == 0) {
                 return mPos;        // use row# as the _id
             }
             throw new UnsupportedOperationException();
         }
+        @Override
         public float getFloat(int column) {
             throw new UnsupportedOperationException();
         }
+        @Override
         public double getDouble(int column) {
             throw new UnsupportedOperationException();
         }
+        @Override
         public boolean isNull(int column) {
             throw new UnsupportedOperationException();
         }
     }
 
+    /** Contains custom suggestions results set by the UI */
     private ResultsCursor mResultsCursor;
+    /** Locks access to {@link #mResultsCursor} */
+    private Object mResultsCursorLock = new Object();
 
     /**
      * Provide a set of results to be returned to query, intended to be used
@@ -786,10 +828,12 @@
      * @param results Strings to display in the dropdown from the SearchDialog
      */
     /* package */ void setQueryResults(ArrayList<String> results) {
-        if (results == null) {
-            mResultsCursor = null;
-        } else {
-            mResultsCursor = new ResultsCursor(results);
+        synchronized (mResultsCursorLock) {
+            if (results == null) {
+                mResultsCursor = null;
+            } else {
+                mResultsCursor = new ResultsCursor(results);
+            }
         }
     }
 
@@ -801,57 +845,19 @@
         if (match == -1) {
             throw new IllegalArgumentException("Unknown URL");
         }
-        if (match == URI_MATCH_SUGGEST && mResultsCursor != null) {
-            Cursor results = mResultsCursor;
-            mResultsCursor = null;
-            return results;
+
+        // If results for the suggestion are already ready just return them directly
+        synchronized (mResultsCursorLock) {
+            if (match == URI_MATCH_SUGGEST && mResultsCursor != null) {
+                Cursor results = mResultsCursor;
+                mResultsCursor = null;
+                return results;
+            }
         }
-        SQLiteDatabase db = mOpenHelper.getReadableDatabase();
 
         if (match == URI_MATCH_SUGGEST || match == URI_MATCH_BOOKMARKS_SUGGEST) {
-            String suggestSelection;
-            String [] myArgs;
-            if (selectionArgs[0] == null || selectionArgs[0].equals("")) {
-                suggestSelection = null;
-                myArgs = null;
-            } else {
-                String like = selectionArgs[0] + "%";
-                if (selectionArgs[0].startsWith("http")
-                        || selectionArgs[0].startsWith("file")) {
-                    myArgs = new String[1];
-                    myArgs[0] = like;
-                    suggestSelection = selection;
-                } else {
-                    SUGGEST_ARGS[0] = "http://" + like;
-                    SUGGEST_ARGS[1] = "http://www." + like;
-                    SUGGEST_ARGS[2] = "https://" + like;
-                    SUGGEST_ARGS[3] = "https://www." + like;
-                    // To match against titles.
-                    SUGGEST_ARGS[4] = like;
-                    myArgs = SUGGEST_ARGS;
-                    suggestSelection = SUGGEST_SELECTION;
-                }
-            }
-
-            Cursor c = db.query(TABLE_NAMES[URI_MATCH_BOOKMARKS],
-                    SUGGEST_PROJECTION, suggestSelection, myArgs, null, null,
-                    ORDER_BY, MAX_SUGGESTION_LONG_ENTRIES_STRING);
-
-            if (match == URI_MATCH_BOOKMARKS_SUGGEST
-                    || Patterns.WEB_URL.matcher(selectionArgs[0]).matches()) {
-                return new MySuggestionCursor(c, null, "");
-            } else {
-                // get search suggestions if there is still space in the list
-                if (myArgs != null && myArgs.length > 1
-                        && c.getCount() < (MAX_SUGGESTION_SHORT_ENTRIES - 1)) {
-                    SearchEngine searchEngine = mSettings.getSearchEngine();
-                    if (searchEngine != null && searchEngine.supportsSuggestions()) {
-                        Cursor sc = searchEngine.getSuggestions(getContext(), selectionArgs[0]);
-                        return new MySuggestionCursor(c, sc, selectionArgs[0]);
-                    }
-                }
-                return new MySuggestionCursor(c, null, selectionArgs[0]);
-            }
+            // Handle suggestions
+            return doSuggestQuery(selection, selectionArgs, match == URI_MATCH_BOOKMARKS_SUGGEST);
         }
 
         String[] projection = null;
@@ -861,29 +867,62 @@
             projection[projectionIn.length] = "_id AS _id";
         }
 
-        StringBuilder whereClause = new StringBuilder(256);
+        String whereClause = null;
         if (match == URI_MATCH_BOOKMARKS_ID || match == URI_MATCH_SEARCHES_ID) {
-            whereClause.append("(_id = ").append(url.getPathSegments().get(1))
-                    .append(")");
+            whereClause = "_id = " + url.getPathSegments().get(1);
         }
 
-        // Tack on the user's selection, if present
-        if (selection != null && selection.length() > 0) {
-            if (whereClause.length() > 0) {
-                whereClause.append(" AND ");
-            }
-
-            whereClause.append('(');
-            whereClause.append(selection);
-            whereClause.append(')');
-        }
-        Cursor c = db.query(TABLE_NAMES[match % 10], projection,
-                whereClause.toString(), selectionArgs, null, null, sortOrder,
-                null);
+        Cursor c = mOpenHelper.getReadableDatabase().query(TABLE_NAMES[match % 10], projection,
+                DatabaseUtils.concatenateWhere(whereClause, selection), selectionArgs,
+                null, null, sortOrder, null);
         c.setNotificationUri(getContext().getContentResolver(), url);
         return c;
     }
 
+    private Cursor doSuggestQuery(String selection, String[] selectionArgs, boolean bookmarksOnly) {
+        String suggestSelection;
+        String [] myArgs;
+        if (selectionArgs[0] == null || selectionArgs[0].equals("")) {
+            return new MySuggestionCursor(null, null, "");
+        } else {
+            String like = selectionArgs[0] + "%";
+            if (selectionArgs[0].startsWith("http")
+                    || selectionArgs[0].startsWith("file")) {
+                myArgs = new String[1];
+                myArgs[0] = like;
+                suggestSelection = selection;
+            } else {
+                SUGGEST_ARGS[0] = "http://" + like;
+                SUGGEST_ARGS[1] = "http://www." + like;
+                SUGGEST_ARGS[2] = "https://" + like;
+                SUGGEST_ARGS[3] = "https://www." + like;
+                // To match against titles.
+                SUGGEST_ARGS[4] = like;
+                myArgs = SUGGEST_ARGS;
+                suggestSelection = SUGGEST_SELECTION;
+            }
+        }
+
+        Cursor c = mOpenHelper.getReadableDatabase().query(TABLE_NAMES[URI_MATCH_BOOKMARKS],
+                SUGGEST_PROJECTION, suggestSelection, myArgs, null, null,
+                ORDER_BY, Integer.toString(mMaxSuggestionLongSize));
+
+        if (bookmarksOnly || Patterns.WEB_URL.matcher(selectionArgs[0]).matches()) {
+            return new MySuggestionCursor(c, null, "");
+        } else {
+            // get search suggestions if there is still space in the list
+            if (myArgs != null && myArgs.length > 1
+                    && c.getCount() < (MAX_SUGGEST_SHORT_SMALL - 1)) {
+                SearchEngine searchEngine = mSettings.getSearchEngine();
+                if (searchEngine != null && searchEngine.supportsSuggestions()) {
+                    Cursor sc = searchEngine.getSuggestions(getContext(), selectionArgs[0]);
+                    return new MySuggestionCursor(c, sc, selectionArgs[0]);
+                }
+            }
+            return new MySuggestionCursor(c, null, selectionArgs[0]);
+        }
+    }
+
     @Override
     public String getType(Uri url) {
         int match = URI_MATCHER.match(url);
@@ -1089,4 +1128,10 @@
         }
     }
 
+    public static Cursor getBookmarksSuggestions(ContentResolver cr, String constraint) {
+        Uri uri = Uri.parse("content://browser/" + SearchManager.SUGGEST_URI_PATH_QUERY);
+        return cr.query(uri, SUGGEST_PROJECTION, SUGGEST_SELECTION,
+            new String[] { constraint }, ORDER_BY);
+    }
+
 }
diff --git a/src/com/android/browser/BrowserSettings.java b/src/com/android/browser/BrowserSettings.java
index 3791eb0..db0f73e 100644
--- a/src/com/android/browser/BrowserSettings.java
+++ b/src/com/android/browser/BrowserSettings.java
@@ -28,9 +28,15 @@
 import android.content.SharedPreferences;
 import android.content.SharedPreferences.Editor;
 import android.database.ContentObserver;
+import android.database.Cursor;
+import android.net.Uri;
+import android.os.AsyncTask;
 import android.os.Handler;
+import android.os.Message;
 import android.preference.PreferenceActivity;
+import android.preference.PreferenceManager;
 import android.preference.PreferenceScreen;
+import android.provider.Browser;
 import android.provider.Settings;
 import android.util.Log;
 import android.webkit.CookieManager;
@@ -40,9 +46,9 @@
 import android.webkit.WebViewDatabase;
 import android.webkit.WebIconDatabase;
 import android.webkit.WebSettings;
+import android.webkit.WebSettings.AutoFillProfile;
 import android.webkit.WebStorage;
-import android.preference.PreferenceManager;
-import android.provider.Browser;
+import android.widget.Toast;
 
 import java.util.HashMap;
 import java.util.Map;
@@ -62,7 +68,7 @@
  * To remove an observer:
  * s.deleteObserver(webView.getSettings());
  */
-class BrowserSettings extends Observable {
+public class BrowserSettings extends Observable {
 
     // Private variables for settings
     // NOTE: these defaults need to be kept in sync with the XML
@@ -76,6 +82,7 @@
     private boolean showSecurityWarnings;
     private boolean rememberPasswords;
     private boolean saveFormData;
+    private boolean autoFillEnabled;
     private boolean openInBackground;
     private String defaultTextEncodingName;
     private String homeUrl = "";
@@ -115,8 +122,8 @@
     private boolean showConsole = true;
 
     // Private preconfigured values
-    private static int minimumFontSize = 8;
-    private static int minimumLogicalFontSize = 8;
+    private static int minimumFontSize = 1;
+    private static int minimumLogicalFontSize = 1;
     private static int defaultFontSize = 16;
     private static int defaultFixedFontSize = 13;
     private static WebSettings.TextSize textSize =
@@ -125,6 +132,15 @@
         WebSettings.ZoomDensity.MEDIUM;
     private static int pageCacheCapacity;
 
+
+    private AutoFillProfile autoFillProfile;
+    // Default to zero. In the case no profile is set up, the initial
+    // value will come from the AutoFillSettingsFragment when the user
+    // creates a profile. Otherwise, we'll read the ID of the last used
+    // profile from the prefs db.
+    private int autoFillActiveProfileId;
+    private static final int NO_AUTOFILL_PROFILE_SET = 0;
+
     // Preference keys that are used outside this class
     public final static String PREF_CLEAR_CACHE = "privacy_clear_cache";
     public final static String PREF_CLEAR_COOKIES = "privacy_clear_cookies";
@@ -145,6 +161,9 @@
             "default_text_encoding";
     public final static String PREF_CLEAR_GEOLOCATION_ACCESS =
             "privacy_clear_geolocation_access";
+    public final static String PREF_AUTOFILL_ENABLED = "autofill_enabled";
+    public final static String PREF_AUTOFILL_PROFILE = "autofill_profile";
+    public final static String PREF_AUTOFILL_ACTIVE_PROFILE_ID = "autofill_active_profile_id";
 
     private static final String DESKTOP_USERAGENT = "Mozilla/5.0 (Macintosh; " +
             "U; Intel Mac OS X 10_6_3; en-us) AppleWebKit/533.16 (KHTML, " +
@@ -166,6 +185,10 @@
     // a ListView
     public final static int MAX_TEXTVIEW_LEN = 80;
 
+    public static final String RLZ_PROVIDER = "com.google.android.partnersetup.rlzappprovider";
+
+    public static final Uri RLZ_PROVIDER_URI = Uri.parse("content://" + RLZ_PROVIDER + "/");
+
     private TabControl mTabControl;
 
     // Single instance of the BrowserSettings for use in the Browser app.
@@ -221,6 +244,7 @@
             s.setDefaultZoom(b.zoomDensity);
             s.setLightTouchEnabled(b.lightTouch);
             s.setSaveFormData(b.saveFormData);
+            s.setAutoFillEnabled(b.autoFillEnabled);
             s.setSavePassword(b.rememberPasswords);
             s.setLoadWithOverviewMode(b.loadsPageInOverviewMode);
             s.setPageCacheCapacity(pageCacheCapacity);
@@ -229,6 +253,9 @@
             s.setNeedInitialFocus(false);
             // Browser supports multiple windows
             s.setSupportMultipleWindows(true);
+            // enable smooth transition for better performance during panning or
+            // zooming
+            s.setEnableSmoothTransition(true);
 
             // HTML5 API flags
             s.setAppCacheEnabled(b.appCacheEnabled);
@@ -243,6 +270,9 @@
             s.setDatabasePath(b.databasePath);
             s.setGeolocationDatabasePath(b.geolocationDatabasePath);
 
+            // Active AutoFill profile data.
+            s.setAutoFillProfile(b.autoFillProfile);
+
             b.updateTabControlSettings();
         }
     }
@@ -250,7 +280,7 @@
     /**
      * Load settings from the browser app's database.
      * NOTE: Strings used for the preferences must match those specified
-     * in the browser_preferences.xml
+     * in the various preference XML files.
      * @param ctx A Context object used to query the browser's settings
      *            database. If the database exists, the saved settings will be
      *            stored in this BrowserSettings object. This will update all
@@ -288,10 +318,48 @@
             pageCacheCapacity = 1;
         }
 
-    // Load the defaults from the xml
-        // This call is TOO SLOW, need to manually keep the defaults
-        // in sync
-        //PreferenceManager.setDefaultValues(ctx, R.xml.browser_preferences);
+        // Read the last active AutoFill profile id.
+        autoFillActiveProfileId = p.getInt(
+                PREF_AUTOFILL_ACTIVE_PROFILE_ID, autoFillActiveProfileId);
+
+        // Load the autofill profile data from the database. We use a database separate
+        // to the browser preference DB to make it easier to support multiple profiles
+        // and switching between them.
+        AutoFillProfileDatabase autoFillDb = AutoFillProfileDatabase.getInstance(ctx);
+        Cursor c = autoFillDb.getProfile(autoFillActiveProfileId);
+
+        if (c.getCount() > 0) {
+            c.moveToFirst();
+
+            String fullName = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.FULL_NAME));
+            String email = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.EMAIL_ADDRESS));
+            String company = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.COMPANY_NAME));
+            String addressLine1 = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.ADDRESS_LINE_1));
+            String addressLine2 = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.ADDRESS_LINE_2));
+            String city = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.CITY));
+            String state = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.STATE));
+            String zip = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.ZIP_CODE));
+            String country = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.COUNTRY));
+            String phone = c.getString(c.getColumnIndex(
+                    AutoFillProfileDatabase.Profiles.PHONE_NUMBER));
+            autoFillProfile = new AutoFillProfile(autoFillActiveProfileId,
+                    fullName, email, company, addressLine1, addressLine2, city,
+                    state, zip, country, phone);
+        }
+        c.close();
+        autoFillDb.close();
+
+        // PreferenceManager.setDefaultValues is TOO SLOW, need to manually keep
+        // the defaults in sync
         syncSharedPreferences(ctx, p);
     }
 
@@ -332,6 +400,7 @@
                 rememberPasswords);
         saveFormData = p.getBoolean("save_formdata",
                 saveFormData);
+        autoFillEnabled = p.getBoolean("autofill_enabled", autoFillEnabled);
         boolean accept_cookies = p.getBoolean("accept_cookies",
                 CookieManager.getInstance().acceptCookie());
         CookieManager.getInstance().setAcceptCookie(accept_cookies);
@@ -466,6 +535,31 @@
         update();
     }
 
+    public void setAutoFillProfile(Context ctx, AutoFillProfile profile, Message msg) {
+        if (profile != null) {
+            setActiveAutoFillProfileId(ctx, profile.getUniqueId());
+            // Update the AutoFill DB with the new profile.
+            new SaveProfileToDbTask(ctx, msg).execute(profile);
+        } else {
+            // Delete the current profile.
+            new DeleteProfileFromDbTask(ctx, msg).execute(autoFillProfile.getUniqueId());
+            setActiveAutoFillProfileId(ctx, NO_AUTOFILL_PROFILE_SET);
+        }
+        autoFillProfile = profile;
+    }
+
+    public AutoFillProfile getAutoFillProfile() {
+        return autoFillProfile;
+    }
+
+    private void setActiveAutoFillProfileId(Context context, int activeProfileId) {
+        autoFillActiveProfileId = activeProfileId;
+        Editor ed = PreferenceManager.
+            getDefaultSharedPreferences(context).edit();
+        ed.putInt(PREF_AUTOFILL_ACTIVE_PROFILE_ID, activeProfileId);
+        ed.apply();
+    }
+
     /**
      * Add a WebSettings object to the list of observers that will be updated
      * when update() is called.
@@ -568,52 +662,31 @@
             : ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED);
     }
 
-    private void maybeDisableWebsiteSettings(Context context) {
-        PreferenceActivity activity = (PreferenceActivity) context;
-        final PreferenceScreen screen = (PreferenceScreen)
-            activity.findPreference(BrowserSettings.PREF_WEBSITE_SETTINGS);
-        screen.setEnabled(false);
-        WebStorage.getInstance().getOrigins(new ValueCallback<Map>() {
-            public void onReceiveValue(Map webStorageOrigins) {
-                if ((webStorageOrigins != null) && !webStorageOrigins.isEmpty()) {
-                    screen.setEnabled(true);
-                }
-            }
-        });
-
-        GeolocationPermissions.getInstance().getOrigins(new ValueCallback<Set<String> >() {
-            public void onReceiveValue(Set<String> geolocationOrigins) {
-                if ((geolocationOrigins != null) && !geolocationOrigins.isEmpty()) {
-                    screen.setEnabled(true);
-                }
-            }
-        });
-    }
-
     /*package*/ void clearDatabases(Context context) {
         WebStorage.getInstance().deleteAllData();
-        maybeDisableWebsiteSettings(context);
     }
 
     /*package*/ void clearLocationAccess(Context context) {
         GeolocationPermissions.getInstance().clearAll();
-        maybeDisableWebsiteSettings(context);
     }
 
     /*package*/ void resetDefaultPreferences(Context ctx) {
         reset();
-        SharedPreferences p =
-            PreferenceManager.getDefaultSharedPreferences(ctx);
+        SharedPreferences p = PreferenceManager.getDefaultSharedPreferences(ctx);
         p.edit().clear().apply();
-        PreferenceManager.setDefaultValues(ctx, R.xml.browser_preferences,
-                true);
+        PreferenceManager.setDefaultValues(ctx, R.xml.page_content_preferences, true);
+        PreferenceManager.setDefaultValues(ctx, R.xml.personal_preferences, true);
+        PreferenceManager.setDefaultValues(ctx, R.xml.privacy_preferences, true);
+        PreferenceManager.setDefaultValues(ctx, R.xml.security_preferences, true);
+        PreferenceManager.setDefaultValues(ctx, R.xml.advanced_preferences, true);
         // reset homeUrl
         setHomePage(ctx, getFactoryResetHomeUrl(ctx));
         // reset appcache max size
         appCacheMaxSize = webStorageSizeManager.getAppCacheMaxSize();
+        setActiveAutoFillProfileId(ctx, NO_AUTOFILL_PROFILE_SET);
     }
 
-    private String getFactoryResetHomeUrl(Context context) {
+    /*package*/ static String getFactoryResetHomeUrl(Context context) {
         String url = context.getResources().getString(R.string.homepage_base);
         if (url.indexOf("{CID}") != -1) {
             url = url.replace("{CID}",
@@ -639,6 +712,7 @@
         showSecurityWarnings = true;
         rememberPasswords = true;
         saveFormData = true;
+        autoFillEnabled = false;
         openInBackground = false;
         autoFitPage = true;
         landscapeOnly = false;
@@ -651,4 +725,53 @@
         geolocationEnabled = true;
         workersEnabled = true;  // only affects V8. JSC does not have a similar setting
     }
+
+    private abstract class AutoFillProfileDbTask<T> extends AsyncTask<T, Void, Void> {
+        Context mContext;
+        AutoFillProfileDatabase mAutoFillProfileDb;
+        Message mCompleteMessage;
+
+        public AutoFillProfileDbTask(Context ctx, Message msg) {
+            mContext = ctx;
+            mCompleteMessage = msg;
+        }
+
+        protected void onPostExecute(Void result) {
+            if (mCompleteMessage != null) {
+                mCompleteMessage.sendToTarget();
+            }
+            mAutoFillProfileDb.close();
+        }
+
+        abstract protected Void doInBackground(T... values);
+    }
+
+
+    private class SaveProfileToDbTask extends AutoFillProfileDbTask<AutoFillProfile> {
+        public SaveProfileToDbTask(Context ctx, Message msg) {
+            super(ctx, msg);
+        }
+
+        protected Void doInBackground(AutoFillProfile... values) {
+            mAutoFillProfileDb = AutoFillProfileDatabase.getInstance(mContext);
+            assert autoFillActiveProfileId != NO_AUTOFILL_PROFILE_SET;
+            AutoFillProfile newProfile = values[0];
+            mAutoFillProfileDb.addOrUpdateProfile(autoFillActiveProfileId, newProfile);
+            return null;
+        }
+    }
+
+    private class DeleteProfileFromDbTask extends AutoFillProfileDbTask<Integer> {
+        public DeleteProfileFromDbTask(Context ctx, Message msg) {
+            super(ctx, msg);
+        }
+
+        protected Void doInBackground(Integer... values) {
+            mAutoFillProfileDb = AutoFillProfileDatabase.getInstance(mContext);
+            int id = values[0];
+            assert  id > 0;
+            mAutoFillProfileDb.dropProfile(id);
+            return null;
+        }
+    }
 }
diff --git a/src/com/android/browser/CircularProgressView.java b/src/com/android/browser/CircularProgressView.java
new file mode 100644
index 0000000..48f293a
--- /dev/null
+++ b/src/com/android/browser/CircularProgressView.java
@@ -0,0 +1,140 @@
+
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser;
+
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.Paint;
+import android.graphics.Path;
+import android.graphics.RectF;
+import android.util.AttributeSet;
+import android.widget.ImageButton;
+
+/**
+ *
+ */
+public class CircularProgressView extends ImageButton {
+
+    private static final int[] ALPHAS = {
+       64, 96, 128, 160, 192, 192, 160, 128, 96, 64
+    };
+
+    // 100 ms delay between frames, 10fps
+    private static int ALPHA_REFRESH_DELAY = 100;
+
+    private int     mEndAngle;
+    private int     mProgress;
+    private Paint   mPaint;
+    private int     mAlpha;
+    private boolean mAnimated;
+    private RectF   mRect;
+    private int     mMaxProgress;
+
+    /**
+     * @param context
+     * @param attrs
+     * @param defStyle
+     */
+    public CircularProgressView(Context context, AttributeSet attrs, int defStyle) {
+        super(context, attrs, defStyle);
+        init(context);
+    }
+
+    /**
+     * @param context
+     * @param attrs
+     */
+    public CircularProgressView(Context context, AttributeSet attrs) {
+        super(context, attrs);
+        init(context);
+    }
+
+    /**
+     * @param context
+     */
+    public CircularProgressView(Context context) {
+        super(context);
+        init(context);
+    }
+
+    private void init(Context ctx) {
+        mEndAngle = 0;
+        mProgress = 0;
+        mMaxProgress = 100;
+        mPaint = new Paint();
+        mPaint.setAntiAlias(true);
+        mPaint.setColor(Color.BLACK);
+        mRect = new RectF();
+    }
+
+    void setMaxProgress(int max) {
+        mMaxProgress = max;
+    }
+
+    private synchronized boolean isAnimated() {
+        return mAnimated;
+    }
+
+    private synchronized void setAnimated(boolean animated) {
+        mAnimated = animated;
+    }
+
+    void setProgress(int progress) {
+        mProgress = progress;
+        mEndAngle = 360 * progress / mMaxProgress;
+        invalidate();
+        if (!isAnimated() && (progress > 0) && (progress < mMaxProgress)) {
+            setAnimated(true);
+            mAlpha = 0;
+            post(new Runnable() {
+                @Override
+                public void run() {
+                    if (isAnimated()) {
+                        mAlpha = (mAlpha + 1) % ALPHAS.length;
+                        mPaint.setAlpha(ALPHAS[mAlpha]);
+                        invalidate();
+                        postDelayed(this, ALPHA_REFRESH_DELAY);
+                    }
+                }
+            });
+        } else if ((progress <= 0) || (progress >= mMaxProgress))  {
+            setAnimated(false);
+        }
+    }
+
+    @Override
+    public void onDraw(Canvas canvas) {
+        int w = getWidth();
+        int h = getHeight();
+        float cx = w * 0.5f;
+        float cy = h * 0.5f;
+        mRect.set(0, 0, w, h);
+        if ((mProgress > 0) && (mProgress < mMaxProgress)) {
+            Path p = new Path();
+            p.moveTo(cx, cy);
+            p.lineTo(cx, 0);
+            p.arcTo(mRect, 270, mEndAngle);
+            p.lineTo(cx, cy);
+            int state = canvas.save();
+            canvas.drawPath(p, mPaint);
+            canvas.restoreToCount(state);
+        }
+        super.onDraw(canvas);
+    }
+
+}
diff --git a/src/com/android/browser/CombinedBookmarkHistoryActivity.java b/src/com/android/browser/CombinedBookmarkHistoryActivity.java
deleted file mode 100644
index 194956f..0000000
--- a/src/com/android/browser/CombinedBookmarkHistoryActivity.java
+++ /dev/null
@@ -1,192 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser;
-
-import android.app.Activity;
-import android.app.TabActivity;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.os.AsyncTask;
-import android.os.Bundle;
-import android.provider.Browser;
-import android.webkit.WebIconDatabase;
-import android.webkit.WebIconDatabase.IconListener;
-import android.widget.TabHost;
-
-import java.util.HashMap;
-import java.util.Vector;
-
-public class CombinedBookmarkHistoryActivity extends TabActivity
-        implements TabHost.OnTabChangeListener {
-    /**
-     * Used to inform BrowserActivity to remove the parent/child relationships
-     * from all the tabs.
-     */
-    private String mExtraData;
-    /**
-     * Intent to be passed to calling Activity when finished.  Keep a pointer to
-     * it locally so mExtraData can be added.
-     */
-    private Intent mResultData;
-    /**
-     * Result code to pass back to calling Activity when finished.
-     */
-    private int mResultCode;
-
-    /* package */ static String BOOKMARKS_TAB = "bookmark";
-    /* package */ static String VISITED_TAB = "visited";
-    /* package */ static String HISTORY_TAB = "history";
-    /* package */ static String STARTING_TAB = "tab";
-
-    static class IconListenerSet implements IconListener {
-        // Used to store favicons as we get them from the database
-        // FIXME: We use a different method to get the Favicons in
-        // BrowserBookmarksAdapter. They should probably be unified.
-        private HashMap<String, Bitmap> mUrlsToIcons;
-        private Vector<IconListener> mListeners;
-
-        public IconListenerSet() {
-            mUrlsToIcons = new HashMap<String, Bitmap>();
-            mListeners = new Vector<IconListener>();
-        }
-        public void onReceivedIcon(String url, Bitmap icon) {
-            mUrlsToIcons.put(url, icon);
-            for (IconListener listener : mListeners) {
-                listener.onReceivedIcon(url, icon);
-            }
-        }
-        public void addListener(IconListener listener) {
-            mListeners.add(listener);
-        }
-        public void removeListener(IconListener listener) {
-            mListeners.remove(listener);
-        }
-        public Bitmap getFavicon(String url) {
-            return (Bitmap) mUrlsToIcons.get(url);
-        }
-    }
-    private static IconListenerSet sIconListenerSet;
-    static IconListenerSet getIconListenerSet() {
-        if (null == sIconListenerSet) {
-            sIconListenerSet = new IconListenerSet();
-        }
-        return sIconListenerSet;
-    }
-
-    @Override
-    protected void onCreate(Bundle savedInstanceState) {
-        super.onCreate(savedInstanceState);
-        setContentView(R.layout.tabs);
-
-        setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
-
-        getTabHost().setOnTabChangedListener(this);
-
-        Bundle extras = getIntent().getExtras();
-
-        Intent bookmarksIntent = new Intent(this, BrowserBookmarksPage.class);
-        if (extras != null) {
-            bookmarksIntent.putExtras(extras);
-        }
-        createTab(bookmarksIntent, R.string.tab_bookmarks,
-                R.drawable.browser_bookmark_tab, BOOKMARKS_TAB);
-
-        Intent visitedIntent = new Intent(this, BrowserBookmarksPage.class);
-        // Need to copy extras so the bookmarks activity and this one will be
-        // different
-        Bundle visitedExtras = extras == null ? new Bundle() : new Bundle(extras);
-        visitedExtras.putBoolean("mostVisited", true);
-        visitedIntent.putExtras(visitedExtras);
-        createTab(visitedIntent, R.string.tab_most_visited,
-                R.drawable.browser_visited_tab, VISITED_TAB);
-
-        Intent historyIntent = new Intent(this, BrowserHistoryPage.class);
-        String defaultTab = null;
-        if (extras != null) {
-            historyIntent.putExtras(extras);
-            defaultTab = extras.getString(STARTING_TAB);
-        }
-        createTab(historyIntent, R.string.tab_history,
-                R.drawable.browser_history_tab, HISTORY_TAB);
-
-        if (defaultTab != null) {
-            getTabHost().setCurrentTab(2);
-        }
-
-        // XXX: Must do this before launching the AsyncTask to avoid a
-        // potential crash if the icon database has not been created.
-        WebIconDatabase.getInstance();
-        // Do this every time we launch the activity in case a new favicon was
-        // added to the webkit db.
-        (new AsyncTask<Void, Void, Void>() {
-            public Void doInBackground(Void... v) {
-                Browser.requestAllIcons(getContentResolver(),
-                    Browser.BookmarkColumns.FAVICON + " is NULL",
-                    getIconListenerSet());
-                return null;
-            }
-        }).execute();
-    }
-
-    private void createTab(Intent intent, int labelResId, int iconResId,
-            String tab) {
-        Resources resources = getResources();
-        TabHost tabHost = getTabHost();
-        tabHost.addTab(tabHost.newTabSpec(tab).setIndicator(
-                resources.getText(labelResId), resources.getDrawable(iconResId))
-                .setContent(intent));
-    }
-    // Copied from DialTacts Activity
-    /** {@inheritDoc} */
-    public void onTabChanged(String tabId) {
-        Activity activity = getLocalActivityManager().getActivity(tabId);
-        if (activity != null) {
-            activity.onWindowFocusChanged(true);
-        }
-    }
-
-    /**
-     * Store extra data in the Intent to return to the calling Activity to tell
-     * it to clear the parent/child relationships from all tabs.
-     */
-    /* package */ void removeParentChildRelationShips() {
-        mExtraData = BrowserSettings.PREF_CLEAR_HISTORY;
-    }
-
-    /**
-     * Custom setResult() method so that the Intent can have extra data attached
-     * if necessary.
-     * @param resultCode Uses same codes as Activity.setResult
-     * @param data Intent returned to onActivityResult.
-     */
-    /* package */ void setResultFromChild(int resultCode, Intent data) {
-        mResultCode = resultCode;
-        mResultData = data;
-    }
-
-    @Override
-    public void finish() {
-        if (mExtraData != null) {
-            mResultCode = RESULT_OK;
-            if (mResultData == null) mResultData = new Intent();
-            mResultData.putExtra(Intent.EXTRA_TEXT, mExtraData);
-        }
-        setResult(mResultCode, mResultData);
-        super.finish();
-    }
-}
diff --git a/src/com/android/browser/CombinedBookmarkHistoryView.java b/src/com/android/browser/CombinedBookmarkHistoryView.java
new file mode 100644
index 0000000..c829079
--- /dev/null
+++ b/src/com/android/browser/CombinedBookmarkHistoryView.java
@@ -0,0 +1,213 @@
+/*
+ * Copyright (C) 2009 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.BreadCrumbView.Controller;
+
+import android.app.Fragment;
+import android.app.FragmentManager;
+import android.app.FragmentTransaction;
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.provider.Browser;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.webkit.WebIconDatabase;
+import android.webkit.WebIconDatabase.IconListener;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import java.util.HashMap;
+import java.util.Vector;
+
+interface BookmarksHistoryCallbacks {
+    public void onUrlSelected(String url, boolean newWindow);
+    public void onRemoveParentChildRelationships();
+    public void onComboCanceled();
+}
+
+public class CombinedBookmarkHistoryView extends LinearLayout
+        implements OnClickListener, Controller {
+
+    final static String STARTING_FRAGMENT = "fragment";
+
+    final static int FRAGMENT_ID_BOOKMARKS = 1;
+    final static int FRAGMENT_ID_HISTORY = 2;
+
+    private BrowserActivity mBrowserActivity;
+
+    private Bundle mExtras;
+
+    long mCurrentFragment;
+
+    View mTabs;
+    BreadCrumbView mCrumbs;
+    TextView mTabBookmarks;
+    TextView mTabHistory;
+    TextView mAddBookmark;
+
+    BrowserBookmarksPage mBookmarks;
+    BrowserHistoryPage mHistory;
+
+    static class IconListenerSet implements IconListener {
+        // Used to store favicons as we get them from the database
+        // FIXME: We use a different method to get the Favicons in
+        // BrowserBookmarksAdapter. They should probably be unified.
+        private HashMap<String, Bitmap> mUrlsToIcons;
+        private Vector<IconListener> mListeners;
+
+        public IconListenerSet() {
+            mUrlsToIcons = new HashMap<String, Bitmap>();
+            mListeners = new Vector<IconListener>();
+        }
+        @Override
+        public void onReceivedIcon(String url, Bitmap icon) {
+            mUrlsToIcons.put(url, icon);
+            for (IconListener listener : mListeners) {
+                listener.onReceivedIcon(url, icon);
+            }
+        }
+        public void addListener(IconListener listener) {
+            mListeners.add(listener);
+        }
+        public void removeListener(IconListener listener) {
+            mListeners.remove(listener);
+        }
+        public Bitmap getFavicon(String url) {
+            return mUrlsToIcons.get(url);
+        }
+    }
+
+    private static IconListenerSet sIconListenerSet;
+    static IconListenerSet getIconListenerSet() {
+        if (null == sIconListenerSet) {
+            sIconListenerSet = new IconListenerSet();
+        }
+        return sIconListenerSet;
+    }
+
+    public CombinedBookmarkHistoryView(Context context, int startingFragment, Bundle extras) {
+        super(context);
+        mBrowserActivity = (BrowserActivity) context;
+        mExtras = extras;
+        View v = LayoutInflater.from(context).inflate(R.layout.bookmarks_history, this);
+        Resources res = context.getResources();
+
+//        setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
+
+        mTabs = findViewById(R.id.tabs);
+        mCrumbs = (BreadCrumbView) findViewById(R.id.crumbs);
+        mCrumbs.setController(this);
+
+        mTabBookmarks = (TextView) findViewById(R.id.bmtab);
+        mTabHistory = (TextView) findViewById(R.id.historytab);
+        mAddBookmark = (TextView) findViewById(R.id.addbm);
+        mAddBookmark.setOnClickListener(this);
+        mTabHistory.setOnClickListener(this);
+        mTabBookmarks.setOnClickListener(this);
+        // Start up the default fragment
+        initFragments(mExtras);
+        loadFragment(startingFragment, mExtras, false);
+
+        // XXX: Must do this before launching the AsyncTask to avoid a
+        // potential crash if the icon database has not been created.
+        WebIconDatabase.getInstance();
+
+        // Do this every time the view is created in case a new favicon was
+        // added to the webkit db.
+        (new AsyncTask<Void, Void, Void>() {
+            @Override
+            public Void doInBackground(Void... v) {
+                Browser.requestAllIcons(mBrowserActivity.getContentResolver(),
+                        Browser.BookmarkColumns.FAVICON + " is NULL", getIconListenerSet());
+                return null;
+            }
+        }).execute();
+
+    }
+
+    private void initFragments(Bundle extras) {
+        mBookmarks =  BrowserBookmarksPage.newInstance(mBrowserActivity, mCrumbs, extras);
+        mHistory = BrowserHistoryPage.newInstance(mBrowserActivity, extras);
+    }
+
+    private void loadFragment(int id, Bundle extras, boolean notify) {
+        String fragmentClassName;
+        Fragment fragment = null;
+        switch (id) {
+            case FRAGMENT_ID_BOOKMARKS:
+                fragment = mBookmarks;
+                mCrumbs.setVisibility(View.VISIBLE);
+                if (notify) {
+                    mCrumbs.notifyController();
+                }
+                break;
+            case FRAGMENT_ID_HISTORY:
+                fragment = mHistory;
+                mCrumbs.setVisibility(View.GONE);
+                break;
+            default:
+                throw new IllegalArgumentException();
+        }
+        mCurrentFragment = id;
+
+        FragmentManager fm = mBrowserActivity.getFragmentManager();
+        FragmentTransaction transaction = fm.openTransaction();
+        transaction.replace(R.id.fragment, fragment);
+        transaction.commit();
+    }
+
+    @Override
+    public void onClick(View view) {
+        if ((mTabHistory == view) && (mCurrentFragment != FRAGMENT_ID_HISTORY)) {
+            loadFragment(FRAGMENT_ID_HISTORY, mExtras, false);
+        } else if (mTabBookmarks == view) {
+            if (mCurrentFragment != FRAGMENT_ID_BOOKMARKS) {
+                loadFragment(FRAGMENT_ID_BOOKMARKS, mExtras, true);
+            } else {
+                mCrumbs.clear();
+            }
+        } else if (mAddBookmark == view) {
+            mBrowserActivity.bookmarkCurrentPage(mBookmarks.getFolderId());
+        }
+    }
+
+    /**
+     * BreadCrumb controller callback
+     */
+    @Override
+    public void onTop(int level, Object data) {
+        mBookmarks.onFolderChange(level, data);
+    }
+
+    /**
+     * callback for back key presses
+     */
+    boolean onBackPressed() {
+        if ((mCurrentFragment == FRAGMENT_ID_BOOKMARKS) &&
+                (mCrumbs.size() > 0)) {
+            mCrumbs.popView();
+            return true;
+        }
+        return false;
+    }
+
+}
diff --git a/src/com/android/browser/DateSortedExpandableListAdapter.java b/src/com/android/browser/DateSortedExpandableListAdapter.java
index 1d04493..a48efe6 100644
--- a/src/com/android/browser/DateSortedExpandableListAdapter.java
+++ b/src/com/android/browser/DateSortedExpandableListAdapter.java
@@ -17,65 +17,55 @@
 package com.android.browser;
 
 import android.content.Context;
-import android.database.ContentObserver;
 import android.database.Cursor;
 import android.database.DataSetObserver;
-import android.os.Handler;
-import android.provider.BaseColumns;
 import android.view.LayoutInflater;
 import android.view.View;
 import android.view.ViewGroup;
 import android.webkit.DateSorter;
-import android.widget.ExpandableListAdapter;
+import android.widget.BaseExpandableListAdapter;
 import android.widget.ExpandableListView;
 import android.widget.TextView;
 
-import java.util.Vector;
-
 /**
  * ExpandableListAdapter which separates data into categories based on date.
  * Used for History and Downloads.
  */
-public class DateSortedExpandableListAdapter implements ExpandableListAdapter {
+public class DateSortedExpandableListAdapter extends BaseExpandableListAdapter {
     // Array for each of our bins.  Each entry represents how many items are
     // in that bin.
     private int mItemMap[];
     // This is our GroupCount.  We will have at most DateSorter.DAY_COUNT
     // bins, less if the user has no items in one or more bins.
     private int mNumberOfBins;
-    private Vector<DataSetObserver> mObservers;
     private Cursor mCursor;
     private DateSorter mDateSorter;
     private int mDateIndex;
     private int mIdIndex;
     private Context mContext;
 
-    private class ChangeObserver extends ContentObserver {
-        public ChangeObserver() {
-            super(new Handler());
+    boolean mDataValid;
+
+    DataSetObserver mDataSetObserver = new DataSetObserver() {
+        @Override
+        public void onChanged() {
+            mDataValid = true;
+            notifyDataSetChanged();
         }
 
         @Override
-        public boolean deliverSelfNotifications() {
-            return true;
+        public void onInvalidated() {
+            mDataValid = false;
+            notifyDataSetInvalidated();
         }
-
-        @Override
-        public void onChange(boolean selfChange) {
-            refreshData();
-        }
-    }
-
-    public DateSortedExpandableListAdapter(Context context, Cursor cursor,
-            int dateIndex) {
+    };
+    
+    public DateSortedExpandableListAdapter(Context context, int dateIndex) {
         mContext = context;
         mDateSorter = new DateSorter(context);
-        mObservers = new Vector<DataSetObserver>();
-        mCursor = cursor;
-        mIdIndex = cursor.getColumnIndexOrThrow(BaseColumns._ID);
-        cursor.registerContentObserver(new ChangeObserver());
         mDateIndex = dateIndex;
-        buildMap();
+        mDataValid = false;
+        mIdIndex = -1;
     }
 
     /**
@@ -122,6 +112,7 @@
      * @return corresponding byte array from the Cursor.
      */
     /* package */ byte[] getBlob(int cursorIndex) {
+        if (!mDataValid) return null; 
         return mCursor.getBlob(cursorIndex);
     }
 
@@ -138,6 +129,7 @@
      * @return corresponding integer from the Cursor.
      */
     /* package */ int getInt(int cursorIndex) {
+        if (!mDataValid) return 0; 
         return mCursor.getInt(cursorIndex);
     }
 
@@ -146,6 +138,7 @@
      * already been moved to the correct position.
      */
     /* package */ long getLong(int cursorIndex) {
+        if (!mDataValid) return 0; 
         return mCursor.getLong(cursorIndex);
     }
 
@@ -158,6 +151,7 @@
      * @return corresponding String from the Cursor.
      */
     /* package */ String getString(int cursorIndex) {
+        if (!mDataValid) return null; 
         return mCursor.getString(cursorIndex);
     }
 
@@ -166,6 +160,7 @@
      * @param childId ID of the child view in question.
      * @return int Group position of the containing group.
     /* package */ int groupFromChildId(long childId) {
+        if (!mDataValid) return -1; 
         int group = -1;
         for (mCursor.moveToFirst(); !mCursor.isAfterLast();
                 mCursor.moveToNext()) {
@@ -173,11 +168,15 @@
                 int bin = mDateSorter.getIndex(getLong(mDateIndex));
                 // bin is the same as the group if the number of bins is the
                 // same as DateSorter
-                if (mDateSorter.DAY_COUNT == mNumberOfBins) return bin;
+                if (DateSorter.DAY_COUNT == mNumberOfBins) {
+                    return bin;
+                }
                 // There are some empty bins.  Find the corresponding group.
                 group = 0;
                 for (int i = 0; i < bin; i++) {
-                    if (mItemMap[i] != 0) group++;
+                    if (mItemMap[i] != 0) {
+                        group++;
+                    }
                 }
                 break;
             }
@@ -193,6 +192,7 @@
      * @return The corresponding bin that holds that group.
      */
     private int groupPositionToBin(int groupPosition) {
+        if (!mDataValid) return -1; 
         if (groupPosition < 0 || groupPosition >= DateSorter.DAY_COUNT) {
             throw new AssertionError("group position out of range");
         }
@@ -241,7 +241,9 @@
      */
     /* package */ boolean moveCursorToChildPosition(int groupPosition,
             int childPosition) {
-        if (mCursor.isClosed()) return false;
+        if (!mDataValid || mCursor.isClosed()) {
+            return false;
+        }
         groupPosition = groupPositionToBin(groupPosition);
         int index = childPosition;
         for (int i = 0; i < groupPosition; i++) {
@@ -250,19 +252,34 @@
         return mCursor.moveToPosition(index);
     }
 
-    /* package */ void refreshData() {
-        if (mCursor.isClosed()) {
+    public void changeCursor(Cursor cursor) {
+        if (cursor == mCursor) {
             return;
         }
-        mCursor.requery();
-        buildMap();
-        for (DataSetObserver o : mObservers) {
-            o.onChanged();
+        if (mCursor != null) {
+            mCursor.unregisterDataSetObserver(mDataSetObserver);
+            mCursor.close();
+        }
+        mCursor = cursor;
+        if (cursor != null) {
+            cursor.registerDataSetObserver(mDataSetObserver);
+            mIdIndex = cursor.getColumnIndexOrThrow("_id");
+            mDataValid = true;
+            buildMap();
+            // notify the observers about the new cursor
+            notifyDataSetChanged();
+        } else {
+            mIdIndex = -1;
+            mDataValid = false;
+            // notify the observers about the lack of a data set
+            notifyDataSetInvalidated();
         }
     }
 
+    @Override
     public View getGroupView(int groupPosition, boolean isExpanded,
             View convertView, ViewGroup parent) {
+        if (!mDataValid) throw new IllegalStateException("Data is not valid"); 
         TextView item;
         if (null == convertView || !(convertView instanceof TextView)) {
             LayoutInflater factory = LayoutInflater.from(mContext);
@@ -275,73 +292,87 @@
         return item;
     }
 
+    @Override
     public View getChildView(int groupPosition, int childPosition,
             boolean isLastChild, View convertView, ViewGroup parent) {
+        if (!mDataValid) throw new IllegalStateException("Data is not valid"); 
         return null;
     }
 
+    @Override
     public boolean areAllItemsEnabled() {
         return true;
     }
 
+    @Override
     public boolean isChildSelectable(int groupPosition, int childPosition) {
         return true;
     }
 
+    @Override
     public int getGroupCount() {
+        if (!mDataValid) return 0;
         return mNumberOfBins;
     }
 
+    @Override
     public int getChildrenCount(int groupPosition) {
+        if (!mDataValid) return 0;
         return mItemMap[groupPositionToBin(groupPosition)];
     }
 
+    @Override
     public Object getGroup(int groupPosition) {
         return null;
     }
 
+    @Override
     public Object getChild(int groupPosition, int childPosition) {
         return null;
     }
 
+    @Override
     public long getGroupId(int groupPosition) {
+        if (!mDataValid) return 0; 
         return groupPosition;
     }
 
+    @Override
     public long getChildId(int groupPosition, int childPosition) {
+        if (!mDataValid) return 0; 
         if (moveCursorToChildPosition(groupPosition, childPosition)) {
             return getLong(mIdIndex);
         }
         return 0;
     }
 
+    @Override
     public boolean hasStableIds() {
         return true;
     }
 
-    public void registerDataSetObserver(DataSetObserver observer) {
-        mObservers.add(observer);
-    }
-
-    public void unregisterDataSetObserver(DataSetObserver observer) {
-        mObservers.remove(observer);
-    }
-
+    @Override
     public void onGroupExpanded(int groupPosition) {
     }
 
+    @Override
     public void onGroupCollapsed(int groupPosition) {
     }
 
+    @Override
     public long getCombinedChildId(long groupId, long childId) {
+        if (!mDataValid) return 0; 
         return childId;
     }
 
+    @Override
     public long getCombinedGroupId(long groupId) {
+        if (!mDataValid) return 0; 
         return groupId;
     }
 
+    @Override
     public boolean isEmpty() {
-        return mCursor.isClosed() || mCursor.getCount() == 0;
+        return !mDataValid || mCursor == null || mCursor.isClosed() || mCursor.getCount() == 0;
     }
 }
diff --git a/src/com/android/browser/Dots.java b/src/com/android/browser/Dots.java
index eb8d493..e28d868 100644
--- a/src/com/android/browser/Dots.java
+++ b/src/com/android/browser/Dots.java
@@ -48,7 +48,7 @@
                                  LayoutParams.WRAP_CONTENT);
 
         for (int i = 0; i < MAX_DOTS; i++) {
-            ImageView dotView = new ImageView(mContext);
+            ImageView dotView = new ImageView(getContext());
             dotView.setImageResource(R.drawable.page_indicator_unselected2);
             addView(dotView, lp);
         }
diff --git a/src/com/android/browser/DownloadTouchIcon.java b/src/com/android/browser/DownloadTouchIcon.java
index e8a912c..768eab5 100644
--- a/src/com/android/browser/DownloadTouchIcon.java
+++ b/src/com/android/browser/DownloadTouchIcon.java
@@ -16,20 +16,6 @@
 
 package com.android.browser;
 
-import android.content.ContentResolver;
-import android.content.ContentUris;
-import android.content.ContentValues;
-import android.content.Context;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.net.http.AndroidHttpClient;
-import android.net.Proxy;
-import android.os.AsyncTask;
-import android.provider.Browser;
-import android.webkit.WebView;
-
-
 import org.apache.http.HttpEntity;
 import org.apache.http.HttpHost;
 import org.apache.http.HttpResponse;
@@ -37,6 +23,21 @@
 import org.apache.http.client.params.HttpClientParams;
 import org.apache.http.conn.params.ConnRouteParams;
 
+import android.content.ContentResolver;
+import android.content.ContentValues;
+import android.content.Context;
+import android.database.Cursor;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.net.Proxy;
+import android.net.http.AndroidHttpClient;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.os.Message;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Images;
+import android.webkit.WebView;
+
 import java.io.ByteArrayOutputStream;
 import java.io.IOException;
 import java.io.InputStream;
@@ -46,10 +47,17 @@
     private Cursor mCursor;
     private final String mOriginalUrl;
     private final String mUrl;
-    private final String mUserAgent;
+    private final String mUserAgent; // Sites may serve a different icon to different UAs
+    private Message mMessage;
+
     private final Context mContext;
     /* package */ Tab mTab;
 
+    /**
+     * Use this ctor to store the touch icon in the bookmarks database for
+     * the originalUrl so we take account of redirects. Used when the user
+     * bookmarks a page from outside the bookmarks activity.
+     */
     public DownloadTouchIcon(Tab tab, Context ctx, ContentResolver cr, WebView view) {
         mTab = tab;
         mContext = ctx;
@@ -60,6 +68,13 @@
         mUserAgent = view.getSettings().getUserAgentString();
     }
 
+    /**
+     * Use this ctor to download the touch icon and update the bookmarks database
+     * entry for the given url. Used when the user creates a bookmark from
+     * within the bookmarks activity and there haven't been any redirects.
+     * TODO: Would be nice to set the user agent here so that there is no
+     * potential for the three different ctors here to return different icons.
+     */
     public DownloadTouchIcon(Context ctx, ContentResolver cr, String url) {
         mTab = null;
         mContext = ctx;
@@ -69,15 +84,33 @@
         mUserAgent = null;
     }
 
+    /**
+     * Use this ctor to not store the touch icon in a database, rather add it to
+     * the passed Message's data bundle with the key
+     * {@link BrowserContract.Bookmarks#TOUCH_ICON} and then send the message.
+     */
+    public DownloadTouchIcon(Context context, Message msg, String userAgent) {
+        mMessage = msg;
+        mContext = context;
+        mContentResolver = null;
+        mOriginalUrl = null;
+        mUrl = null;
+        mUserAgent = userAgent;
+    }
+
     @Override
     public Void doInBackground(String... values) {
-        mCursor = BrowserBookmarksAdapter.queryBookmarksForUrl(mContentResolver,
-                mOriginalUrl, mUrl, true);
-        if (mCursor != null && mCursor.getCount() > 0) {
-            String url = values[0];
+        if (mContentResolver != null) {
+            mCursor = Bookmarks.queryCombinedForUrl(mContentResolver,
+                    mOriginalUrl, mUrl);
+        }
 
-            AndroidHttpClient client = AndroidHttpClient.newInstance(
-                    mUserAgent);
+        boolean inDatabase = mCursor != null && mCursor.getCount() > 0;
+
+        String url = values[0];
+
+        if (inDatabase || mMessage != null) {
+            AndroidHttpClient client = AndroidHttpClient.newInstance(mUserAgent);
             HttpHost httpHost = Proxy.getPreferredHttpHost(mContext, url);
             if (httpHost != null) {
                 ConnRouteParams.setDefaultProxy(client.getParams(), httpHost);
@@ -90,7 +123,6 @@
 
             try {
                 HttpResponse response = client.execute(request);
-
                 if (response.getStatusLine().getStatusCode() == 200) {
                     HttpEntity entity = response.getEntity();
                     if (entity != null) {
@@ -98,7 +130,12 @@
                         if (content != null) {
                             Bitmap icon = BitmapFactory.decodeStream(
                                     content, null, null);
-                            storeIcon(icon);
+                            if (inDatabase) {
+                                storeIcon(icon);
+                            } else if (mMessage != null) {
+                                Bundle b = mMessage.getData();
+                                b.putParcelable(BrowserContract.Bookmarks.TOUCH_ICON, icon);
+                            }
                         }
                     }
                 }
@@ -110,9 +147,15 @@
                 client.close();
             }
         }
+
         if (mCursor != null) {
             mCursor.close();
         }
+
+        if (mMessage != null) {
+            mMessage.sendToTarget();
+        }
+
         return null;
     }
 
@@ -134,17 +177,16 @@
             return;
         }
 
-        final ByteArrayOutputStream os = new ByteArrayOutputStream();
-        icon.compress(Bitmap.CompressFormat.PNG, 100, os);
-        ContentValues values = new ContentValues();
-        values.put(Browser.BookmarkColumns.TOUCH_ICON,
-                os.toByteArray());
-
         if (mCursor.moveToFirst()) {
+            final ByteArrayOutputStream os = new ByteArrayOutputStream();
+            icon.compress(Bitmap.CompressFormat.PNG, 100, os);
+
+            ContentValues values = new ContentValues();
+            values.put(Images.TOUCH_ICON, os.toByteArray());
+            values.put(Images.URL, mCursor.getString(0));
+
             do {
-                mContentResolver.update(ContentUris.withAppendedId(
-                        Browser.BOOKMARKS_URI, mCursor.getInt(0)),
-                        values, null, null);
+                mContentResolver.update(Images.CONTENT_URI, values, null, null);
             } while (mCursor.moveToNext());
         }
     }
diff --git a/src/com/android/browser/FetchUrlMimeType.java b/src/com/android/browser/FetchUrlMimeType.java
index 62d877e..89ac13d 100644
--- a/src/com/android/browser/FetchUrlMimeType.java
+++ b/src/com/android/browser/FetchUrlMimeType.java
@@ -16,7 +16,9 @@
 
 package com.android.browser;
 
+import android.app.DownloadManager;
 import android.content.ContentValues;
+import android.content.Context;
 import android.net.Proxy;
 import android.net.Uri;
 import android.net.http.AndroidHttpClient;
@@ -30,7 +32,6 @@
 import java.io.IOException;
 
 import android.os.AsyncTask;
-import android.provider.Downloads;
 import android.webkit.MimeTypeMap;
 import android.webkit.URLUtil;
 
@@ -49,11 +50,17 @@
  */
 class FetchUrlMimeType extends AsyncTask<ContentValues, String, ContentValues> {
 
+    public static final String URI = "uri";
+    public static final String USER_AGENT = "user_agent";
+    public static final String COOKIE_DATA = "cookie_data";
     BrowserActivity mActivity;
     ContentValues mValues;
+    DownloadManager.Request mRequest;
 
-    public FetchUrlMimeType(BrowserActivity activity) {
+    public FetchUrlMimeType(BrowserActivity activity,
+            DownloadManager.Request request) {
         mActivity = activity;
+        mRequest = request;
     }
 
     @Override
@@ -61,7 +68,7 @@
         mValues = values[0];
 
         // Check to make sure we have a URI to download
-        String uri = mValues.getAsString(Downloads.Impl.COLUMN_URI);
+        String uri = mValues.getAsString(URI);
         if (uri == null || uri.length() == 0) {
             return null;
         }
@@ -69,23 +76,18 @@
         // User agent is likely to be null, though the AndroidHttpClient
         // seems ok with that.
         AndroidHttpClient client = AndroidHttpClient.newInstance(
-                mValues.getAsString(Downloads.Impl.COLUMN_USER_AGENT));
+                mValues.getAsString(USER_AGENT));
         HttpHost httpHost = Proxy.getPreferredHttpHost(mActivity, uri);
         if (httpHost != null) {
             ConnRouteParams.setDefaultProxy(client.getParams(), httpHost);
         }
         HttpHead request = new HttpHead(uri);
 
-        String cookie = mValues.getAsString(Downloads.Impl.COLUMN_COOKIE_DATA);
+        String cookie = mValues.getAsString(COOKIE_DATA);
         if (cookie != null && cookie.length() > 0) {
             request.addHeader("Cookie", cookie);
         }
 
-        String referer = mValues.getAsString(Downloads.Impl.COLUMN_REFERER);
-        if (referer != null && referer.length() > 0) {
-            request.addHeader("Referer", referer);
-        }
-
         HttpResponse response;
         ContentValues result = new ContentValues();
         try {
@@ -124,24 +126,25 @@
        final String mimeType = values.getAsString("Content-Type");
        final String contentDisposition = values.getAsString("Content-Disposition");
        if (mimeType != null) {
-           String url = mValues.getAsString(Downloads.Impl.COLUMN_URI);
+           String url = mValues.getAsString(URI);
            if (mimeType.equalsIgnoreCase("text/plain") ||
                    mimeType.equalsIgnoreCase("application/octet-stream")) {
                String newMimeType =
                        MimeTypeMap.getSingleton().getMimeTypeFromExtension(
                            MimeTypeMap.getFileExtensionFromUrl(url));
                if (newMimeType != null) {
-                   mValues.put(Downloads.Impl.COLUMN_MIME_TYPE, newMimeType);
+                   mRequest.setMimeType(newMimeType);
                }
            }
            String filename = URLUtil.guessFileName(url,
                    contentDisposition, mimeType);
-           mValues.put(Downloads.Impl.COLUMN_FILE_NAME_HINT, filename);
+           mRequest.setDestinationInExternalFilesDir(mActivity, null, filename);
        }
 
        // Start the download
-       final Uri contentUri =
-           mActivity.getContentResolver().insert(Downloads.Impl.CONTENT_URI, mValues);
+       DownloadManager manager = (DownloadManager) mActivity.getSystemService(
+               Context.DOWNLOAD_SERVICE);
+       manager.enqueue(mRequest);
     }
 
 }
diff --git a/src/com/android/browser/FindDialog.java b/src/com/android/browser/FindDialog.java
deleted file mode 100644
index 726138e..0000000
--- a/src/com/android/browser/FindDialog.java
+++ /dev/null
@@ -1,247 +0,0 @@
-/*
- * Copyright (C) 2007 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser;
-
-import android.content.Context;
-import android.text.Editable;
-import android.text.Selection;
-import android.text.Spannable;
-import android.text.TextWatcher;
-import android.view.Gravity;
-import android.view.KeyEvent;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.animation.AnimationUtils;
-import android.view.inputmethod.InputMethodManager;
-import android.webkit.WebView;
-import android.widget.EditText;
-import android.widget.LinearLayout;
-import android.widget.TextView;
-
-/* package */ class FindDialog extends WebDialog implements TextWatcher {
-    private TextView        mMatches;
-    
-    // Views with which the user can interact.
-    private EditText        mEditText;
-    private View            mNextButton;
-    private View            mPrevButton;
-    private View            mMatchesView;
-
-    // When the dialog is opened up with old text, enter needs to be pressed
-    // (or the text needs to be changed) before WebView.findAll can be called.
-    // Once it has been called, enter should move to the next match.
-    private boolean         mMatchesFound;
-    private int             mNumberOfMatches;
-
-    private View.OnClickListener mFindListener = new View.OnClickListener() {
-        public void onClick(View v) {
-            findNext();
-        }
-    };
-
-    private View.OnClickListener mFindPreviousListener  =
-            new View.OnClickListener() {
-        public void onClick(View v) {
-            if (mWebView == null) {
-                throw new AssertionError("No WebView for FindDialog::onClick");
-            }
-            mWebView.findNext(false);
-            updateMatchesString();
-            hideSoftInput();
-        }
-    };
-
-    private void disableButtons() {
-        mPrevButton.setEnabled(false);
-        mNextButton.setEnabled(false);
-        mPrevButton.setFocusable(false);
-        mNextButton.setFocusable(false);
-    }
-
-    /* package */ FindDialog(BrowserActivity context) {
-        super(context);
-
-        LayoutInflater factory = LayoutInflater.from(context);
-        factory.inflate(R.layout.browser_find, this);
-
-        addCancel();
-        mEditText = (EditText) findViewById(R.id.edit);
-        
-        View button = findViewById(R.id.next);
-        button.setOnClickListener(mFindListener);
-        mNextButton = button;
-        
-        button = findViewById(R.id.previous);
-        button.setOnClickListener(mFindPreviousListener);
-        mPrevButton = button;
-        
-        mMatches = (TextView) findViewById(R.id.matches);
-        mMatchesView = findViewById(R.id.matches_view);
-        disableButtons();
-
-    }
-
-    /**
-     * Called by BrowserActivity.closeDialog.  Start the animation to hide
-     * the dialog, inform the WebView that the dialog is being dismissed,
-     * and hide the soft keyboard.
-     */
-    public void dismiss() {
-        super.dismiss();
-        mWebView.notifyFindDialogDismissed();
-        hideSoftInput();
-    }
-
-    @Override
-    public boolean dispatchKeyEventPreIme(KeyEvent event) {
-        if (event.getKeyCode() == KeyEvent.KEYCODE_BACK) {
-            KeyEvent.DispatcherState state = getKeyDispatcherState();
-            if (state != null) {
-                int action = event.getAction();
-                if (KeyEvent.ACTION_DOWN == action
-                        && event.getRepeatCount() == 0) {
-                    state.startTracking(event, this);
-                    return true;
-                } else if (KeyEvent.ACTION_UP == action
-                        && !event.isCanceled() && state.isTracking(event)) {
-                    mBrowserActivity.closeDialogs();
-                    return true;
-                }
-            }
-        }
-        return super.dispatchKeyEventPreIme(event);
-    }
-
-    @Override
-    public boolean dispatchKeyEvent(KeyEvent event) {
-        int keyCode = event.getKeyCode();
-        if (event.getAction() == KeyEvent.ACTION_UP) {
-            if (keyCode == KeyEvent.KEYCODE_ENTER
-                    && mEditText.hasFocus()) {
-                if (mMatchesFound) {
-                    findNext();
-                } else {
-                    findAll();
-                    // Set the selection to the end.
-                    Spannable span = (Spannable) mEditText.getText();
-                    Selection.setSelection(span, span.length());
-                }
-                return true;
-            }
-        }
-        return super.dispatchKeyEvent(event);
-    }
-
-    private void findNext() {
-        if (mWebView == null) {
-            throw new AssertionError("No WebView for FindDialog::findNext");
-        }
-        mWebView.findNext(true);
-        updateMatchesString();
-        hideSoftInput();
-    }
-
-    public void show() {
-        super.show();
-        // In case the matches view is showing from a previous search
-        mMatchesView.setVisibility(View.INVISIBLE);
-        mMatchesFound = false;
-        // This text is only here to ensure that mMatches has a height.
-        mMatches.setText("0");
-        mEditText.requestFocus();
-        Spannable span = (Spannable) mEditText.getText();
-        int length = span.length();
-        Selection.setSelection(span, 0, length);
-        span.setSpan(this, 0, length, Spannable.SPAN_INCLUSIVE_INCLUSIVE);
-        disableButtons();
-        InputMethodManager imm = (InputMethodManager)
-                mBrowserActivity.getSystemService(Context.INPUT_METHOD_SERVICE);
-        imm.showSoftInput(mEditText, 0);
-    }
-    
-    // TextWatcher methods
-    public void beforeTextChanged(CharSequence s, 
-                                  int start, 
-                                  int count, 
-                                  int after) {
-    }
-    
-    public void onTextChanged(CharSequence s,  
-                              int start, 
-                              int before, 
-                              int count) {
-        findAll();
-    }
-
-    private void findAll() {
-        if (mWebView == null) {
-            throw new AssertionError(
-                    "No WebView for FindDialog::findAll");
-        }
-        CharSequence find = mEditText.getText();
-        if (0 == find.length()) {
-            disableButtons();
-            mWebView.clearMatches();
-            mMatchesView.setVisibility(View.INVISIBLE);
-        } else {
-            mMatchesView.setVisibility(View.VISIBLE);
-            int found = mWebView.findAll(find.toString());
-            mMatchesFound = true;
-            setMatchesFound(found);
-            if (found < 2) {
-                disableButtons();
-                if (found == 0) {
-                    // Cannot use getQuantityString, which ignores the "zero"
-                    // quantity.
-                    // FIXME: is this fix is beyond the scope
-                    // of adding touch selection to gingerbread?
-                    // mMatches.setText(mBrowserActivity.getResources().getString(
-                    //        R.string.no_matches));
-                }
-            } else {
-                mPrevButton.setFocusable(true);
-                mNextButton.setFocusable(true);
-                mPrevButton.setEnabled(true);
-                mNextButton.setEnabled(true);
-            }
-        }
-    }
-
-    private void setMatchesFound(int found) {
-        mNumberOfMatches = found;
-        updateMatchesString();
-    }
-
-    public void setText(String text) {
-        mEditText.setText(text);
-        findAll();
-    }
-
-    private void updateMatchesString() {
-        // Note: updateMatchesString is only called by methods that have already
-        // checked mWebView for null.
-        String template = mBrowserActivity.getResources().
-                getQuantityString(R.plurals.matches_found, mNumberOfMatches,
-                mWebView.findIndex() + 1, mNumberOfMatches);
-
-        mMatches.setText(template);
-    }
-
-    public void afterTextChanged(Editable s) {
-    }
-}
diff --git a/src/com/android/browser/HistoryItem.java b/src/com/android/browser/HistoryItem.java
index 72e1b19..11198f0 100644
--- a/src/com/android/browser/HistoryItem.java
+++ b/src/com/android/browser/HistoryItem.java
@@ -18,12 +18,8 @@
 package com.android.browser;
 
 import android.content.Context;
-import android.graphics.Bitmap;
-import android.provider.Browser;
 import android.view.View;
 import android.widget.CompoundButton;
-import android.widget.ImageView;
-import android.widget.TextView;
 
 /**
  *  Layout representing a history item in the classic history viewer.
@@ -45,12 +41,13 @@
             public void onCheckedChanged(CompoundButton buttonView,
                     boolean isChecked) {
                 if (isChecked) {
-                    Bookmarks.addBookmark(mContext,
-                            mContext.getContentResolver(), mUrl, getName(), null, true);
+                    // FIXME: For now, add at the root level.  Should we
+                    // open AddBookmark from here?
+                    Bookmarks.addBookmark(getContext(), true, mUrl, getName(), null, true, 0);
                     LogTag.logBookmarkAdded(mUrl, "history");
                 } else {
-                    Bookmarks.removeFromBookmarks(mContext,
-                            mContext.getContentResolver(), mUrl, getName());
+                    Bookmarks.removeFromBookmarks(getContext(),
+                            getContext().getContentResolver(), mUrl, getName());
                 }
             }
         };
diff --git a/src/com/android/browser/HttpAuthenticationDialog.java b/src/com/android/browser/HttpAuthenticationDialog.java
new file mode 100644
index 0000000..a9ba332
--- /dev/null
+++ b/src/com/android/browser/HttpAuthenticationDialog.java
@@ -0,0 +1,153 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser;
+
+import android.app.AlertDialog;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.WindowManager;
+import android.widget.TextView;
+
+/**
+ * HTTP authentication dialog.
+ */
+public class HttpAuthenticationDialog {
+
+    private final Context mContext;
+
+    private final String mHost;
+    private final String mRealm;
+
+    private AlertDialog mDialog;
+    private TextView mUsernameView;
+    private TextView mPasswordView;
+
+    private OkListener mOkListener;
+    private CancelListener mCancelListener;
+
+    /**
+     * Creates an HTTP authentication dialog.
+     */
+    public HttpAuthenticationDialog(Context context, String host, String realm) {
+        mContext = context;
+        mHost = host;
+        mRealm = realm;
+        createDialog();
+    }
+
+    private String getUsername() {
+        return mUsernameView.getText().toString();
+    }
+
+    private String getPassword() {
+        return mPasswordView.getText().toString();
+    }
+
+    /**
+     * Sets the listener that will be notified when the user submits the credentials.
+     */
+    public void setOkListener(OkListener okListener) {
+        mOkListener = okListener;
+    }
+
+    /**
+     * Sets the listener that will be notified when the user cancels the authentication
+     * dialog.
+     */
+    public void setCancelListener(CancelListener cancelListener) {
+        mCancelListener = cancelListener;
+    }
+
+    /**
+     * Shows the dialog.
+     */
+    public void show() {
+        mDialog.show();
+        mUsernameView.requestFocus();
+    }
+
+    /**
+     * Hides, recreates, and shows the dialog. This can be used to handle configuration changes.
+     */
+    public void reshow() {
+        String username = getUsername();
+        String password = getPassword();
+        int focusId = mDialog.getCurrentFocus().getId();
+        mDialog.dismiss();
+        createDialog();
+        mDialog.show();
+        if (username != null) {
+            mUsernameView.setText(username);
+        }
+        if (password != null) {
+            mPasswordView.setText(password);
+        }
+        if (focusId != 0) {
+            mDialog.findViewById(focusId).requestFocus();
+        } else {
+            mUsernameView.requestFocus();
+        }
+    }
+
+    private void createDialog() {
+        LayoutInflater factory = LayoutInflater.from(mContext);
+        View v = factory.inflate(R.layout.http_authentication, null);
+        mUsernameView = (TextView) v.findViewById(R.id.username_edit);
+        mPasswordView = (TextView) v.findViewById(R.id.password_edit);
+
+        String title = mContext.getText(R.string.sign_in_to).toString().replace(
+                "%s1", mHost).replace("%s2", mRealm);
+
+        mDialog = new AlertDialog.Builder(mContext)
+                .setTitle(title)
+                .setIcon(android.R.drawable.ic_dialog_alert)
+                .setView(v)
+                .setPositiveButton(R.string.action, new DialogInterface.OnClickListener() {
+                    public void onClick(DialogInterface dialog, int whichButton) {
+                        if (mOkListener != null) {
+                            mOkListener.onOk(mHost, mRealm, getUsername(), getPassword());
+                        }
+                    }})
+                .setNegativeButton(R.string.cancel,new DialogInterface.OnClickListener() {
+                    public void onClick(DialogInterface dialog, int whichButton) {
+                        if (mCancelListener != null) mCancelListener.onCancel();
+                    }})
+                .setOnCancelListener(new DialogInterface.OnCancelListener() {
+                    public void onCancel(DialogInterface dialog) {
+                        if (mCancelListener != null) mCancelListener.onCancel();
+                    }})
+                .create();
+
+        // Make the IME appear when the dialog is displayed if applicable.
+        mDialog.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE);
+    }
+
+    /**
+     * Interface for listeners that are notified when the user submits the credentials.
+     */
+    public interface OkListener {
+        void onOk(String host, String realm, String username, String password);
+    }
+
+    /**
+     * Interface for listeners that are notified when the user cancels the dialog.
+     */
+    public interface CancelListener {
+        void onCancel();
+    }
+}
diff --git a/src/com/android/browser/MeshTracker.java b/src/com/android/browser/MeshTracker.java
deleted file mode 100644
index c4b6332..0000000
--- a/src/com/android/browser/MeshTracker.java
+++ /dev/null
@@ -1,198 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser;
-
-import android.graphics.Bitmap;
-import android.graphics.utils.BoundaryPatch;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.webkit.WebView;
-
-/*package*/ class MeshTracker extends WebView.DragTracker {
-
-    private static class Mesh {
-        private int mWhich;
-        private int mRows;
-        private int mCols;
-        private BoundaryPatch mPatch = new BoundaryPatch();
-        private float[] mCubics = new float[24];
-        private float[] mOrig = new float[24];
-        private float mStretchX, mStretchY;
-
-        Mesh(int which, int rows, int cols) {
-            mWhich = which;
-            mRows = rows;
-            mCols = cols;
-        }
-
-        private void rebuildPatch() {
-            mPatch.setCubicBoundary(mCubics, 0, mRows, mCols);
-        }
-
-        private void setSize(float w, float h) {
-            float[] pts = mCubics;
-            float x1 = w*0.3333f;
-            float y1 = h*0.3333f;
-            float x2 = w*0.6667f;
-            float y2 = h*0.6667f;
-            pts[0*2+0] = 0;  pts[0*2+1] = 0;
-            pts[1*2+0] = x1; pts[1*2+1] = 0;
-            pts[2*2+0] = x2; pts[2*2+1] = 0;
-
-            pts[3*2+0] = w; pts[3*2+1] = 0;
-            pts[4*2+0] = w; pts[4*2+1] = y1;
-            pts[5*2+0] = w; pts[5*2+1] = y2;
-
-            pts[6*2+0] = w; pts[6*2+1] = h;
-            pts[7*2+0] = x2; pts[7*2+1] = h;
-            pts[8*2+0] = x1; pts[8*2+1] = h;
-
-            pts[9*2+0] = 0;  pts[9*2+1] = h;
-            pts[10*2+0] = 0; pts[10*2+1] = y2;
-            pts[11*2+0] = 0; pts[11*2+1] = y1;
-
-            System.arraycopy(pts, 0, mOrig, 0, 24);
-
-            // recall our stretcher
-            setStretch(mStretchX, mStretchY);
-        }
-
-        public void setBitmap(Bitmap bm) {
-            mPatch.setTexture(bm);
-            setSize(bm.getWidth(), bm.getHeight());
-        }
-
-        // first experimental behavior
-        private void doit1(float dx, float dy) {
-            final float scale = 0.75f;  // temper how far we actually move
-            dx *= scale;
-            dy *= scale;
-
-            int index;
-            if (dx < 0) {
-                index = 10;
-            } else {
-                index = 4;
-            }
-            mCubics[index*2 + 0] = mOrig[index*2 + 0] + dx;
-            mCubics[index*2 + 2] = mOrig[index*2 + 2] + dx;
-
-            if (dy < 0) {
-                index = 1;
-            } else {
-                index = 7;
-            }
-            mCubics[index*2 + 1] = mOrig[index*2 + 1] + dy;
-            mCubics[index*2 + 3] = mOrig[index*2 + 3] + dy;
-        }
-
-        private void doit2(float dx, float dy) {
-            final float scale = 0.35f;  // temper how far we actually move
-            dx *= scale;
-            dy *= scale;
-            final float cornerScale = 0.25f;
-
-            int index;
-            if (dx < 0) {
-                index = 4;
-            } else {
-                index = 10;
-            }
-            mCubics[index*2 + 0] = mOrig[index*2 + 0] + dx;
-            mCubics[index*2 + 2] = mOrig[index*2 + 2] + dx;
-            // corners
-            index -= 1;
-            mCubics[index*2 + 0] = mOrig[index*2 + 0] + dx * cornerScale;
-            index = (index + 3) % 12; // next corner
-            mCubics[index*2 + 0] = mOrig[index*2 + 0] + dx * cornerScale;
-
-            if (dy < 0) {
-                index = 7;
-            } else {
-                index = 1;
-            }
-            mCubics[index*2 + 1] = mOrig[index*2 + 1] + dy;
-            mCubics[index*2 + 3] = mOrig[index*2 + 3] + dy;
-            // corners
-            index -= 1;
-            mCubics[index*2 + 1] = mOrig[index*2 + 1] + dy * cornerScale;
-            index = (index + 3) % 12; // next corner
-            mCubics[index*2 + 1] = mOrig[index*2 + 1] + dy * cornerScale;
-        }
-
-        public void setStretch(float dx, float dy) {
-            mStretchX = dx;
-            mStretchY = dy;
-            switch (mWhich) {
-                case 1:
-                    doit1(dx, dy);
-                    break;
-                case 2:
-                    doit2(dx, dy);
-                    break;
-            }
-            rebuildPatch();
-        }
-
-        public void draw(Canvas canvas) {
-            mPatch.draw(canvas);
-        }
-    }
-
-    private Mesh mMesh;
-    private Bitmap mBitmap;
-    private int mWhich;
-    private Paint mBGPaint;
-
-    public MeshTracker(int which) {
-        mWhich = which;
-    }
-
-    public void setBGPaint(Paint paint) {
-        mBGPaint = paint;
-    }
-
-    @Override public void onStartDrag(float x, float y) {
-        mMesh = new Mesh(mWhich, 16, 16);
-    }
-
-    @Override public void onBitmapChange(Bitmap bm) {
-        mBitmap = bm;
-        mMesh.setBitmap(bm);
-    }
-
-    @Override public boolean onStretchChange(float sx, float sy) {
-        mMesh.setStretch(-sx, -sy);
-        return true;
-    }
-
-    @Override public void onStopDrag() {
-        mMesh = null;
-    }
-
-    @Override public void onDraw(Canvas canvas) {
-        if (mWhich == 2) {
-            if (mBGPaint != null) {
-                canvas.drawPaint(mBGPaint);
-            } else {
-                canvas.drawColor(0xFF000000);
-            }
-        }
-        mMesh.draw(canvas);
-    }
-}
-
diff --git a/src/com/android/browser/OpenDownloadReceiver.java b/src/com/android/browser/OpenDownloadReceiver.java
index 99e5f41..f66c332 100644
--- a/src/com/android/browser/OpenDownloadReceiver.java
+++ b/src/com/android/browser/OpenDownloadReceiver.java
@@ -43,16 +43,16 @@
         try {
             cursor = cr.query(data,
                     new String[] { Downloads.Impl._ID, Downloads.Impl._DATA,
-                    Downloads.Impl.COLUMN_MIME_TYPE, Downloads.COLUMN_STATUS },
+                    Downloads.Impl.COLUMN_MIME_TYPE, Downloads.Impl.COLUMN_STATUS },
                     null, null, null);
             if (cursor.moveToFirst()) {
                 String filename = cursor.getString(1);
                 String mimetype = cursor.getString(2);
                 String action = intent.getAction();
-                if (Downloads.ACTION_NOTIFICATION_CLICKED.equals(action)) {
+                if (Downloads.Impl.ACTION_NOTIFICATION_CLICKED.equals(action)) {
                     int status = cursor.getInt(3);
-                    if (Downloads.isStatusCompleted(status)
-                            && Downloads.isStatusSuccess(status)) {
+                    if (Downloads.Impl.isStatusCompleted(status)
+                            && Downloads.Impl.isStatusSuccess(status)) {
                         Intent launchIntent = new Intent(Intent.ACTION_VIEW);
                         Uri path = Uri.parse(filename);
                         // If there is no scheme, then it must be a file
diff --git a/src/com/android/browser/PageProgressView.java b/src/com/android/browser/PageProgressView.java
new file mode 100644
index 0000000..f512cef
--- /dev/null
+++ b/src/com/android/browser/PageProgressView.java
@@ -0,0 +1,117 @@
+
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser;
+
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.Rect;
+import android.graphics.drawable.Drawable;
+import android.os.Handler;
+import android.os.Message;
+import android.util.AttributeSet;
+import android.widget.ImageView;
+
+/**
+ *
+ */
+public class PageProgressView extends ImageView {
+
+    public static final int MAX_PROGRESS = 10000;
+    private static final int MSG_UPDATE = 42;
+    private static final int STEPS = 10;
+    private static final int DELAY = 40;
+
+    private int mCurrentProgress;
+    private int mTargetProgress;
+    private int mIncrement;
+    private Rect mBounds;
+    private Handler mHandler;
+
+    /**
+     * @param context
+     * @param attrs
+     * @param defStyle
+     */
+    public PageProgressView(Context context, AttributeSet attrs, int defStyle) {
+        super(context, attrs, defStyle);
+        init(context);
+    }
+
+    /**
+     * @param context
+     * @param attrs
+     */
+    public PageProgressView(Context context, AttributeSet attrs) {
+        super(context, attrs);
+        init(context);
+    }
+
+    /**
+     * @param context
+     */
+    public PageProgressView(Context context) {
+        super(context);
+        init(context);
+    }
+
+    private void init(Context ctx) {
+        mBounds = new Rect(0,0,0,0);
+        mCurrentProgress = 0;
+        mTargetProgress = 0;
+        mHandler = new Handler() {
+
+            @Override
+            public void handleMessage(Message msg) {
+                if (msg.what == MSG_UPDATE) {
+                    mCurrentProgress = Math.min(mTargetProgress,
+                            mCurrentProgress + mIncrement);
+                    mBounds.right = getWidth() * mCurrentProgress / MAX_PROGRESS;
+                    invalidate();
+                    if (mCurrentProgress < mTargetProgress) {
+                        sendMessageDelayed(mHandler.obtainMessage(MSG_UPDATE), DELAY);
+                    }
+                }
+            }
+
+        };
+    }
+
+    @Override
+    public void onLayout(boolean f, int l, int t, int r, int b) {
+        mBounds.left = 0;
+        mBounds.right = (r - l) * mCurrentProgress / MAX_PROGRESS;
+        mBounds.top = 0;
+        mBounds.bottom = b-t;
+    }
+
+    void setProgress(int progress) {
+        mCurrentProgress = mTargetProgress;
+        mTargetProgress = progress;
+        mIncrement = (mTargetProgress - mCurrentProgress) / STEPS;
+        mHandler.removeMessages(MSG_UPDATE);
+        mHandler.sendEmptyMessage(MSG_UPDATE);
+    }
+
+    @Override
+    public void onDraw(Canvas canvas) {
+//        super.onDraw(canvas);
+        Drawable d = getDrawable();
+        d.setBounds(mBounds);
+        d.draw(canvas);
+    }
+
+}
diff --git a/src/com/android/browser/ScrollWebView.java b/src/com/android/browser/ScrollWebView.java
new file mode 100644
index 0000000..97bd2c7
--- /dev/null
+++ b/src/com/android/browser/ScrollWebView.java
@@ -0,0 +1,125 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.util.AttributeSet;
+import android.view.View;
+import android.webkit.WebView;
+
+import java.util.Map;
+
+/**
+ *  Manage WebView scroll events
+ */
+public class ScrollWebView extends WebView {
+
+    private ScrollListener mScrollListener;
+    private boolean mIsCancelled;
+    private Runnable mScrollRunnable;
+
+    /**
+     * @param context
+     * @param attrs
+     * @param defStyle
+     * @param javascriptInterfaces
+     */
+    public ScrollWebView(Context context, AttributeSet attrs, int defStyle,
+            Map<String, Object> javascriptInterfaces, boolean privateBrowsing) {
+        super(context, attrs, defStyle, javascriptInterfaces, privateBrowsing);
+    }
+
+    /**
+     * @param context
+     * @param attrs
+     * @param defStyle
+     */
+    public ScrollWebView(Context context, AttributeSet attrs, int defStyle,
+            boolean privateBrowsing) {
+        super(context, attrs, defStyle, privateBrowsing);
+    }
+
+    /**
+     * @param context
+     * @param attrs
+     */
+    public ScrollWebView(Context context, AttributeSet attrs) {
+        super(context, attrs);
+    }
+
+    /**
+     * @param context
+     */
+    public ScrollWebView(Context context) {
+        super(context);
+    }
+
+    void hideEmbeddedTitleBar() {
+        scrollBy(0, getVisibleTitleHeight());
+    }
+
+    @Override
+    public void setEmbeddedTitleBar(final View title) {
+        super.setEmbeddedTitleBar(title);
+        if (title != null && mScrollListener != null) {
+            // allow the scroll listener to initialize its state
+            post(new Runnable() {
+                @Override
+                public void run() {
+                    mScrollListener.onScroll((title.getHeight() == 0 ||
+                            getVisibleTitleHeight() > 0));
+                }
+            });
+        }
+    }
+
+    @Override
+    public void stopScroll() {
+        mIsCancelled = true;
+        super.stopScroll();
+    }
+
+    @Override
+    protected void onScrollChanged(int l, final int t, int ol, int ot) {
+        super.onScrollChanged(l, t, ol, ot);
+        if (!mIsCancelled) {
+            post(mScrollRunnable);
+        } else {
+            mIsCancelled = false;
+        }
+    }
+
+    void setScrollListener(ScrollListener l) {
+        mScrollListener = l;
+        if (mScrollListener != null) {
+            mScrollRunnable = new Runnable() {
+                public void run() {
+                    if (!mIsCancelled) {
+                        mScrollListener.onScroll(getVisibleTitleHeight() > 0);
+                    }
+                }
+            };
+        }
+    }
+
+    // callback for scroll events
+
+    interface ScrollListener {
+        public void onScroll(boolean titleVisible);
+    }
+
+}
diff --git a/src/com/android/browser/SelectDialog.java b/src/com/android/browser/SelectDialog.java
deleted file mode 100644
index 461127a..0000000
--- a/src/com/android/browser/SelectDialog.java
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser;
-
-import android.provider.Browser;
-import android.view.LayoutInflater;
-import android.view.View;
-
-/* package */ class SelectDialog extends WebDialog {
-    private View mCopyButton;
-    private View mSelectAllButton;
-    private View mShareButton;
-    private View mFindButton;
-
-    SelectDialog(BrowserActivity context) {
-        super(context);
-        LayoutInflater factory = LayoutInflater.from(context);
-        factory.inflate(R.layout.browser_select, this);
-        addCancel();
-
-        mCopyButton = findViewById(R.id.copy);
-        mCopyButton.setOnClickListener(mCopyListener);
-        mSelectAllButton = findViewById(R.id.select_all);
-        mSelectAllButton.setOnClickListener(mSelectAllListener);
-        mShareButton = findViewById(R.id.share);
-        mShareButton.setOnClickListener(mShareListener);
-        mFindButton = findViewById(R.id.find);
-        mFindButton.setOnClickListener(mFindListener);
-    }
-
-    private View.OnClickListener mCopyListener = new View.OnClickListener() {
-        public void onClick(View v) {
-            mWebView.copySelection();
-            mBrowserActivity.closeDialogs();
-        }
-    };
-
-    private View.OnClickListener mSelectAllListener = new View.OnClickListener() {
-        public void onClick(View v) {
-            mWebView.selectAll();
-        }
-    };
-
-    private View.OnClickListener mShareListener = new View.OnClickListener() {
-        public void onClick(View v) {
-            String selection = mWebView.getSelection();
-            Browser.sendString(mBrowserActivity, selection);
-            mBrowserActivity.closeDialogs();
-        }
-    };
-
-    private View.OnClickListener mFindListener = new View.OnClickListener() {
-        public void onClick(View v) {
-            String selection = mWebView.getSelection();
-            mBrowserActivity.closeDialogs();
-            mBrowserActivity.showFindDialog();
-            mBrowserActivity.setFindDialogText(selection);
-        }
-    };
-
-    /**
-     * Called by BrowserActivity.closeDialog.  Start the animation to hide
-     * the dialog, and inform the WebView that the dialog is being dismissed.
-     */
-    @Override
-    public void dismiss() {
-        super.dismiss();
-        mWebView.notifySelectDialogDismissed();
-    }
-
-}
diff --git a/src/com/android/browser/ShortcutActivity.java b/src/com/android/browser/ShortcutActivity.java
new file mode 100644
index 0000000..354d694
--- /dev/null
+++ b/src/com/android/browser/ShortcutActivity.java
@@ -0,0 +1,78 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Activity;
+import android.app.Fragment;
+import android.app.FragmentManager;
+import android.app.FragmentTransaction;
+import android.content.Intent;
+import android.os.Bundle;
+
+public class ShortcutActivity extends Activity
+    implements BookmarksHistoryCallbacks {
+
+    @Override
+    protected void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
+        FragmentManager fm = getFragmentManager();
+        FragmentTransaction transaction = fm.openTransaction();
+        Bundle extras = new Bundle();
+        extras.putBoolean(BrowserBookmarksPage.EXTRA_SHORTCUT, true);
+        extras.putBoolean(BrowserBookmarksPage.EXTRA_DISABLE_WINDOW, true);
+        Fragment frag = BrowserBookmarksPage.newInstance(this, null, extras);
+        transaction.add(android.R.id.content, frag);
+        transaction.commit();
+    }
+
+
+    /**
+     * handle fragment startActivity
+     */
+    @Override
+    public void startActivityFromFragment(Fragment f, Intent intent, int requestCode) {
+        setResult(RESULT_OK, intent);
+        finish();
+    }
+
+    @Override
+    public void finish() {
+        super.finish();
+    }
+
+    // BookmarksHistoryCallbacks
+
+    /**
+     * not used for shortcuts
+     */
+    @Override
+    public void onRemoveParentChildRelationships() {}
+
+    @Override
+    public void onComboCanceled() {
+        setResult(RESULT_CANCELED);
+        finish();
+    }
+
+    /**
+     * not used for shortcuts
+     */
+    @Override
+    public void onUrlSelected(String url, boolean newWindow) {}
+
+}
diff --git a/src/com/android/browser/SuggestionsAdapter.java b/src/com/android/browser/SuggestionsAdapter.java
new file mode 100644
index 0000000..626283a
--- /dev/null
+++ b/src/com/android/browser/SuggestionsAdapter.java
@@ -0,0 +1,569 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.search.SearchEngine;
+
+import android.app.SearchManager;
+import android.content.Context;
+import android.database.Cursor;
+import android.net.Uri;
+import android.provider.BrowserContract;
+import android.text.TextUtils;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.view.ViewGroup;
+import android.widget.BaseAdapter;
+import android.widget.Filter;
+import android.widget.Filterable;
+import android.widget.ImageView;
+import android.widget.LinearLayout.LayoutParams;
+import android.widget.TextView;
+
+import java.util.ArrayList;
+import java.util.List;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * adapter to wrap multiple cursors for url/search completions
+ */
+public class SuggestionsAdapter extends BaseAdapter implements Filterable, OnClickListener {
+
+    static final int TYPE_SEARCH = 0;
+    static final int TYPE_SUGGEST = 1;
+    static final int TYPE_BOOKMARK = 2;
+    static final int TYPE_SUGGEST_URL = 3;
+    static final int TYPE_HISTORY = 4;
+
+    private static final String[] COMBINED_PROJECTION =
+            {BrowserContract.Combined._ID, BrowserContract.Combined.TITLE,
+                    BrowserContract.Combined.URL, BrowserContract.Combined.IS_BOOKMARK};
+
+    private static final String[] SEARCHES_PROJECTION = {BrowserContract.Searches.SEARCH};
+
+    private static final String COMBINED_SELECTION =
+            "(url LIKE ? OR url LIKE ? OR url LIKE ? OR url LIKE ? OR title LIKE ?)";
+
+    Context mContext;
+    Filter mFilter;
+    SuggestionResults mResults;
+    List<CursorSource> mSources;
+    boolean mLandscapeMode;
+    CompletionListener mListener;
+    int mLinesPortrait;
+    int mLinesLandscape;
+
+    interface CompletionListener {
+
+        public void onSearch(String txt);
+
+        public void onSelect(String txt);
+
+        public void onFilterComplete(int count);
+
+    }
+
+    public SuggestionsAdapter(Context ctx, CompletionListener listener) {
+        mContext = ctx;
+        mListener = listener;
+        mLinesPortrait = mContext.getResources().
+                getInteger(R.integer.max_suggest_lines_portrait);
+        mLinesLandscape = mContext.getResources().
+                getInteger(R.integer.max_suggest_lines_landscape);
+        mFilter = new SuggestFilter();
+        addSource(new SuggestCursor());
+        addSource(new SearchesCursor());
+        addSource(new CombinedCursor());
+    }
+
+    public void setLandscapeMode(boolean mode) {
+        mLandscapeMode = mode;
+    }
+
+    public int getLeftCount() {
+        return mResults.getLeftCount();
+    }
+
+    public int getRightCount() {
+        return mResults.getRightCount();
+    }
+
+    public void addSource(CursorSource c) {
+        if (mSources == null) {
+            mSources = new ArrayList<CursorSource>(5);
+        }
+        mSources.add(c);
+    }
+
+    @Override
+    public void onClick(View v) {
+        if (R.id.icon2 == v.getId()) {
+            // replace input field text with suggestion text
+            SuggestItem item = (SuggestItem) ((View) v.getParent()).getTag();
+            mListener.onSearch(item.title);
+        } else {
+            SuggestItem item = (SuggestItem) v.getTag();
+            mListener.onSelect((TextUtils.isEmpty(item.url)? item.title : item.url));
+        }
+    }
+
+    @Override
+    public Filter getFilter() {
+        return mFilter;
+    }
+
+    @Override
+    public int getCount() {
+        return (mResults == null) ? 0 : mResults.getLineCount();
+    }
+
+    @Override
+    public SuggestItem getItem(int position) {
+        if (mResults == null) {
+            return null;
+        }
+        if (mLandscapeMode) {
+            if (position >= mResults.getLineCount()) {
+                // right column
+                position = position - mResults.getLineCount();
+                // index in column
+                if (position >= mResults.getRightCount()) {
+                    return null;
+                }
+                return mResults.items.get(position + mResults.getLeftCount());
+            } else {
+                // left column
+                if (position >= mResults.getLeftCount()) {
+                    return null;
+                }
+                return mResults.items.get(position);
+            }
+        } else {
+            return mResults.items.get(position);
+        }
+    }
+
+    @Override
+    public long getItemId(int position) {
+        return 0;
+    }
+
+    @Override
+    public View getView(int position, View convertView, ViewGroup parent) {
+        final LayoutInflater inflater = LayoutInflater.from(mContext);
+        if (mLandscapeMode) {
+            View view = inflater.inflate(R.layout.suggestion_two_column, parent, false);
+            SuggestItem item = getItem(position);
+            View iv = view.findViewById(R.id.suggest1);
+            LayoutParams lp = new LayoutParams(iv.getLayoutParams());
+            lp.weight = 0.5f;
+            iv.setLayoutParams(lp);
+            if (item != null) {
+                bindView(iv, item);
+            } else {
+                iv.setVisibility((mResults.getLeftCount() == 0) ? View.GONE :
+                        View.INVISIBLE);
+            }
+            item = getItem(position + mResults.getLineCount());
+            iv = view.findViewById(R.id.suggest2);
+            lp = new LayoutParams(iv.getLayoutParams());
+            lp.weight = 0.5f;
+            iv.setLayoutParams(lp);
+            if (item != null) {
+                bindView(iv, item);
+            } else {
+                iv.setVisibility((mResults.getRightCount() == 0) ? View.GONE :
+                        View.INVISIBLE);
+            }
+            return view;
+        } else {
+            View view = inflater.inflate(R.layout.suggestion_item, parent, false);
+            bindView(view, getItem(position));
+            return view;
+        }
+    }
+
+    private void bindView(View view, SuggestItem item) {
+        // store item for click handling
+        view.setTag(item);
+        TextView tv1 = (TextView) view.findViewById(android.R.id.text1);
+        TextView tv2 = (TextView) view.findViewById(android.R.id.text2);
+        ImageView ic1 = (ImageView) view.findViewById(R.id.icon1);
+        View spacer = view.findViewById(R.id.spacer);
+        View ic2 = view.findViewById(R.id.icon2);
+        View div = view.findViewById(R.id.divider);
+        tv1.setText(item.title);
+        tv2.setText(item.url);
+        int id = -1;
+        switch (item.type) {
+            case TYPE_SUGGEST:
+            case TYPE_SEARCH:
+                id = R.drawable.ic_search_category_suggest;
+                break;
+            case TYPE_BOOKMARK:
+                id = R.drawable.ic_search_category_bookmark;
+                break;
+            case TYPE_HISTORY:
+                id = R.drawable.ic_search_category_history;
+                break;
+            case TYPE_SUGGEST_URL:
+                id = R.drawable.ic_search_category_browser;
+                break;
+            default:
+                id = -1;
+        }
+        if (id != -1) {
+            ic1.setImageDrawable(mContext.getResources().getDrawable(id));
+        }
+        ic2.setVisibility(((TYPE_SUGGEST == item.type) || (TYPE_SEARCH == item.type))
+                ? View.VISIBLE : View.GONE);
+        div.setVisibility(ic2.getVisibility());
+        spacer.setVisibility(((TYPE_SUGGEST == item.type) || (TYPE_SEARCH == item.type))
+                ? View.GONE : View.INVISIBLE);
+        view.setOnClickListener(this);
+        ic2.setOnClickListener(this);
+    }
+
+    class SuggestFilter extends Filter {
+
+        SuggestionResults results;
+
+        @Override
+        public CharSequence convertResultToString(Object item) {
+            if (item == null) {
+                return "";
+            }
+            SuggestItem sitem = (SuggestItem) item;
+            if (sitem.title != null) {
+                return sitem.title;
+            } else {
+                return sitem.url;
+            }
+        }
+
+        @Override
+        protected FilterResults performFiltering(CharSequence constraint) {
+            FilterResults res = new FilterResults();
+            if (TextUtils.isEmpty(constraint)) {
+                res.count = 0;
+                res.values = null;
+                return res;
+            }
+            results = new SuggestionResults();
+            if (constraint != null) {
+                for (CursorSource sc : mSources) {
+                    sc.runQuery(constraint);
+                }
+                mixResults();
+            }
+            res.count = results.getLineCount();
+            res.values = results;
+            return res;
+        }
+
+        void mixResults() {
+            for (int i = 0; i < mSources.size(); i++) {
+                CursorSource s = mSources.get(i);
+                int n = Math.min(s.getCount(), (mLandscapeMode ? mLinesLandscape
+                        : mLinesPortrait));
+                boolean more = false;
+                for (int j = 0; j < n; j++) {
+                    results.addResult(s.getItem());
+                    more = s.moveToNext();
+                }
+                if (s instanceof SuggestCursor) {
+                    int k = n;
+                    while (more && (k < mLinesPortrait)) {
+                        SuggestItem item  = s.getItem();
+                        if (item.type == TYPE_SUGGEST_URL) {
+                            results.addResult(item);
+                            break;
+                        }
+                        more = s.moveToNext();
+                        k++;
+
+                    }
+                }
+            }
+        }
+
+        @Override
+        protected void publishResults(CharSequence constraint, FilterResults fresults) {
+            mResults = (SuggestionResults) fresults.values;
+            mListener.onFilterComplete(fresults.count);
+            notifyDataSetChanged();
+        }
+
+    }
+
+    /**
+     * sorted list of results of a suggestion query
+     *
+     */
+    class SuggestionResults {
+
+        ArrayList<SuggestItem> items;
+        // count per type
+        int[] counts;
+
+        SuggestionResults() {
+            items = new ArrayList<SuggestItem>(24);
+            // n of types:
+            counts = new int[5];
+        }
+
+        int getTypeCount(int type) {
+            return counts[type];
+        }
+
+        void addResult(SuggestItem item) {
+            int ix = 0;
+            while ((ix < items.size()) && (item.type >= items.get(ix).type))
+                ix++;
+            items.add(ix, item);
+            counts[item.type]++;
+        }
+
+        int getLineCount() {
+            if (mLandscapeMode) {
+                return Math.max(getLeftCount(), getRightCount());
+            } else {
+                return getLeftCount() + getRightCount();
+            }
+        }
+
+        int getLeftCount() {
+            return counts[TYPE_SEARCH] + counts[TYPE_SUGGEST];
+        }
+
+        int getRightCount() {
+            return counts[TYPE_BOOKMARK] + counts[TYPE_HISTORY] + counts[TYPE_SUGGEST_URL];
+        }
+
+        public String toString() {
+            if (items == null) return null;
+            if (items.size() == 0) return "[]";
+            StringBuilder sb = new StringBuilder();
+            for (int i = 0; i < items.size(); i++) {
+                SuggestItem item = items.get(i);
+                sb.append(item.type + ": " + item.title);
+                if (i < items.size() - 1) {
+                    sb.append(", ");
+                }
+            }
+            return sb.toString();
+        }
+    }
+
+    /**
+     * data object to hold suggestion values
+     */
+    class SuggestItem {
+        String title;
+        String url;
+        int type;
+
+        public SuggestItem(String text, String u, int t) {
+            title = text;
+            url = u;
+            type = t;
+        }
+    }
+
+    abstract class CursorSource {
+
+        Cursor mCursor;
+
+        boolean moveToNext() {
+            return mCursor.moveToNext();
+        }
+
+        public abstract void runQuery(CharSequence constraint);
+
+        public abstract SuggestItem getItem();
+
+        public int getCount() {
+            return (mCursor != null) ? mCursor.getCount() : 0;
+        }
+
+        public void close() {
+            if (mCursor != null) {
+                mCursor.close();
+            }
+        }
+    }
+
+    /**
+     * combined bookmark & history source
+     */
+    class CombinedCursor extends CursorSource {
+
+        @Override
+        public SuggestItem getItem() {
+            if ((mCursor != null) && (!mCursor.isAfterLast())) {
+                String title = mCursor.getString(1);
+                String url = mCursor.getString(2);
+                boolean isBookmark = (mCursor.getInt(3) == 1);
+                return new SuggestItem(getTitle(title, url), getUrl(title, url),
+                        isBookmark ? TYPE_BOOKMARK : TYPE_HISTORY);
+            }
+            return null;
+        }
+
+        @Override
+        public void runQuery(CharSequence constraint) {
+            // constraint != null
+            if (mCursor != null) {
+                mCursor.close();
+            }
+            String like = constraint + "%";
+            String[] args = null;
+            String selection = null;
+            if (like.startsWith("http") || like.startsWith("file")) {
+                args = new String[1];
+                args[0] = like;
+                selection = "url LIKE ?";
+            } else {
+                args = new String[5];
+                args[0] = "http://" + like;
+                args[1] = "http://www." + like;
+                args[2] = "https://" + like;
+                args[3] = "https://www." + like;
+                // To match against titles.
+                args[4] = like;
+                selection = COMBINED_SELECTION;
+            }
+            Uri.Builder ub = BrowserContract.Combined.CONTENT_URI.buildUpon();
+            ub.appendQueryParameter(BrowserContract.PARAM_LIMIT,
+                    Integer.toString(mLinesPortrait));
+            mCursor =
+                    mContext.getContentResolver().query(ub.build(), COMBINED_PROJECTION,
+                            selection,
+                            (constraint != null) ? args : null,
+                            BrowserContract.Combined.VISITS + " DESC, " +
+                            BrowserContract.Combined.DATE_LAST_VISITED + " DESC");
+            if (mCursor != null) {
+                mCursor.moveToFirst();
+            }
+        }
+
+        /**
+         * Provides the title (text line 1) for a browser suggestion, which should be the
+         * webpage title. If the webpage title is empty, returns the stripped url instead.
+         *
+         * @return the title string to use
+         */
+        private String getTitle(String title, String url) {
+            if (TextUtils.isEmpty(title) || TextUtils.getTrimmedLength(title) == 0) {
+                title = UrlUtils.stripUrl(url);
+            }
+            return title;
+        }
+
+        /**
+         * Provides the subtitle (text line 2) for a browser suggestion, which should be the
+         * webpage url. If the webpage title is empty, then the url should go in the title
+         * instead, and the subtitle should be empty, so this would return null.
+         *
+         * @return the subtitle string to use, or null if none
+         */
+        private String getUrl(String title, String url) {
+            if (TextUtils.isEmpty(title)
+                    || TextUtils.getTrimmedLength(title) == 0
+                    || title.equals(url)) {
+                return null;
+            } else {
+                return UrlUtils.stripUrl(url);
+            }
+        }
+    }
+
+    class SearchesCursor extends CursorSource {
+
+        @Override
+        public SuggestItem getItem() {
+            if ((mCursor != null) && (!mCursor.isAfterLast())) {
+                return new SuggestItem(mCursor.getString(0), null, TYPE_SEARCH);
+            }
+            return null;
+        }
+
+        @Override
+        public void runQuery(CharSequence constraint) {
+            // constraint != null
+            if (mCursor != null) {
+                mCursor.close();
+            }
+            String like = constraint + "%";
+            String[] args = new String[] {constraint.toString()};
+            String selection = BrowserContract.Searches.SEARCH + " LIKE ?";
+            Uri.Builder ub = BrowserContract.Searches.CONTENT_URI.buildUpon();
+            ub.appendQueryParameter(BrowserContract.PARAM_LIMIT,
+                    Integer.toString(mLinesPortrait));
+            mCursor =
+                    mContext.getContentResolver().query(ub.build(), SEARCHES_PROJECTION,
+                            selection,
+                            args, BrowserContract.Searches.DATE + " DESC");
+            if (mCursor != null) {
+                mCursor.moveToFirst();
+            }
+        }
+
+    }
+
+    class SuggestCursor extends CursorSource {
+
+        @Override
+        public SuggestItem getItem() {
+            if (mCursor != null) {
+                String title = mCursor.getString(
+                        mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_TEXT_1));
+                String text2 = mCursor.getString(
+                        mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_TEXT_2));
+                String url = mCursor.getString(
+                        mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_TEXT_2_URL));
+                String uri = mCursor.getString(
+                        mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_INTENT_DATA));
+                int type = (TextUtils.isEmpty(url)) ? TYPE_SUGGEST : TYPE_SUGGEST_URL;
+                return new SuggestItem(title, url, type);
+            }
+            return null;
+        }
+
+        @Override
+        public void runQuery(CharSequence constraint) {
+            if (mCursor != null) {
+                mCursor.close();
+            }
+            if (!TextUtils.isEmpty(constraint)) {
+                SearchEngine searchEngine = BrowserSettings.getInstance().getSearchEngine();
+                if (searchEngine != null && searchEngine.supportsSuggestions()) {
+                    mCursor = searchEngine.getSuggestions(mContext, constraint.toString());
+                    if (mCursor != null) {
+                        mCursor.moveToFirst();
+                    }
+                }
+            } else {
+                mCursor = null;
+            }
+        }
+
+    }
+
+}
diff --git a/src/com/android/browser/Tab.java b/src/com/android/browser/Tab.java
index 7019c8a..2436e84 100644
--- a/src/com/android/browser/Tab.java
+++ b/src/com/android/browser/Tab.java
@@ -16,13 +16,8 @@
 
 package com.android.browser;
 
-import java.io.File;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.LinkedList;
-import java.util.Map;
-import java.util.Vector;
+import com.android.browser.TabControl.TabChangeListener;
+import com.android.common.speech.LoggingEvents;
 
 import android.app.AlertDialog;
 import android.app.SearchManager;
@@ -42,14 +37,15 @@
 import android.os.Message;
 import android.os.SystemClock;
 import android.provider.Browser;
+import android.provider.BrowserContract.History;
 import android.speech.RecognizerResultsIntent;
 import android.util.Log;
 import android.view.KeyEvent;
 import android.view.LayoutInflater;
 import android.view.View;
+import android.view.View.OnClickListener;
 import android.view.ViewGroup;
 import android.view.ViewStub;
-import android.view.View.OnClickListener;
 import android.webkit.ConsoleMessage;
 import android.webkit.CookieSyncManager;
 import android.webkit.DownloadListener;
@@ -71,7 +67,12 @@
 import android.widget.LinearLayout;
 import android.widget.TextView;
 
-import com.android.common.speech.LoggingEvents;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.Map;
+import java.util.Vector;
 
 /**
  * Class for maintaining Tabs with a main WebView and a subwindow.
@@ -155,6 +156,7 @@
     static final String PARENTTAB = "parentTab";
     static final String APPID = "appid";
     static final String ORIGINALURL = "originalUrl";
+    static final String INCOGNITO = "privateBrowsingEnabled";
 
     // -------------------------------------------------------------------------
 
@@ -494,10 +496,7 @@
             }
 
             // update the bookmark database for favicon
-            if (favicon != null) {
-                BrowserBookmarksAdapter.updateBookmarkFavicon(mActivity
-                        .getContentResolver(), null, url, favicon);
-            }
+            maybeUpdateFavicon(null, url, favicon);
 
             // reset sync timer to avoid sync starts during loading a page
             CookieSyncManager.getInstance().resetSync();
@@ -510,6 +509,9 @@
             if (mInForeground) {
                 mActivity.onPageStarted(view, url, favicon);
             }
+            if (getTabChangeListener() != null) {
+                getTabChangeListener().onPageStarted(Tab.this, url, favicon);
+            }
         }
 
         @Override
@@ -518,19 +520,24 @@
                     url, SystemClock.uptimeMillis() - mLoadStartTime);
             mInLoad = false;
 
-            if (mInForeground && !mActivity.didUserStopLoading()
-                    || !mInForeground) {
-                // Only update the bookmark screenshot if the user did not
-                // cancel the load early.
-                mActivity.postMessage(
-                        BrowserActivity.UPDATE_BOOKMARK_THUMBNAIL, 0, 0, view,
-                        500);
+            if (!isPrivateBrowsingEnabled()) {
+                if (mInForeground && !mActivity.didUserStopLoading()
+                        || !mInForeground) {
+                    // Only update the bookmark screenshot if the user did not
+                    // cancel the load early.
+                    mActivity.postMessage(
+                            BrowserActivity.UPDATE_BOOKMARK_THUMBNAIL, 0, 0, view,
+                            500);
+                }
             }
 
             // finally update the UI in the activity if it is in the foreground
             if (mInForeground) {
                 mActivity.onPageFinished(view, url);
             }
+            if (getTabChangeListener() != null) {
+                getTabChangeListener().onPageFinished(Tab.this);
+            }
         }
 
         // return true if want to hijack the url to let another app to handle it
@@ -590,8 +597,12 @@
                     errorCode != WebViewClient.ERROR_FILE) {
                 queueError(errorCode, description);
             }
-            Log.e(LOGTAG, "onReceivedError " + errorCode + " " + failingUrl
-                    + " " + description);
+
+            // Don't log URLs when in private browsing mode
+            if (!isPrivateBrowsingEnabled()) {
+                Log.e(LOGTAG, "onReceivedError " + errorCode + " " + failingUrl
+                        + " " + description);
+            }
 
             // We need to reset the title after an error if it is in foreground.
             if (mInForeground) {
@@ -661,6 +672,9 @@
         @Override
         public void doUpdateVisitedHistory(WebView view, String url,
                 boolean isReload) {
+            // Don't save anything in private browsing mode
+            if (isPrivateBrowsingEnabled()) return;
+
             if (url.regionMatches(true, 0, "about:", 0, 6)) {
                 return;
             }
@@ -680,6 +694,7 @@
             final ContentResolver cr = mActivity.getContentResolver();
             final String newUrl = url;
             new AsyncTask<Void, Void, Void>() {
+                @Override
                 protected Void doInBackground(Void... unused) {
                     Browser.updateVisitedHistory(cr, newUrl, true);
                     return null;
@@ -803,8 +818,7 @@
                 handler.proceed(username, password);
             } else {
                 if (mInForeground) {
-                    mActivity.showHttpAuthentication(handler, host, realm,
-                            null, null, null, 0);
+                    mActivity.showHttpAuthentication(handler, host, realm);
                 } else {
                     handler.cancel();
                 }
@@ -830,7 +844,7 @@
             if (!mInForeground || mActivity.mActivityInPause) {
                 return;
             }
-            if (event.isDown()) {
+            if (event.getAction() == KeyEvent.ACTION_DOWN) {
                 mActivity.onKeyDown(event.getKeyCode(), event);
             } else {
                 mActivity.onKeyUp(event.getKeyCode(), event);
@@ -956,6 +970,9 @@
             if (mInForeground) {
                 mActivity.onProgressChanged(view, newProgress);
             }
+            if (getTabChangeListener() != null) {
+                getTabChangeListener().onProgress(Tab.this, newProgress);
+            }
         }
 
         @Override
@@ -965,69 +982,64 @@
                 // here, if url is null, we want to reset the title
                 mActivity.setUrlTitle(pageUrl, title);
             }
+            TabChangeListener tcl = getTabChangeListener();
+            if (tcl != null) {
+                tcl.onUrlAndTitle(Tab.this, pageUrl,title);
+            }
             if (pageUrl == null || pageUrl.length()
                     >= SQLiteDatabase.SQLITE_MAX_LIKE_PATTERN_LENGTH) {
                 return;
             }
-            new AsyncTask<Void, Void, Void>() {
-                protected Void doInBackground(Void... unused) {
-                    // See if we can find the current url in our history
-                    // database and add the new title to it.
-                    String url = pageUrl;
-                    if (url.startsWith("http://www.")) {
-                        url = url.substring(11);
-                    } else if (url.startsWith("http://")) {
-                        url = url.substring(4);
-                    }
-                    // Escape wildcards for LIKE operator.
-                    url = url.replace("\\", "\\\\").replace("%", "\\%")
-                            .replace("_", "\\_");
-                    Cursor c = null;
-                    try {
-                        final ContentResolver cr
-                                = mActivity.getContentResolver();
-                        url = "%" + url;
-                        String [] selArgs = new String[] { url };
-                        String where = Browser.BookmarkColumns.URL
-                                + " LIKE ? ESCAPE '\\' AND "
-                                + Browser.BookmarkColumns.BOOKMARK + " = 0";
-                        c = cr.query(Browser.BOOKMARKS_URI, new String[]
-                                { Browser.BookmarkColumns._ID }, where, selArgs,
-                                null);
-                        if (c.moveToFirst()) {
-                            // Current implementation of database only has one
-                            // entry per url.
-                            ContentValues map = new ContentValues();
-                            map.put(Browser.BookmarkColumns.TITLE, title);
-                            String[] projection = new String[]
-                                    { Integer.valueOf(c.getInt(0)).toString() };
-                            cr.update(Browser.BOOKMARKS_URI, map, "_id = ?",
-                                    projection);
+
+            // Update the title in the history database if not in private browsing mode
+            if (!isPrivateBrowsingEnabled()) {
+                new AsyncTask<Void, Void, Void>() {
+                    @Override
+                    protected Void doInBackground(Void... unused) {
+                        // See if we can find the current url in our history
+                        // database and add the new title to it.
+                        String url = pageUrl;
+                        if (url.startsWith("http://www.")) {
+                            url = url.substring(11);
+                        } else if (url.startsWith("http://")) {
+                            url = url.substring(4);
                         }
-                    } catch (IllegalStateException e) {
-                        Log.e(LOGTAG, "Tab onReceived title", e);
-                    } catch (SQLiteException ex) {
-                        Log.e(LOGTAG,
-                                "onReceivedTitle() caught SQLiteException: ",
-                                ex);
-                    } finally {
-                        if (c != null) c.close();
+                        // Escape wildcards for LIKE operator.
+                        url = url.replace("\\", "\\\\").replace("%", "\\%")
+                                .replace("_", "\\_");
+                        Cursor c = null;
+                        try {
+                            final ContentResolver cr = mActivity.getContentResolver();
+                            String selection = History.URL + " LIKE ? ESCAPE '\\'";
+                            String [] selectionArgs = new String[] { "%" + url };
+                            ContentValues values = new ContentValues();
+                            values.put(History.TITLE, title);
+                            cr.update(History.CONTENT_URI, values, selection, selectionArgs);
+                        } catch (IllegalStateException e) {
+                            Log.e(LOGTAG, "Tab onReceived title", e);
+                        } catch (SQLiteException ex) {
+                            Log.e(LOGTAG,
+                                    "onReceivedTitle() caught SQLiteException: ",
+                                    ex);
+                        } finally {
+                            if (c != null) c.close();
+                        }
+                        return null;
                     }
-                    return null;
-                }
-            }.execute();
+                }.execute();
+            }
         }
 
         @Override
         public void onReceivedIcon(WebView view, Bitmap icon) {
-            if (icon != null) {
-                BrowserBookmarksAdapter.updateBookmarkFavicon(mActivity
-                        .getContentResolver(), view.getOriginalUrl(), view
-                        .getUrl(), icon);
-            }
+            maybeUpdateFavicon(view.getOriginalUrl(), view.getUrl(), icon);
+
             if (mInForeground) {
                 mActivity.setFavicon(icon);
             }
+            if (getTabChangeListener() != null) {
+                getTabChangeListener().onFavicon(Tab.this, icon);
+            }
         }
 
         @Override
@@ -1048,16 +1060,6 @@
         }
 
         @Override
-        public void onSelectionDone(WebView view) {
-            if (mInForeground) mActivity.closeDialogs();
-        }
-
-        @Override
-        public void onSelectionStart(WebView view) {
-            if (false && mInForeground) mActivity.showSelectDialog();
-        }
-
-        @Override
         public void onShowCustomView(View view,
                 WebChromeClient.CustomViewCallback callback) {
             if (mInForeground) mActivity.onShowCustomView(view, callback);
@@ -1150,6 +1152,9 @@
                 }
             }
 
+            // Don't log console messages in private browsing mode
+            if (isPrivateBrowsingEnabled()) return true;
+
             String message = "Console: " + consoleMessage.message() + " "
                     + consoleMessage.sourceId() +  ":"
                     + consoleMessage.lineNumber();
@@ -1202,9 +1207,9 @@
         }
 
         @Override
-        public void openFileChooser(ValueCallback<Uri> uploadMsg) {
+        public void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType) {
             if (mInForeground) {
-                mActivity.openFileChooser(uploadMsg);
+                mActivity.openFileChooser(uploadMsg, acceptType);
             } else {
                 uploadMsg.onReceiveValue(null);
             }
@@ -1216,10 +1221,12 @@
         @Override
         public void getVisitedHistory(final ValueCallback<String[]> callback) {
             AsyncTask<Void, Void, String[]> task = new AsyncTask<Void, Void, String[]>() {
+                @Override
                 public String[] doInBackground(Void... unused) {
                     return Browser.getVisitedHistory(mActivity
                             .getContentResolver());
                 }
+                @Override
                 public void onPostExecute(String[] result) {
                     callback.onReceiveValue(result);
                 };
@@ -1248,7 +1255,7 @@
             // Unlike the others, do not call mClient's version, which would
             // change the progress bar.  However, we do want to remove the
             // find or select dialog.
-            mBrowserActivity.closeDialogs();
+            mBrowserActivity.endActionMode();
         }
         @Override
         public void doUpdateVisitedHistory(WebView view, String url,
@@ -1449,7 +1456,7 @@
      */
     boolean createSubWindow() {
         if (mSubView == null) {
-            mActivity.closeDialogs();
+            mActivity.endActionMode();
             mSubViewContainer = mInflateService.inflate(
                     R.layout.browser_subwindow, null);
             mSubView = (WebView) mSubViewContainer.findViewById(R.id.webview);
@@ -1497,7 +1504,7 @@
      */
     void dismissSubWindow() {
         if (mSubView != null) {
-            mActivity.closeDialogs();
+            mActivity.endActionMode();
             BrowserSettings.getInstance().deleteObserver(
                     mSubView.getSettings());
             mSubView.destroy();
@@ -1522,7 +1529,7 @@
     void removeSubWindow(ViewGroup content) {
         if (mSubView != null) {
             content.removeView(mSubViewContainer);
-            mActivity.closeDialogs();
+            mActivity.endActionMode();
         }
     }
 
@@ -1581,7 +1588,7 @@
                 (FrameLayout) mContainer.findViewById(R.id.webview_wrapper);
         wrapper.removeView(mMainView);
         content.removeView(mContainer);
-        mActivity.closeDialogs();
+        mActivity.endActionMode();
         removeSubWindow(content);
     }
 
@@ -1684,6 +1691,19 @@
     }
 
     /**
+     * Return whether private browsing is enabled for the main window of
+     * this tab.
+     * @return True if private browsing is enabled.
+     */
+    private boolean isPrivateBrowsingEnabled() {
+        WebView webView = getWebView();
+        if (webView == null) {
+            return false;
+        }
+        return webView.isPrivateBrowsingEnabled();
+    }
+
+    /**
      * Return the subwindow of this tab or null if there is no subwindow.
      * @return The subwindow of this tab or null.
      */
@@ -1771,6 +1791,20 @@
         return null;
     }
 
+    /*
+     * Update the favorites icon if the private browsing isn't enabled and the
+     * icon is valid.
+     */
+    void maybeUpdateFavicon(final String originalUrl, final String url, Bitmap favicon) {
+        if (favicon == null) {
+            return;
+        }
+        if (!isPrivateBrowsingEnabled()) {
+            Bookmarks.updateFavicon(mActivity
+                    .getContentResolver(), originalUrl, url, favicon);
+        }
+    }
+
     /**
      * Return the tab's error console. Creates the console if createIfNEcessary
      * is true and we haven't already created the console.
@@ -1855,6 +1889,9 @@
         // FIXME: The only place we cared about subwindow was for
         // bookmarking (i.e. not when saving state). Was this deliberate?
         final WebBackForwardList list = mMainView.copyBackForwardList();
+        if (list == null) {
+            Log.w(LOGTAG, "populatePickerData called and WebBackForwardList is null");
+        }
         final WebHistoryItem item = list != null ? list.getCurrentItem() : null;
         populatePickerData(item);
     }
@@ -1863,7 +1900,9 @@
     // WebView.
     private void populatePickerData(WebHistoryItem item) {
         mPickerData = new PickerData();
-        if (item != null) {
+        if (item == null) {
+            Log.w(LOGTAG, "populatePickerData called with a null WebHistoryItem");
+        } else {
             mPickerData.mUrl = item.getUrl();
             mPickerData.mTitle = item.getTitle();
             mPickerData.mFavicon = item.getFavicon();
@@ -1962,35 +2001,12 @@
         return true;
     }
 
-    /*
-     * Opens the find and select text dialogs.  Called by BrowserActivity.
+    /**
+     * always get the TabChangeListener form the tab control
+     * @return the TabControl change listener
      */
-    WebView showDialog(WebDialog dialog) {
-        LinearLayout container;
-        WebView view;
-        if (mSubView != null) {
-            view = mSubView;
-            container = (LinearLayout) mSubViewContainer.findViewById(
-                    R.id.inner_container);
-        } else {
-            view = mMainView;
-            container = mContainer;
-        }
-        dialog.show();
-        container.addView(dialog, 0, new LinearLayout.LayoutParams(
-                ViewGroup.LayoutParams.MATCH_PARENT,
-                ViewGroup.LayoutParams.WRAP_CONTENT));
-        dialog.setWebView(view);
-        return view;
+    private TabChangeListener getTabChangeListener() {
+        return mActivity.getTabControl().getTabChangeListener();
     }
 
-    /*
-     * Close the find or select dialog. Called by BrowserActivity.closeDialog.
-     */
-    void closeDialog(WebDialog dialog) {
-        // The dialog may be attached to the subwindow.  Ensure that the
-        // correct parent has it removed.
-        LinearLayout parent = (LinearLayout) dialog.getParent();
-        if (parent != null) parent.removeView(dialog);
-    }
 }
diff --git a/src/com/android/browser/TabBar.java b/src/com/android/browser/TabBar.java
new file mode 100644
index 0000000..a939639
--- /dev/null
+++ b/src/com/android/browser/TabBar.java
@@ -0,0 +1,475 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.ScrollWebView.ScrollListener;
+import com.android.browser.TabControl.TabChangeListener;
+
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.graphics.Color;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.LayerDrawable;
+import android.graphics.drawable.PaintDrawable;
+import android.view.ContextMenu;
+import android.view.Gravity;
+import android.view.LayoutInflater;
+import android.view.MenuInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.webkit.WebView;
+import android.widget.ImageButton;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * tabbed title bar for xlarge screen browser
+ */
+public class TabBar extends LinearLayout
+        implements TabChangeListener, ScrollListener, OnClickListener {
+
+    private static final int PROGRESS_MAX = 100;
+
+    private BrowserActivity mBrowserActivity;
+
+    private final int mTabWidthSelected;
+    private final int mTabWidthUnselected;
+
+    private TitleBarXLarge mTitleBar;
+
+    private TabScrollView mTabs;
+    private TabControl mControl;
+    private ImageButton mNewTab;
+    private int mButtonWidth;
+
+    private Map<Tab, TabViewData> mTabMap;
+
+    private boolean mUserRequestedUrlbar;
+    private boolean mTitleVisible;
+    private boolean mShowUrlMode;
+    private boolean mHasReceivedTitle;
+
+    private Drawable mGenericFavicon;
+    private String mLoadingText;
+
+    public TabBar(BrowserActivity context, TabControl tabcontrol, TitleBarXLarge titlebar) {
+        super(context);
+        Resources res = context.getResources();
+        mTabWidthSelected = (int) res.getDimension(R.dimen.tab_width_selected);
+        mTabWidthUnselected = (int) res.getDimension(R.dimen.tab_width_unselected);
+
+        mTitleBar = titlebar;
+        mTitleBar.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,
+                LayoutParams.WRAP_CONTENT));
+        mTabMap = new HashMap<Tab, TabViewData>();
+        mBrowserActivity = context;
+        mControl = tabcontrol;
+        Resources resources = context.getResources();
+        LayoutInflater factory = LayoutInflater.from(context);
+        factory.inflate(R.layout.tab_bar, this);
+        mTabs = (TabScrollView) findViewById(R.id.tabs);
+        mNewTab = (ImageButton) findViewById(R.id.newtab);
+        mNewTab.setOnClickListener(this);
+        mGenericFavicon = res.getDrawable(R.drawable.app_web_browser_sm);
+        mLoadingText = res.getString(R.string.title_bar_loading);
+
+        // TODO: Change enabled states based on whether you can go
+        // back/forward.  Probably should be done inside onPageStarted.
+
+        // build tabs
+        int tabcount = mControl.getTabCount();
+        for (int i = 0; i < tabcount; i++) {
+            Tab tab = mControl.getTab(i);
+            TabViewData data = buildTab(tab);
+            TabView tv = buildView(data);
+        }
+        mTabs.setSelectedTab(mControl.getCurrentIndex());
+
+        // register the tab change listener
+        mControl.setOnTabChangeListener(this);
+        mUserRequestedUrlbar = false;
+        mTitleVisible = true;
+        mButtonWidth = -1;
+    }
+
+    @Override
+    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+        if (mButtonWidth == -1) {
+            mButtonWidth = mNewTab.getMeasuredWidth();
+        }
+        int sw = mTabs.getMeasuredWidth();
+        int w = right-left;
+        if (w-sw < mButtonWidth) {
+            sw = w - mButtonWidth;
+        }
+        mTabs.layout(0, 0, sw, bottom-top );
+        mNewTab.layout(sw, 0, sw+mButtonWidth, bottom-top);
+    }
+
+    public void onClick(View view) {
+        mBrowserActivity.removeComboView();
+        if (mNewTab == view) {
+            mBrowserActivity.openTabToHomePage();
+        } else if (mTabs.getSelectedTab() == view) {
+            if (mBrowserActivity.isFakeTitleBarShowing() && !isLoading()) {
+                mBrowserActivity.hideFakeTitleBar();
+            } else {
+                showUrlBar();
+            }
+        } else {
+            int ix = mTabs.getChildIndex(view);
+            if (ix >= 0) {
+                mTabs.setSelectedTab(ix);
+                mBrowserActivity.switchToTab(ix);
+            }
+        }
+    }
+
+    private void showUrlBar() {
+        mBrowserActivity.stopScrolling();
+        mBrowserActivity.showFakeTitleBar();
+        mUserRequestedUrlbar = true;
+    }
+
+    private void setShowUrlMode(boolean showUrl) {
+        mShowUrlMode = showUrl;
+    }
+
+    // callback after fake titlebar is shown
+    void onShowTitleBar() {
+        setShowUrlMode(false);
+    }
+
+    // callback after fake titlebar is hidden
+    void onHideTitleBar() {
+        setShowUrlMode(!mTitleVisible);
+        Tab tab = mControl.getCurrentTab();
+        tab.getWebView().requestFocus();
+        mUserRequestedUrlbar = false;
+    }
+
+    // webview scroll listener
+
+    @Override
+    public void onScroll(boolean titleVisible) {
+        mTitleVisible = titleVisible;
+        if (!mShowUrlMode && !mTitleVisible && !isLoading()) {
+            if (mUserRequestedUrlbar) {
+                mBrowserActivity.hideFakeTitleBar();
+            } else {
+                setShowUrlMode(true);
+            }
+        } else if (mTitleVisible && !isLoading()) {
+            if (mShowUrlMode) {
+                setShowUrlMode(false);
+            }
+        }
+    }
+
+    @Override
+    public void createContextMenu(ContextMenu menu) {
+        MenuInflater inflater = mBrowserActivity.getMenuInflater();
+        inflater.inflate(R.menu.title_context, menu);
+        mBrowserActivity.onCreateContextMenu(menu, this, null);
+    }
+
+    private TabViewData buildTab(Tab tab) {
+        TabViewData data = new TabViewData(tab);
+        mTabMap.put(tab, data);
+        return data;
+    }
+
+    private TabView buildView(final TabViewData data) {
+        TabView tv = new TabView(mBrowserActivity, data);
+        tv.setTag(data);
+        tv.setOnClickListener(this);
+        mTabs.addTab(tv);
+        return tv;
+    }
+
+    /**
+     * View used in the tab bar
+     */
+    class TabView extends LinearLayout implements OnClickListener {
+
+        TabViewData mTabData;
+        View mTabContent;
+        TextView mTitle;
+        View mIncognito;
+        ImageView mIconView;
+        ImageView mLock;
+        ImageView mClose;
+        boolean mSelected;
+        boolean mInLoad;
+
+        /**
+         * @param context
+         */
+        public TabView(Context context, TabViewData tab) {
+            super(context);
+            mTabData = tab;
+            setGravity(Gravity.CENTER_VERTICAL);
+            setOrientation(LinearLayout.HORIZONTAL);
+            setBackgroundResource(R.drawable.tab_background);
+            LayoutInflater inflater = LayoutInflater.from(getContext());
+            mTabContent = inflater.inflate(R.layout.tab_title, this, true);
+            mTitle = (TextView) mTabContent.findViewById(R.id.title);
+            mIconView = (ImageView) mTabContent.findViewById(R.id.favicon);
+            mLock = (ImageView) mTabContent.findViewById(R.id.lock);
+            mClose = (ImageView) mTabContent.findViewById(R.id.close);
+            mClose.setOnClickListener(this);
+            mIncognito = mTabContent.findViewById(R.id.incognito);
+            mSelected = false;
+            mInLoad = false;
+            // update the status
+            updateFromData();
+        }
+
+        @Override
+        public void onClick(View v) {
+            if (v == mClose) {
+                closeTab();
+            }
+        }
+
+        private void updateFromData() {
+            mTabData.mTabView = this;
+            if (mTabData.mUrl != null) {
+                setDisplayTitle(mTabData.mUrl);
+            }
+            if (mTabData.mTitle != null) {
+                setDisplayTitle(mTabData.mTitle);
+            }
+            setProgress(mTabData.mProgress);
+            if (mTabData.mIcon != null) {
+                setFavicon(mTabData.mIcon);
+            }
+            if (mTabData.mLock != null) {
+                setLock(mTabData.mLock);
+            }
+            if (mTabData.mTab != null) {
+                mIncognito.setVisibility(
+                        mTabData.mTab.getWebView().isPrivateBrowsingEnabled() ?
+                        View.VISIBLE : View.GONE);
+            }
+        }
+
+        @Override
+        public void setActivated(boolean selected) {
+            mSelected = selected;
+            mClose.setVisibility(mSelected ? View.VISIBLE : View.GONE);
+            mTitle.setTextAppearance(mBrowserActivity, mSelected ?
+                    R.style.TabTitleSelected : R.style.TabTitleUnselected);
+            setHorizontalFadingEdgeEnabled(!mSelected);
+            setFadingEdgeLength(50);
+            super.setActivated(selected);
+            setLayoutParams(new LayoutParams(selected ?
+                    mTabWidthSelected : mTabWidthUnselected,
+                    LayoutParams.MATCH_PARENT));
+        }
+
+        void setDisplayTitle(String title) {
+            mTitle.setText(title);
+        }
+
+        void setFavicon(Drawable d) {
+            mIconView.setImageDrawable(d);
+        }
+
+        void setLock(Drawable d) {
+            if (null == d) {
+                mLock.setVisibility(View.GONE);
+            } else {
+                mLock.setImageDrawable(d);
+                mLock.setVisibility(View.VISIBLE);
+            }
+        }
+
+        void setTitleCompoundDrawables(Drawable left, Drawable top,
+                Drawable right, Drawable bottom) {
+            mTitle.setCompoundDrawables(left, top, right, bottom);
+        }
+
+        void setProgress(int newProgress) {
+            if (newProgress >= PROGRESS_MAX) {
+                mInLoad = false;
+            } else {
+                if (!mInLoad && getWindowToken() != null) {
+                    mInLoad = true;
+                }
+            }
+        }
+
+        private void closeTab() {
+            if (mTabData.mTab == mControl.getCurrentTab()) {
+                mBrowserActivity.closeCurrentWindow();
+            } else {
+                mBrowserActivity.closeTab(mTabData.mTab);
+            }
+        }
+
+    }
+
+    /**
+     * Store tab state within the title bar
+     */
+    class TabViewData {
+
+        Tab mTab;
+        TabView mTabView;
+        int mProgress;
+        Drawable mIcon;
+        Drawable mLock;
+        String mTitle;
+        String mUrl;
+
+        TabViewData(Tab tab) {
+            mTab = tab;
+            WebView web = tab.getWebView();
+            if (web != null) {
+                setUrlAndTitle(web.getUrl(), web.getTitle());
+            }
+        }
+
+        void setUrlAndTitle(String url, String title) {
+            mUrl = url;
+            mTitle = title;
+            if (mTabView != null) {
+                if (title != null) {
+                    mTabView.setDisplayTitle(title);
+                } else if (url != null) {
+                    mTabView.setDisplayTitle(UrlUtils.stripUrl(url));
+                }
+            }
+        }
+
+        void setProgress(int newProgress) {
+            mProgress = newProgress;
+            if (mTabView != null) {
+                mTabView.setProgress(mProgress);
+            }
+        }
+
+        void setFavicon(Bitmap icon) {
+            Drawable[] array = new Drawable[3];
+            array[0] = new PaintDrawable(Color.BLACK);
+            array[1] = new PaintDrawable(Color.WHITE);
+            if (icon == null) {
+                array[2] = mGenericFavicon;
+            } else {
+                array[2] = new BitmapDrawable(icon);
+            }
+            LayerDrawable d = new LayerDrawable(array);
+            d.setLayerInset(1, 1, 1, 1, 1);
+            d.setLayerInset(2, 2, 2, 2, 2);
+            mIcon = d;
+            if (mTabView != null) {
+                mTabView.setFavicon(mIcon);
+            }
+        }
+
+    }
+
+    // TabChangeListener implementation
+
+    @Override
+    public void onCurrentTab(Tab tab) {
+        mTabs.setSelectedTab(mControl.getCurrentIndex());
+        TabViewData tvd = mTabMap.get(tab);
+        if (tvd != null) {
+            tvd.setProgress(tvd.mProgress);
+            // update the scroll state
+            WebView webview = tab.getWebView();
+            onScroll(webview.getVisibleTitleHeight() > 0);
+        }
+    }
+
+    @Override
+    public void onFavicon(Tab tab, Bitmap favicon) {
+        TabViewData tvd = mTabMap.get(tab);
+        if (tvd != null) {
+            tvd.setFavicon(favicon);
+        }
+    }
+
+    @Override
+    public void onNewTab(Tab tab) {
+        TabViewData tvd = buildTab(tab);
+        buildView(tvd);
+    }
+
+    @Override
+    public void onProgress(Tab tab, int progress) {
+        TabViewData tvd = mTabMap.get(tab);
+        if (tvd != null) {
+            tvd.setProgress(progress);
+        }
+    }
+
+    @Override
+    public void onRemoveTab(Tab tab) {
+        TabViewData tvd = mTabMap.get(tab);
+        if (tvd != null) {
+            TabView tv = tvd.mTabView;
+            if (tv != null) {
+                mTabs.removeTab(tv);
+            }
+        }
+        mTabMap.remove(tab);
+    }
+
+    @Override
+    public void onUrlAndTitle(Tab tab, String url, String title) {
+        mHasReceivedTitle = true;
+        TabViewData tvd = mTabMap.get(tab);
+        if (tvd != null) {
+            tvd.setUrlAndTitle(url, title);
+        }
+    }
+
+    @Override
+    public void onPageFinished(Tab tab) {
+        if (!mHasReceivedTitle) {
+            TabViewData tvd = mTabMap.get(tab);
+            if (tvd != null) {
+                tvd.setUrlAndTitle(tvd.mUrl, null);
+            }
+        }
+    }
+
+    @Override
+    public void onPageStarted(Tab tab, String url, Bitmap favicon) {
+        mHasReceivedTitle = false;
+        TabViewData tvd = mTabMap.get(tab);
+        if (tvd != null) {
+            tvd.setFavicon(favicon);
+            tvd.setUrlAndTitle(url, mLoadingText);
+        }
+    }
+
+
+    private boolean isLoading() {
+        return mTabMap.get(mControl.getCurrentTab()).mTabView.mInLoad;
+    }
+
+}
diff --git a/src/com/android/browser/TabControl.java b/src/com/android/browser/TabControl.java
index afd4ea8..fcccad1 100644
--- a/src/com/android/browser/TabControl.java
+++ b/src/com/android/browser/TabControl.java
@@ -17,10 +17,6 @@
 package com.android.browser;
 
 import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapShader;
-import android.graphics.Paint;
-import android.graphics.Shader;
 import android.os.Bundle;
 import android.util.Log;
 import android.view.View;
@@ -29,17 +25,18 @@
 
 import java.io.File;
 import java.util.ArrayList;
+import java.util.HashMap;
 import java.util.Vector;
 
 class TabControl {
     // Log Tag
     private static final String LOGTAG = "TabControl";
     // Maximum number of tabs.
-    private static final int MAX_TABS = 8;
+    private int mMaxTabs;
     // Private array of WebViews that are used as tabs.
-    private ArrayList<Tab> mTabs = new ArrayList<Tab>(MAX_TABS);
+    private ArrayList<Tab> mTabs;
     // Queue of most recently viewed tabs.
-    private ArrayList<Tab> mTabQueue = new ArrayList<Tab>(MAX_TABS);
+    private ArrayList<Tab> mTabQueue;
     // Current position in mTabs.
     private int mCurrentTab = -1;
     // A private instance of BrowserActivity to interface with when adding and
@@ -47,6 +44,8 @@
     private final BrowserActivity mActivity;
     // Directory to store thumbnails for each WebView.
     private final File mThumbnailDir;
+    // Use on screen zoom buttons
+    private boolean mDisplayZoomControls;
 
     /**
      * Construct a new TabControl object that interfaces with the given
@@ -57,6 +56,10 @@
     TabControl(BrowserActivity activity) {
         mActivity = activity;
         mThumbnailDir = activity.getDir("thumbnails", 0);
+        mDisplayZoomControls = true;
+        mMaxTabs = activity.getResources().getInteger(R.integer.max_tabs);
+        mTabs = new ArrayList<Tab>(mMaxTabs);
+        mTabQueue = new ArrayList<Tab>(mMaxTabs);
     }
 
     File getThumbnailDir() {
@@ -68,6 +71,14 @@
     }
 
     /**
+     * Set if the webview should use the on screen zoom controls
+     * @param enabled
+     */
+    void setDisplayZoomControls(boolean enabled) {
+        mDisplayZoomControls = enabled;
+    }
+
+    /**
      * Return the current tab's main WebView. This will always return the main
      * WebView for a given tab and not a subwindow.
      * @return The current tab's WebView.
@@ -132,7 +143,7 @@
     int getCurrentIndex() {
         return mCurrentTab;
     }
-    
+
     /**
      * Given a Tab, find it's index
      * @param Tab to find
@@ -146,7 +157,20 @@
     }
 
     boolean canCreateNewTab() {
-        return MAX_TABS != mTabs.size();
+        return mMaxTabs != mTabs.size();
+    }
+
+    /**
+     * Returns true if there are any incognito tabs open.
+     * @return True when any incognito tabs are open, false otherwise.
+     */
+    boolean hasAnyOpenIncognitoTabs() {
+        for (Tab tab : mTabs) {
+            if (tab.getWebView() != null && tab.getWebView().isPrivateBrowsingEnabled()) {
+                return true;
+            }
+        }
+        return false;
     }
 
     /**
@@ -154,28 +178,32 @@
      * @return The newly createTab or null if we have reached the maximum
      *         number of open tabs.
      */
-    Tab createNewTab(boolean closeOnExit, String appId, String url) {
+    Tab createNewTab(boolean closeOnExit, String appId, String url,
+            boolean privateBrowsing) {
         int size = mTabs.size();
         // Return false if we have maxed out on tabs
-        if (MAX_TABS == size) {
+        if (mMaxTabs == size) {
             return null;
         }
-        final WebView w = createNewWebView();
+        final WebView w = createNewWebView(privateBrowsing);
 
         // Create a new tab and add it to the tab list
         Tab t = new Tab(mActivity, w, closeOnExit, appId, url);
         mTabs.add(t);
         // Initially put the tab in the background.
         t.putInBackground();
+        if (mTabChangeListener != null) {
+            mTabChangeListener.onNewTab(t);
+        }
         return t;
     }
 
     /**
      * Create a new tab with default values for closeOnExit(false),
-     * appId(null), and url(null).
+     * appId(null), url(null), and privateBrowsing(false).
      */
     Tab createNewTab() {
-        return createNewTab(false, null, null);
+        return createNewTab(false, null, null, false);
     }
 
     /**
@@ -231,6 +259,9 @@
 
         // Remove it from the queue of viewed tabs.
         mTabQueue.remove(t);
+        if (mTabChangeListener != null) {
+            mTabChangeListener.onRemoveTab(t);
+        }
         return true;
     }
 
@@ -277,29 +308,56 @@
      * @return True if there were previous tabs that were restored. False if
      *         there was no saved state or restoring the state failed.
      */
-    boolean restoreState(Bundle inState) {
+    boolean restoreState(Bundle inState, boolean dontRestoreIncognitoTabs) {
         final int numTabs = (inState == null)
                 ? -1 : inState.getInt(Tab.NUMTABS, -1);
         if (numTabs == -1) {
             return false;
         } else {
-            final int currentTab = inState.getInt(Tab.CURRTAB, -1);
+            final int oldCurrentTab = inState.getInt(Tab.CURRTAB, -1);
+
+            // Determine whether the saved current tab can be restored, and
+            // if not, which tab will take its place.
+            int currentTab = -1;
+            if (!dontRestoreIncognitoTabs
+                    || !inState.getBundle(Tab.WEBVIEW + oldCurrentTab).getBoolean(Tab.INCOGNITO)) {
+                currentTab = oldCurrentTab;
+            } else {
+                for (int i = 0; i < numTabs; i++) {
+                    if (!inState.getBundle(Tab.WEBVIEW + i).getBoolean(Tab.INCOGNITO)) {
+                        currentTab = i;
+                        break;
+                    }
+                }
+            }
+            if (currentTab < 0) {
+                return false;
+            }
+
+            // Map saved tab indices to new indices, in case any incognito tabs
+            // need to not be restored.
+            HashMap<Integer, Integer> originalTabIndices = new HashMap<Integer, Integer>();
+            originalTabIndices.put(-1, -1);
             for (int i = 0; i < numTabs; i++) {
-                if (i == currentTab) {
+                Bundle state = inState.getBundle(Tab.WEBVIEW + i);
+
+                if (dontRestoreIncognitoTabs && state != null && state.getBoolean(Tab.INCOGNITO)) {
+                    originalTabIndices.put(i, -1);
+                } else if (i == currentTab) {
                     Tab t = createNewTab();
                     // Me must set the current tab before restoring the state
                     // so that all the client classes are set.
                     setCurrentTab(t);
-                    if (!t.restoreState(inState.getBundle(Tab.WEBVIEW + i))) {
+                    if (!t.restoreState(state)) {
                         Log.w(LOGTAG, "Fail in restoreState, load home page.");
                         t.getWebView().loadUrl(BrowserSettings.getInstance()
                                 .getHomePage());
                     }
+                    originalTabIndices.put(i, getTabCount() - 1);
                 } else {
                     // Create a new tab and don't restore the state yet, add it
                     // to the tab list
                     Tab t = new Tab(mActivity, null, false, null, null);
-                    Bundle state = inState.getBundle(Tab.WEBVIEW + i);
                     if (state != null) {
                         t.setSavedState(state);
                         t.populatePickerDataFromSavedState();
@@ -311,15 +369,17 @@
                     mTabs.add(t);
                     // added the tab to the front as they are not current
                     mTabQueue.add(0, t);
+                    originalTabIndices.put(i, getTabCount() - 1);
                 }
             }
+
             // Rebuild the tree of tabs. Do this after all tabs have been
             // created/restored so that the parent tab exists.
             for (int i = 0; i < numTabs; i++) {
                 final Bundle b = inState.getBundle(Tab.WEBVIEW + i);
                 final Tab t = getTab(i);
                 if (b != null && t != null) {
-                    final int parentIndex = b.getInt(Tab.PARENTTAB, -1);
+                    final Integer parentIndex = originalTabIndices.get(b.getInt(Tab.PARENTTAB, -1));
                     if (parentIndex != -1) {
                         final Tab parent = getTab(parentIndex);
                         if (parent != null) {
@@ -529,29 +589,30 @@
      * Creates a new WebView and registers it with the global settings.
      */
     private WebView createNewWebView() {
+        return createNewWebView(false);
+    }
+
+    /**
+     * Creates a new WebView and registers it with the global settings.
+     * @param privateBrowsing When true, enables private browsing in the new
+     *        WebView.
+     */
+    private WebView createNewWebView(boolean privateBrowsing) {
         // Create a new WebView
-        WebView w = new WebView(mActivity);
+        ScrollWebView w = new ScrollWebView(mActivity, null,
+                android.R.attr.webViewStyle, privateBrowsing);
+        w.setScrollListener(mActivity.getScrollListener());
         w.setScrollbarFadingEnabled(true);
         w.setScrollBarStyle(View.SCROLLBARS_OUTSIDE_OVERLAY);
         w.setMapTrackballToArrowKeys(false); // use trackball directly
         // Enable the built-in zoom
         w.getSettings().setBuiltInZoomControls(true);
+        w.getSettings().setDisplayZoomControls(mDisplayZoomControls);
         // Add this WebView to the settings observer list and update the
         // settings
         final BrowserSettings s = BrowserSettings.getInstance();
         s.addObserver(w.getSettings()).update(s, null);
 
-        // pick a default
-        if (false) {
-            MeshTracker mt = new MeshTracker(2);
-            Paint paint = new Paint();
-            Bitmap bm = BitmapFactory.decodeResource(mActivity.getResources(),
-                                         R.drawable.pattern_carbon_fiber_dark);
-            paint.setShader(new BitmapShader(bm, Shader.TileMode.REPEAT,
-                                             Shader.TileMode.REPEAT));
-            mt.setBGPaint(paint);
-            w.setDragTracker(mt);
-        }
         return w;
     }
 
@@ -619,4 +680,42 @@
         }
         return true;
     }
+
+    interface TabChangeListener {
+
+        public void onNewTab(Tab tab);
+
+        public void onRemoveTab(Tab tab);
+
+        public void onCurrentTab(Tab tab);
+
+        public void onProgress(Tab tab, int progress);
+
+        public void onUrlAndTitle(Tab tab, String url, String title);
+
+        public void onFavicon(Tab tab, Bitmap favicon);
+
+        public void onPageStarted(Tab tab, String url, Bitmap favicon);
+
+        public void onPageFinished(Tab tab);
+
+    }
+
+    private TabChangeListener mTabChangeListener;
+
+    /**
+     * register the TabChangeListener with the tab control
+     * @param listener
+     */
+    void setOnTabChangeListener(TabChangeListener listener) {
+        mTabChangeListener = listener;
+    }
+
+    /**
+     * get the current TabChangeListener (used by the tabs)
+     */
+    TabChangeListener getTabChangeListener() {
+        return mTabChangeListener;
+    }
+
 }
diff --git a/src/com/android/browser/TabScrollView.java b/src/com/android/browser/TabScrollView.java
new file mode 100644
index 0000000..7268ddc
--- /dev/null
+++ b/src/com/android/browser/TabScrollView.java
@@ -0,0 +1,214 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+
+package com.android.browser;
+
+import android.animation.Animator;
+import android.animation.Animator.AnimatorListener;
+import android.animation.AnimatorListenerAdapter;
+import android.animation.ObjectAnimator;
+import android.animation.PropertyValuesHolder;
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.drawable.Drawable;
+import android.util.AttributeSet;
+import android.view.View;
+import android.view.animation.AccelerateInterpolator;
+import android.widget.HorizontalScrollView;
+import android.widget.LinearLayout;
+
+/**
+ * custom view for displaying tabs in the tabbed title bar
+ */
+public class TabScrollView extends HorizontalScrollView {
+
+    private BrowserActivity mBrowserActivity;
+    private LinearLayout mContentView;
+    private int mSelected;
+    private Drawable mArrowLeft;
+    private Drawable mArrowRight;
+    private int mAnimationDuration;
+
+    /**
+     * @param context
+     * @param attrs
+     * @param defStyle
+     */
+    public TabScrollView(Context context, AttributeSet attrs, int defStyle) {
+        super(context, attrs, defStyle);
+        init(context);
+    }
+
+    /**
+     * @param context
+     * @param attrs
+     */
+    public TabScrollView(Context context, AttributeSet attrs) {
+        super(context, attrs);
+        init(context);
+    }
+
+    /**
+     * @param context
+     */
+    public TabScrollView(Context context) {
+        super(context);
+        init(context);
+    }
+
+    private void init(Context ctx) {
+        mBrowserActivity = (BrowserActivity) ctx;
+        mAnimationDuration = ctx.getResources().getInteger(
+                R.integer.tab_animation_duration);
+        setHorizontalScrollBarEnabled(false);
+        mContentView = new LinearLayout(mBrowserActivity);
+        mContentView.setOrientation(LinearLayout.HORIZONTAL);
+        mContentView.setLayoutParams(
+                new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.MATCH_PARENT));
+        addView(mContentView);
+        mSelected = -1;
+        mArrowLeft = ctx.getResources().getDrawable(R.drawable.ic_arrow_left);
+        mArrowRight = ctx.getResources().getDrawable(R.drawable.ic_arrow_right);
+        // prevent ProGuard from removing the property methods
+        setScroll(getScroll());
+    }
+
+    @Override
+    protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+        super.onLayout(changed, left, top, right, bottom);
+        ensureChildVisible(getSelectedTab());
+    }
+
+    void setSelectedTab(int position) {
+        View v = getSelectedTab();
+        if (v != null) {
+            v.setActivated(false);
+        }
+        mSelected = position;
+        v = getSelectedTab();
+        if (v != null) {
+            v.setActivated(true);
+        }
+        requestLayout();
+    }
+
+    int getChildIndex(View v) {
+        return mContentView.indexOfChild(v);
+    }
+
+    View getSelectedTab() {
+        if ((mSelected >= 0) && (mSelected < mContentView.getChildCount())) {
+            return mContentView.getChildAt(mSelected);
+        } else {
+            return null;
+        }
+    }
+
+    void clearTabs() {
+        mContentView.removeAllViews();
+    }
+
+    void addTab(View tab) {
+        mContentView.addView(tab);
+        animateIn(tab);
+        tab.setActivated(false);
+    }
+
+    void removeTab(View tab) {
+        int ix = mContentView.indexOfChild(tab);
+        if (ix == mSelected) {
+            mSelected = -1;
+        } else if (ix < mSelected) {
+            mSelected--;
+        }
+        animateOut(tab);
+    }
+
+    private void ensureChildVisible(View child) {
+        if (child != null) {
+            int childl = child.getLeft();
+            int childr = childl + child.getWidth();
+            int viewl = getScrollX();
+            int viewr = viewl + getWidth();
+            if (childl < viewl) {
+                // need scrolling to left
+                animateScroll(childl);
+            } else if (childr > viewr) {
+                // need scrolling to right
+                animateScroll(childr - viewr + viewl);
+            }
+        }
+    }
+
+    @Override
+    protected void dispatchDraw(Canvas canvas) {
+        super.dispatchDraw(canvas);
+        int l = getScrollX();
+        int r = l + getWidth();
+        int dis = 8;
+        if (l > 0) {
+            int aw = mArrowLeft.getIntrinsicWidth();
+            mArrowLeft.setBounds(l + dis, 0, l + dis + aw, getHeight());
+            mArrowLeft.draw(canvas);
+        }
+        if (r < mContentView.getWidth()) {
+            int aw = mArrowRight.getIntrinsicWidth();
+            mArrowRight.setBounds(r - dis - aw, 0, r - dis, getHeight());
+            mArrowRight.draw(canvas);
+        }
+    }
+
+    private void animateIn(View tab) {
+        ObjectAnimator animator = ObjectAnimator.ofInt(tab, "TranslationX", 500, 0);
+        animator.setDuration(mAnimationDuration);
+        animator.start();
+    }
+
+    private void animateOut(final View tab) {
+        ObjectAnimator animator = ObjectAnimator.ofInt(
+                tab, "TranslationX", 0, getScrollX() - tab.getRight());
+        animator.setDuration(mAnimationDuration);
+        animator.addListener(new AnimatorListenerAdapter() {
+            @Override
+            public void onAnimationEnd(Animator animation) {
+                mContentView.removeView(tab);
+            }
+        });
+        animator.setInterpolator(new AccelerateInterpolator());
+        animator.start();
+    }
+
+    private void animateScroll(int newscroll) {
+        ObjectAnimator animator = ObjectAnimator.ofInt(this, "scroll", getScrollX(), newscroll);
+        animator.setDuration(mAnimationDuration);
+        animator.start();
+    }
+
+    /**
+     * required for animation
+     */
+    public void setScroll(int newscroll) {
+        scrollTo(newscroll, getScrollY());
+    }
+
+    /**
+     * required for animation
+     */
+    public int getScroll() {
+        return getScrollX();
+    }
+
+}
diff --git a/src/com/android/browser/TitleBar.java b/src/com/android/browser/TitleBar.java
index dc4979b..035dc34 100644
--- a/src/com/android/browser/TitleBar.java
+++ b/src/com/android/browser/TitleBar.java
@@ -21,14 +21,8 @@
 import android.content.pm.PackageManager;
 import android.content.pm.ResolveInfo;
 import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Color;
-import android.graphics.Rect;
 import android.graphics.drawable.Animatable;
-import android.graphics.drawable.BitmapDrawable;
 import android.graphics.drawable.Drawable;
-import android.graphics.drawable.LayerDrawable;
-import android.graphics.drawable.PaintDrawable;
 import android.os.Handler;
 import android.os.Message;
 import android.speech.RecognizerIntent;
@@ -45,7 +39,6 @@
 import android.view.View;
 import android.view.ViewConfiguration;
 import android.widget.ImageView;
-import android.widget.LinearLayout;
 import android.widget.ProgressBar;
 import android.widget.TextView;
 
@@ -55,21 +48,16 @@
  * This class represents a title bar for a particular "tab" or "window" in the
  * browser.
  */
-public class TitleBar extends LinearLayout {
+public class TitleBar extends TitleBarBase {
     private TextView        mTitle;
-    private Drawable        mCloseDrawable;
     private ImageView       mRtButton;
     private Drawable        mCircularProgress;
     private ProgressBar     mHorizontalProgress;
-    private ImageView       mFavicon;
-    private ImageView       mLockIcon;
     private ImageView       mStopButton;
     private Drawable        mBookmarkDrawable;
     private Drawable        mVoiceDrawable;
     private boolean         mInLoad;
     private BrowserActivity mBrowserActivity;
-    private Drawable        mGenericFavicon;
-    private int             mIconDimension;
     private View            mTitleBg;
     private MyHandler       mHandler;
     private Intent          mVoiceSearchIntent;
@@ -84,7 +72,7 @@
     private static int LONG_PRESS = 1;
 
     public TitleBar(BrowserActivity context) {
-        super(context, null);
+        super(context);
         mHandler = new MyHandler();
         LayoutInflater factory = LayoutInflater.from(context);
         factory.inflate(R.layout.title_bar, this);
@@ -107,13 +95,11 @@
                 TypedValue.COMPLEX_UNIT_DIP, 8f, metrics);
         mRightMargin = (int) TypedValue.applyDimension(
                 TypedValue.COMPLEX_UNIT_DIP, 6f, metrics);
-        mIconDimension = (int) TypedValue.applyDimension(
+        int iconDimension = (int) TypedValue.applyDimension(
                 TypedValue.COMPLEX_UNIT_DIP, 20f, metrics);
-        mCircularProgress.setBounds(0, 0, mIconDimension, mIconDimension);
+        mCircularProgress.setBounds(0, 0, iconDimension, iconDimension);
         mHorizontalProgress = (ProgressBar) findViewById(
                 R.id.progress_horizontal);
-        mGenericFavicon = context.getResources().getDrawable(
-                R.drawable.app_web_browser_sm);
         mVoiceSearchIntent = new Intent(RecognizerIntent.ACTION_WEB_SEARCH);
         mVoiceSearchIntent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL,
                 RecognizerIntent.LANGUAGE_MODEL_WEB_SEARCH);
@@ -219,7 +205,8 @@
                     } else if (mInLoad) {
                         mBrowserActivity.stopLoading();
                     } else {
-                        mBrowserActivity.bookmarksOrHistoryPicker(false);
+                        mBrowserActivity.bookmarkCurrentPage(
+                                AddBookmarkPage.DEFAULT_FOLDER_ID);
                     }
                     button.setPressed(false);
                 } else if (mTitleBg.isPressed()) {
@@ -248,25 +235,6 @@
     }
 
     /**
-     * Set a new Bitmap for the Favicon.
-     */
-    /* package */ void setFavicon(Bitmap icon) {
-        Drawable[] array = new Drawable[3];
-        array[0] = new PaintDrawable(Color.BLACK);
-        PaintDrawable p = new PaintDrawable(Color.WHITE);
-        array[1] = p;
-        if (icon == null) {
-            array[2] = mGenericFavicon;
-        } else {
-            array[2] = new BitmapDrawable(icon);
-        }
-        LayerDrawable d = new LayerDrawable(array);
-        d.setLayerInset(1, 1, 1, 1, 1);
-        d.setLayerInset(2, 2, 2, 2, 2);
-        mFavicon.setImageDrawable(d);
-    }
-
-    /**
      * Change the TitleBar to or from voice mode.  If there is no package to
      * handle voice search, the TitleBar cannot be set to voice mode.
      */
@@ -302,18 +270,6 @@
     }
 
     /**
-     * Set the Drawable for the lock icon, or null to hide it.
-     */
-    /* package */ void setLock(Drawable d) {
-        if (null == d) {
-            mLockIcon.setVisibility(View.GONE);
-        } else {
-            mLockIcon.setImageDrawable(d);
-            mLockIcon.setVisibility(View.VISIBLE);
-        }
-    }
-
-    /**
      * Update the progress, from 0 to 100.
      */
     /* package */ void setProgress(int newProgress) {
@@ -374,11 +330,4 @@
             }
         }
     }
-
-    /* package */ void setToTabPicker() {
-        mTitle.setText(R.string.tab_picker_title);
-        setFavicon(null);
-        setLock(null);
-        mHorizontalProgress.setVisibility(View.GONE);
-    }
 }
diff --git a/src/com/android/browser/TitleBarBase.java b/src/com/android/browser/TitleBarBase.java
new file mode 100644
index 0000000..7016dc0
--- /dev/null
+++ b/src/com/android/browser/TitleBarBase.java
@@ -0,0 +1,78 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.graphics.Bitmap;
+import android.graphics.Color;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.LayerDrawable;
+import android.graphics.drawable.PaintDrawable;
+import android.view.View;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+
+/**
+ * Base class for a title bar used by the browser.
+ */
+public class TitleBarBase extends LinearLayout {
+    // These need to be set by the subclass.
+    protected ImageView mFavicon;
+    protected ImageView mLockIcon;
+
+    protected Drawable mGenericFavicon;
+
+    public TitleBarBase(Context context) {
+        super(context, null);
+        mGenericFavicon = context.getResources().getDrawable(
+                R.drawable.app_web_browser_sm);
+    }
+
+    /* package */ void setProgress(int newProgress) {}
+    /* package */ void setDisplayTitle(String title) {}
+
+    /* package */ void setLock(Drawable d) {
+        assert mLockIcon != null;
+        if (null == d) {
+            mLockIcon.setVisibility(View.GONE);
+        } else {
+            mLockIcon.setImageDrawable(d);
+            mLockIcon.setVisibility(View.VISIBLE);
+        }
+    }
+
+    /* package */ void setFavicon(Bitmap icon) {
+        assert mFavicon != null;
+        Drawable[] array = new Drawable[3];
+        array[0] = new PaintDrawable(Color.BLACK);
+        PaintDrawable p = new PaintDrawable(Color.WHITE);
+        array[1] = p;
+        if (icon == null) {
+            array[2] = mGenericFavicon;
+        } else {
+            array[2] = new BitmapDrawable(icon);
+        }
+        LayerDrawable d = new LayerDrawable(array);
+        d.setLayerInset(1, 1, 1, 1, 1);
+        d.setLayerInset(2, 2, 2, 2, 2);
+        mFavicon.setImageDrawable(d);
+    }
+
+    /* package */ void setInVoiceMode(boolean inVoiceMode) {}
+
+}
diff --git a/src/com/android/browser/TitleBarXLarge.java b/src/com/android/browser/TitleBarXLarge.java
new file mode 100644
index 0000000..b87ea78
--- /dev/null
+++ b/src/com/android/browser/TitleBarXLarge.java
@@ -0,0 +1,252 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.UrlInputView.UrlInputListener;
+
+import android.app.SearchManager;
+import android.content.Context;
+import android.content.Intent;
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.graphics.drawable.Drawable;
+import android.text.TextUtils;
+import android.view.ContextMenu;
+import android.view.LayoutInflater;
+import android.view.MenuInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.view.View.OnFocusChangeListener;
+import android.widget.ImageView;
+import android.widget.TextView;
+
+/**
+ * tabbed title bar for xlarge screen browser
+ */
+public class TitleBarXLarge extends TitleBarBase
+    implements UrlInputListener, OnClickListener, OnFocusChangeListener {
+
+    private static final int PROGRESS_MAX = 100;
+
+    private BrowserActivity mBrowserActivity;
+    private Drawable mStopDrawable;
+    private Drawable mReloadDrawable;
+
+
+    private View mContainer;
+    private View mBackButton;
+    private View mForwardButton;
+    private View mStar;
+    private View mSearchButton;
+    private View mFocusContainer;
+    private View mUnfocusContainer;
+    private View mGoButton;
+    private ImageView mStopButton;
+    private View mAllButton;
+    private View mClearButton;
+    private PageProgressView mProgressView;
+    private UrlInputView mUrlFocused;
+    private TextView mUrlUnfocused;
+    private boolean mInLoad;
+
+    public TitleBarXLarge(BrowserActivity context) {
+        super(context);
+        mBrowserActivity = context;
+        Resources resources = context.getResources();
+        mStopDrawable = resources.getDrawable(R.drawable.ic_stop_normal);
+        mReloadDrawable = resources.getDrawable(R.drawable.ic_refresh_normal);
+        rebuildLayout(context, true);
+    }
+
+    private void rebuildLayout(Context context, boolean rebuildData) {
+        LayoutInflater factory = LayoutInflater.from(context);
+        factory.inflate(R.layout.url_bar, this);
+
+        mContainer = findViewById(R.id.taburlbar);
+        mUrlFocused = (UrlInputView) findViewById(R.id.url_focused);
+        mUrlUnfocused = (TextView) findViewById(R.id.url_unfocused);
+        mAllButton = findViewById(R.id.all_btn);
+        // TODO: Change enabled states based on whether you can go
+        // back/forward.  Probably should be done inside onPageStarted.
+        mBackButton = findViewById(R.id.back);
+        mForwardButton = findViewById(R.id.forward);
+        mStar = findViewById(R.id.star);
+        mStopButton = (ImageView) findViewById(R.id.stop);
+        mSearchButton = findViewById(R.id.search);
+        mLockIcon = (ImageView) findViewById(R.id.lock);
+        mGoButton = findViewById(R.id.go);
+        mClearButton = findViewById(R.id.clear);
+        mProgressView = (PageProgressView) findViewById(R.id.progress);
+        mFocusContainer = findViewById(R.id.urlbar_focused);
+        mUnfocusContainer = findViewById(R.id.urlbar_unfocused);
+
+        mBackButton.setOnClickListener(this);
+        mForwardButton.setOnClickListener(this);
+        mStar.setOnClickListener(this);
+        mAllButton.setOnClickListener(this);
+        mStopButton.setOnClickListener(this);
+        mSearchButton.setOnClickListener(this);
+        mGoButton.setOnClickListener(this);
+        mClearButton.setOnClickListener(this);
+        mUrlFocused.setUrlInputListener(this);
+        mUrlUnfocused.setOnFocusChangeListener(this);
+        mUrlFocused.setContainer(mFocusContainer);
+        mUnfocusContainer.setOnClickListener(this);
+    }
+
+    public void onFocusChange(View v, boolean hasFocus) {
+        if (hasFocus) {
+            setUrlMode(true);
+            mUrlFocused.selectAll();
+            mUrlFocused.requestFocus();
+            mUrlFocused.setDropDownWidth(mUnfocusContainer.getWidth());
+            mUrlFocused.setDropDownHorizontalOffset(-mUrlFocused.getLeft());
+        }
+    }
+
+    @Override
+    public void onClick(View v) {
+        if (mUnfocusContainer == v) {
+            mUrlUnfocused.requestFocus();
+        } else if (mBackButton == v) {
+            mBrowserActivity.getTopWindow().goBack();
+        } else if (mForwardButton == v) {
+            mBrowserActivity.getTopWindow().goForward();
+        } else if (mStar == v) {
+            mBrowserActivity.bookmarkCurrentPage(
+                    AddBookmarkPage.DEFAULT_FOLDER_ID);
+        } else if (mAllButton == v) {
+            mBrowserActivity.bookmarksOrHistoryPicker(false);
+        } else if (mSearchButton == v) {
+            search();
+        } else if (mStopButton == v) {
+            stopOrRefresh();
+        } else if (mGoButton == v) {
+            if (!TextUtils.isEmpty(mUrlFocused.getText())) {
+                onAction(mUrlFocused.getText().toString());
+            }
+        } else if (mClearButton == v) {
+            mUrlFocused.setText("");
+        }
+    }
+
+    int getHeightWithoutProgress() {
+        return mContainer.getHeight();
+    }
+
+    @Override
+    void setFavicon(Bitmap icon) { }
+
+    // UrlInputListener implementation
+
+    @Override
+    public void onAction(String text) {
+        mBrowserActivity.getTabControl().getCurrentTopWebView().requestFocus();
+        mBrowserActivity.hideFakeTitleBar();
+        Intent i = new Intent();
+        i.setAction(Intent.ACTION_SEARCH);
+        i.putExtra(SearchManager.QUERY, text);
+        mBrowserActivity.onNewIntent(i);
+        setUrlMode(false);
+        setDisplayTitle(text);
+    }
+
+    @Override
+    public void onDismiss() {
+        mBrowserActivity.getTabControl().getCurrentTopWebView().requestFocus();
+        mBrowserActivity.hideFakeTitleBar();
+        setUrlMode(false);
+        setDisplayTitle(mBrowserActivity.getTabControl().getCurrentWebView().getUrl());
+    }
+
+    @Override
+    public void onEdit(String text) {
+        setDisplayTitle(text, true);
+        if (text != null) {
+            mUrlFocused.setSelection(text.length());
+        }
+    }
+
+    private void setUrlMode(boolean focused) {
+        swapUrlContainer(focused);
+        if (focused) {
+            mSearchButton.setVisibility(View.GONE);
+            mGoButton.setVisibility(View.VISIBLE);
+        } else {
+            mSearchButton.setVisibility(View.VISIBLE);
+            mGoButton.setVisibility(View.GONE);
+        }
+    }
+
+    private void swapUrlContainer(boolean focus) {
+        mUnfocusContainer.setVisibility(focus ? View.GONE : View.VISIBLE);
+        mFocusContainer.setVisibility(focus ? View.VISIBLE : View.GONE);
+    }
+
+    @Override
+    public void createContextMenu(ContextMenu menu) {
+        MenuInflater inflater = mBrowserActivity.getMenuInflater();
+        inflater.inflate(R.menu.title_context, menu);
+        mBrowserActivity.onCreateContextMenu(menu, this, null);
+    }
+
+    private void search() {
+        setDisplayTitle("");
+        mUrlUnfocused.requestFocus();
+    }
+
+    private void stopOrRefresh() {
+        if (mInLoad) {
+            mBrowserActivity.stopLoading();
+        } else {
+            mBrowserActivity.getTopWindow().reload();
+        }
+    }
+
+    /**
+     * Update the progress, from 0 to 100.
+     */
+    @Override
+    void setProgress(int newProgress) {
+        if (newProgress >= PROGRESS_MAX) {
+            mProgressView.setProgress(PageProgressView.MAX_PROGRESS);
+            mProgressView.setVisibility(View.GONE);
+            mInLoad = false;
+            mStopButton.setImageDrawable(mReloadDrawable);
+        } else {
+            if (!mInLoad) {
+                mProgressView.setVisibility(View.VISIBLE);
+                mInLoad = true;
+                mStopButton.setImageDrawable(mStopDrawable);
+            }
+            mProgressView.setProgress(newProgress * PageProgressView.MAX_PROGRESS
+                    / PROGRESS_MAX);
+        }
+    }
+
+    @Override
+    /* package */ void setDisplayTitle(String title) {
+        mUrlFocused.setText(title, false);
+        mUrlUnfocused.setText(title);
+    }
+
+    void setDisplayTitle(String title, boolean filter) {
+        mUrlFocused.setText(title, filter);
+        mUrlUnfocused.setText(title);
+    }
+
+}
diff --git a/src/com/android/browser/UrlInputView.java b/src/com/android/browser/UrlInputView.java
new file mode 100644
index 0000000..18c5fe6
--- /dev/null
+++ b/src/com/android/browser/UrlInputView.java
@@ -0,0 +1,184 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.SuggestionsAdapter.CompletionListener;
+
+import android.content.ContentResolver;
+import android.content.Context;
+import android.content.res.Configuration;
+import android.util.AttributeSet;
+import android.view.ActionMode;
+import android.view.KeyEvent;
+import android.view.View;
+import android.view.View.OnFocusChangeListener;
+import android.view.inputmethod.InputMethodManager;
+import android.widget.AutoCompleteTextView;
+import android.widget.TextView;
+import android.widget.TextView.OnEditorActionListener;
+
+/**
+ * url/search input view
+ * handling suggestions
+ */
+public class UrlInputView extends AutoCompleteTextView
+        implements OnFocusChangeListener, OnEditorActionListener, CompletionListener {
+
+    private UrlInputListener   mListener;
+    private InputMethodManager mInputManager;
+    private SuggestionsAdapter mAdapter;
+    private OnFocusChangeListener mWrappedFocusListener;
+    private View mContainer;
+    private boolean mLandscape;
+
+    public UrlInputView(Context context, AttributeSet attrs, int defStyle) {
+        super(context, attrs, defStyle);
+        init(context);
+    }
+
+    public UrlInputView(Context context, AttributeSet attrs) {
+        super(context, attrs);
+        init(context);
+    }
+
+    public UrlInputView(Context context) {
+        super(context);
+        init(context);
+    }
+
+    private void init(Context ctx) {
+        mInputManager = (InputMethodManager) ctx.getSystemService(Context.INPUT_METHOD_SERVICE);
+        setOnEditorActionListener(this);
+        super.setOnFocusChangeListener(this);
+        mAdapter = new SuggestionsAdapter(ctx, this);
+        setAdapter(mAdapter);
+        setSelectAllOnFocus(false);
+        onConfigurationChanged(ctx.getResources().getConfiguration());
+    }
+
+    void setContainer(View container) {
+        mContainer = container;
+    }
+
+    @Override
+    protected void onConfigurationChanged(Configuration config) {
+        mLandscape = (config.orientation &
+                Configuration.ORIENTATION_LANDSCAPE) > 0;
+        if (isPopupShowing() && (getVisibility() == View.VISIBLE)) {
+            dismissDropDown();
+            getFilter().filter(getText());
+        }
+    }
+
+    @Override
+    public void showDropDown() {
+        int width = mContainer.getWidth();
+        if (mLandscape && ((mAdapter.getLeftCount() == 0) ||
+                (mAdapter.getRightCount() == 0))) {
+            width = width / 2;
+        }
+        if (width != getDropDownWidth()) {
+            setDropDownWidth(width);
+        }
+        if (getLeft() != -getDropDownHorizontalOffset()) {
+            setDropDownHorizontalOffset(-getLeft());
+        }
+        mAdapter.setLandscapeMode(mLandscape);
+        super.showDropDown();
+    }
+
+    @Override
+    public ActionMode startActionMode(ActionMode.Callback callback) {
+        // suppress selection action mode
+        return null;
+    }
+
+    @Override
+    public void setOnFocusChangeListener(OnFocusChangeListener focusListener) {
+        mWrappedFocusListener = focusListener;
+    }
+
+    @Override
+    public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
+        finishInput(getText().toString());
+        return true;
+    }
+
+    @Override
+    public void onFocusChange(View v, boolean hasFocus) {
+        if (hasFocus) {
+            forceIme();
+        } else {
+            finishInput(null);
+        }
+        if (mWrappedFocusListener != null) {
+            mWrappedFocusListener.onFocusChange(v, hasFocus);
+        }
+    }
+
+    public void setUrlInputListener(UrlInputListener listener) {
+        mListener = listener;
+    }
+
+    public void forceIme() {
+        mInputManager.showSoftInput(this, 0);
+    }
+
+    private void finishInput(String url) {
+        this.dismissDropDown();
+        this.setSelection(0,0);
+        mInputManager.hideSoftInputFromWindow(getWindowToken(), 0);
+        if (url == null) {
+            mListener.onDismiss();
+        } else {
+            mListener.onAction(url);
+        }
+    }
+
+    // Completion Listener
+
+    @Override
+    public void onSearch(String search) {
+        mListener.onEdit(search);
+    }
+
+    @Override
+    public void onSelect(String url) {
+        finishInput(url);
+    }
+
+    @Override
+    public boolean onKeyPreIme(int keyCode, KeyEvent evt) {
+        if (keyCode == KeyEvent.KEYCODE_BACK) {
+            // catch back key in order to do slightly more cleanup than usual
+            finishInput(null);
+            return true;
+        }
+        return super.onKeyPreIme(keyCode, evt);
+    }
+
+    interface UrlInputListener {
+
+        public void onDismiss();
+
+        public void onAction(String text);
+
+        public void onEdit(String text);
+
+    }
+
+}
diff --git a/src/com/android/browser/UrlUtils.java b/src/com/android/browser/UrlUtils.java
new file mode 100644
index 0000000..cb6377a
--- /dev/null
+++ b/src/com/android/browser/UrlUtils.java
@@ -0,0 +1,49 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser;
+
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+public class UrlUtils {
+
+    // Regular expression which matches http://, followed by some stuff, followed by
+    // optionally a trailing slash, all matched as separate groups.
+    private static final Pattern STRIP_URL_PATTERN = Pattern.compile("^(http://)(.*?)(/$)?");
+
+    private UrlUtils() { /* cannot be instantiated */ }
+
+    /**
+     * Strips the provided url of preceding "http://" and any trailing "/". Does not
+     * strip "https://". If the provided string cannot be stripped, the original string
+     * is returned.
+     *
+     * TODO: Put this in TextUtils to be used by other packages doing something similar.
+     *
+     * @param url a url to strip, like "http://www.google.com/"
+     * @return a stripped url like "www.google.com", or the original string if it could
+     *         not be stripped
+     */
+    /* package */ static String stripUrl(String url) {
+        if (url == null) return null;
+        Matcher m = STRIP_URL_PATTERN.matcher(url);
+        if (m.matches() && m.groupCount() == 3) {
+            return m.group(2);
+        } else {
+            return url;
+        }
+    }
+}
diff --git a/src/com/android/browser/WebDialog.java b/src/com/android/browser/WebDialog.java
deleted file mode 100644
index 9995e8f..0000000
--- a/src/com/android/browser/WebDialog.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser;
-
-import android.content.Context;
-import android.view.View;
-import android.view.animation.AnimationUtils;
-import android.view.inputmethod.InputMethodManager;
-import android.webkit.WebView;
-import android.widget.LinearLayout;
-
-/* package */ class WebDialog extends LinearLayout {
-    protected WebView         mWebView;
-    protected BrowserActivity mBrowserActivity;
-    private boolean           mIsVisible;
-
-    /* package */ WebDialog(BrowserActivity context) {
-        super(context);
-        mBrowserActivity = context;
-    }
-
-    /* dialogs that have cancel buttons can optionally share code by including a
-     * view with an id of 'done'.
-     */
-    protected void addCancel() {
-        View button = findViewById(R.id.done);
-        if (button != null) button.setOnClickListener(mCancelListener);
-    }
-
-    private View.OnClickListener mCancelListener = new View.OnClickListener() {
-        public void onClick(View v) {
-            mBrowserActivity.closeDialogs();
-        }
-    };
-
-    protected void dismiss() {
-        startAnimation(AnimationUtils.loadAnimation(mBrowserActivity,
-                R.anim.dialog_exit));
-        mIsVisible = false;
-    }
-
-    /*
-     * Remove the soft keyboard from the screen.
-     */
-    protected void hideSoftInput() {
-        InputMethodManager imm = (InputMethodManager)
-                mBrowserActivity.getSystemService(Context.INPUT_METHOD_SERVICE);
-        imm.hideSoftInputFromWindow(mWebView.getWindowToken(), 0);
-    }
-
-    protected boolean isVisible() {
-        return mIsVisible;
-    }
-
-    /* package */ void setWebView(WebView webview) {
-        mWebView = webview;
-    }
-
-    protected void show() {
-        startAnimation(AnimationUtils.loadAnimation(mBrowserActivity,
-            R.anim.dialog_enter));
-        mIsVisible = true;
-    }
-
-}
diff --git a/src/com/android/browser/preferences/AdvancedPreferencesFragment.java b/src/com/android/browser/preferences/AdvancedPreferencesFragment.java
new file mode 100644
index 0000000..59b6ce1
--- /dev/null
+++ b/src/com/android/browser/preferences/AdvancedPreferencesFragment.java
@@ -0,0 +1,91 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserSettings;
+import com.android.browser.R;
+import com.android.browser.WebsiteSettingsActivity;
+
+import android.content.Intent;
+import android.os.Bundle;
+import android.preference.Preference;
+import android.preference.PreferenceFragment;
+import android.preference.PreferenceScreen;
+import android.webkit.GeolocationPermissions;
+import android.webkit.ValueCallback;
+import android.webkit.WebStorage;
+
+import java.util.Map;
+import java.util.Set;
+
+public class AdvancedPreferencesFragment extends PreferenceFragment 
+        implements Preference.OnPreferenceChangeListener {
+
+    @Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+
+        // Load the XML preferences file
+        addPreferencesFromResource(R.xml.advanced_preferences);
+
+        PreferenceScreen websiteSettings = (PreferenceScreen) findPreference(
+                BrowserSettings.PREF_WEBSITE_SETTINGS);
+        Intent intent = new Intent(getActivity(), WebsiteSettingsActivity.class);
+        websiteSettings.setIntent(intent);
+    }
+
+    /*
+     * We need to set the PreferenceScreen state in onResume(), as the number of
+     * origins with active features (WebStorage, Geolocation etc) could have
+     * changed after calling the WebsiteSettingsActivity.
+     */
+    @Override
+    public void onResume() {
+        super.onResume();
+        final PreferenceScreen websiteSettings = (PreferenceScreen) findPreference(
+                BrowserSettings.PREF_WEBSITE_SETTINGS);
+        websiteSettings.setEnabled(false);
+        WebStorage.getInstance().getOrigins(new ValueCallback<Map>() {
+            @Override
+            public void onReceiveValue(Map webStorageOrigins) {
+                if ((webStorageOrigins != null) && !webStorageOrigins.isEmpty()) {
+                    websiteSettings.setEnabled(true);
+                }
+            }
+        });
+        GeolocationPermissions.getInstance().getOrigins(new ValueCallback<Set<String> >() {
+            @Override
+            public void onReceiveValue(Set<String> geolocationOrigins) {
+                if ((geolocationOrigins != null) && !geolocationOrigins.isEmpty()) {
+                    websiteSettings.setEnabled(true);
+                }
+            }
+        });
+    }
+
+    @Override
+    public boolean onPreferenceChange(Preference pref, Object objValue) {
+        if (pref.getKey().equals(BrowserSettings.PREF_EXTRAS_RESET_DEFAULTS)) {
+            Boolean value = (Boolean) objValue;
+            if (value.booleanValue() == true) {
+                getActivity().finish();
+                return true;
+            }
+        }
+        return false;
+    }
+}
\ No newline at end of file
diff --git a/src/com/android/browser/preferences/DebugPreferencesFragment.java b/src/com/android/browser/preferences/DebugPreferencesFragment.java
new file mode 100644
index 0000000..d643a97
--- /dev/null
+++ b/src/com/android/browser/preferences/DebugPreferencesFragment.java
@@ -0,0 +1,32 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.R;
+
+import android.os.Bundle;
+import android.preference.PreferenceFragment;
+
+public class DebugPreferencesFragment extends PreferenceFragment {
+    @Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+
+        // Load the XML preferences file
+        addPreferencesFromResource(R.xml.debug_preferences);
+    }
+}
diff --git a/src/com/android/browser/preferences/PageContentPreferencesFragment.java b/src/com/android/browser/preferences/PageContentPreferencesFragment.java
new file mode 100644
index 0000000..4bb2fab
--- /dev/null
+++ b/src/com/android/browser/preferences/PageContentPreferencesFragment.java
@@ -0,0 +1,143 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserHomepagePreference;
+import com.android.browser.BrowserPreferencesPage;
+import com.android.browser.BrowserSettings;
+import com.android.browser.R;
+
+import android.content.res.Resources;
+import android.net.Uri;
+import android.os.Bundle;
+import android.preference.EditTextPreference;
+import android.preference.Preference;
+import android.preference.PreferenceFragment;
+
+public class PageContentPreferencesFragment extends PreferenceFragment
+        implements Preference.OnPreferenceChangeListener {
+
+    @Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+
+        // Load the preferences from an XML resource
+        addPreferencesFromResource(R.xml.page_content_preferences);
+
+        Preference e = findPreference(BrowserSettings.PREF_HOMEPAGE);
+        e.setOnPreferenceChangeListener(this);
+        e.setSummary(getPreferenceScreen().getSharedPreferences()
+                .getString(BrowserSettings.PREF_HOMEPAGE, null));
+        ((BrowserHomepagePreference) e).setCurrentPage(
+                getActivity().getIntent().getStringExtra(BrowserPreferencesPage.CURRENT_PAGE));
+        
+        e = findPreference(BrowserSettings.PREF_TEXT_SIZE);
+        e.setOnPreferenceChangeListener(this);
+        e.setSummary(getVisualTextSizeName(
+                getPreferenceScreen().getSharedPreferences()
+                .getString(BrowserSettings.PREF_TEXT_SIZE, null)) );
+        
+        e = findPreference(BrowserSettings.PREF_DEFAULT_ZOOM);
+        e.setOnPreferenceChangeListener(this);
+        e.setSummary(getVisualDefaultZoomName(
+                getPreferenceScreen().getSharedPreferences()
+                .getString(BrowserSettings.PREF_DEFAULT_ZOOM, null)) );
+
+        e = findPreference(BrowserSettings.PREF_DEFAULT_TEXT_ENCODING);
+        e.setOnPreferenceChangeListener(this);
+    }
+
+    @Override
+    public boolean onPreferenceChange(Preference pref, Object objValue) {
+        if (pref.getKey().equals(BrowserSettings.PREF_HOMEPAGE)) {
+            String value = (String) objValue;
+            boolean needUpdate = value.indexOf(' ') != -1;
+            if (needUpdate) {
+                value = value.trim().replace(" ", "%20");
+            }
+            if (value.length() != 0 && Uri.parse(value).getScheme() == null) {
+                value = "http://" + value;
+                needUpdate = true;
+            }
+            // Set the summary value.
+            pref.setSummary(value);
+            if (needUpdate) {
+                // Update through the EditText control as it has a cached copy
+                // of the string and it will handle persisting the value
+                ((EditTextPreference) pref).setText(value);
+
+                // as we update the value above, we need to return false
+                // here so that setText() is not called by EditTextPref
+                // with the old value.
+                return false;
+            } else {
+                return true;
+            }
+        } else if (pref.getKey().equals(BrowserSettings.PREF_TEXT_SIZE)) {
+            pref.setSummary(getVisualTextSizeName((String) objValue));
+            return true;
+        } else if (pref.getKey().equals(BrowserSettings.PREF_DEFAULT_ZOOM)) {
+            pref.setSummary(getVisualDefaultZoomName((String) objValue));
+            return true;
+        } else if (pref.getKey().equals(BrowserSettings.PREF_DEFAULT_TEXT_ENCODING)) {
+            pref.setSummary((String) objValue);
+            return true;
+        }
+        
+        return false;
+    }
+
+    private CharSequence getVisualTextSizeName(String enumName) {
+        Resources res = getActivity().getResources();
+        CharSequence[] visualNames = res.getTextArray(R.array.pref_text_size_choices);
+        CharSequence[] enumNames = res.getTextArray(R.array.pref_text_size_values);
+
+        // Sanity check
+        if (visualNames.length != enumNames.length) {
+            return "";
+        }
+
+        int length = enumNames.length;
+        for (int i = 0; i < length; i++) {
+            if (enumNames[i].equals(enumName)) {
+                return visualNames[i];
+            }
+        }
+
+        return "";
+    }
+
+    private CharSequence getVisualDefaultZoomName(String enumName) {
+        Resources res = getActivity().getResources();
+        CharSequence[] visualNames = res.getTextArray(R.array.pref_default_zoom_choices);
+        CharSequence[] enumNames = res.getTextArray(R.array.pref_default_zoom_values);
+
+        // Sanity check
+        if (visualNames.length != enumNames.length) {
+            return "";
+        }
+
+        int length = enumNames.length;
+        for (int i = 0; i < length; i++) {
+            if (enumNames[i].equals(enumName)) {
+                return visualNames[i];
+            }
+        }
+
+        return "";
+    }
+}
\ No newline at end of file
diff --git a/src/com/android/browser/preferences/PersonalPreferencesFragment.java b/src/com/android/browser/preferences/PersonalPreferencesFragment.java
new file mode 100644
index 0000000..656d47a
--- /dev/null
+++ b/src/com/android/browser/preferences/PersonalPreferencesFragment.java
@@ -0,0 +1,355 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserBookmarksPage;
+import com.android.browser.BrowserSettings;
+import com.android.browser.R;
+
+import android.accounts.Account;
+import android.accounts.AccountManager;
+import android.app.AlertDialog;
+import android.app.Dialog;
+import android.app.DialogFragment;
+import android.app.Fragment;
+import android.content.ContentProviderOperation;
+import android.content.ContentResolver;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.OperationApplicationException;
+import android.content.SharedPreferences;
+import android.database.Cursor;
+import android.os.Bundle;
+import android.os.RemoteException;
+import android.preference.Preference;
+import android.preference.Preference.OnPreferenceClickListener;
+import android.preference.PreferenceFragment;
+import android.preference.PreferenceManager;
+import android.preference.PreferenceScreen;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Bookmarks;
+import android.provider.BrowserContract.ChromeSyncColumns;
+import android.util.Log;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.widget.Button;
+import android.widget.LinearLayout;
+
+import java.util.ArrayList;
+
+public class PersonalPreferencesFragment extends PreferenceFragment
+        implements OnPreferenceClickListener {
+    static final String TAG = "PersonalPreferencesFragment";
+
+    static final String PREF_CHROME_SYNC = "sync_with_chrome";
+
+    Preference mChromeSync;
+    boolean mEnabled;
+
+    @Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+
+        // Load the XML preferences file
+        addPreferencesFromResource(R.xml.personal_preferences);
+    }
+
+    @Override
+    public void onResume() {
+        super.onResume();
+
+        // Setup the proper state for the sync with chrome item
+        Context context = getActivity();
+        mChromeSync = findPreference(PREF_CHROME_SYNC);
+        refreshUi(context);
+    }
+
+    void refreshUi(Context context) {
+        AccountManager am = (AccountManager) context.getSystemService(Context.ACCOUNT_SERVICE);
+        Account[] accounts = am.getAccountsByType("com.google");
+        if (accounts == null || accounts.length == 0) {
+            // No Google accounts setup, don't offer Chrome sync
+            if (mChromeSync != null) {
+                getPreferenceScreen().removePreference(mChromeSync);
+            }
+        } else {
+            SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
+            Bundle args = mChromeSync.getExtras();
+            args.putParcelableArray("accounts", accounts);
+            mEnabled = BrowserContract.Settings.isSyncEnabled(context);
+            if (!mEnabled) {
+                // Google accounts are present, but Chrome sync isn't enabled yet.
+                // Setup a link to the enable wizard
+                mChromeSync.setSummary(R.string.pref_personal_sync_with_chrome_summary);
+            } else {
+                // Chrome sync is enabled, setup a link to account switcher
+                String accountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+                mChromeSync.setSummary(accountName);
+                args.putString("curAccount", accountName);
+            }
+            mChromeSync.setOnPreferenceClickListener(this);
+        }
+
+        PreferenceScreen autoFillSettings =
+                (PreferenceScreen)findPreference(BrowserSettings.PREF_AUTOFILL_PROFILE);
+        autoFillSettings.setDependency(BrowserSettings.PREF_AUTOFILL_ENABLED);
+    }
+
+    @Override
+    public boolean onPreferenceClick(Preference preference) {
+        Fragment frag;
+        if (mEnabled) {
+            frag = new AccountChooserDialog();
+        } else {
+            frag = new ImportWizardDialog();
+        }
+        frag.setArguments(preference.getExtras());
+        getFragmentManager().openTransaction()
+                .add(frag, null)
+                .commit();
+        return true;
+    }
+
+    final class AccountChooserDialog extends DialogFragment
+            implements DialogInterface.OnClickListener {
+
+        AlertDialog mDialog;
+
+        @Override
+        public Dialog onCreateDialog(Bundle savedInstanceState) {
+            Bundle args = getArguments();
+            Account[] accounts = (Account[]) args.getParcelableArray("accounts");
+            String curAccount = args.getString("curAccount");
+            int length = accounts.length;
+            int curAccountOffset = 0;
+            CharSequence[] accountNames = new CharSequence[length];
+            for (int i = 0; i < length; i++) {
+                String name = accounts[i].name;
+                if (name.equals(curAccount)) {
+                    curAccountOffset = i;
+                }
+                accountNames[i] = name;
+            }
+
+            mDialog = new AlertDialog.Builder(getActivity())
+                    .setIcon(android.R.drawable.ic_dialog_alert)
+                    .setTitle("Choose account") // STOPSHIP localize
+                    .setSingleChoiceItems(accountNames, curAccountOffset, this)
+                    .create();
+            return mDialog;
+        }
+
+        @Override
+        public void onClick(DialogInterface dialog, int which) {
+            String accountName = mDialog.getListView().getAdapter().getItem(which).toString();
+            SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
+            prefs.edit().putString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, accountName).apply();
+            refreshUi(getActivity());
+            dismiss();
+        }
+    }
+
+    final class ImportWizardDialog extends DialogFragment implements OnClickListener {
+        View mRemoveButton;
+        View mCancelButton;
+        String mDefaultAccount;
+
+        @Override
+        public Dialog onCreateDialog(Bundle savedInstanceState) {
+            Context context = getActivity();
+            Dialog dialog = new Dialog(context);
+            dialog.setTitle(R.string.import_bookmarks_dialog_title);
+            dialog.setContentView(R.layout.import_bookmarks_dialog);
+            mRemoveButton = dialog.findViewById(R.id.remove);
+            mRemoveButton.setOnClickListener(this);
+            mCancelButton = dialog.findViewById(R.id.cancel);
+            mCancelButton.setOnClickListener(this);
+
+            LayoutInflater inflater = dialog.getLayoutInflater();
+            LinearLayout accountList = (LinearLayout) dialog.findViewById(R.id.accountList);
+            Account[] accounts = (Account[]) getArguments().getParcelableArray("accounts");
+            mDefaultAccount = accounts[0].name;
+            int length = accounts.length;
+            for (int i = 0; i < length; i++) {
+                Button button = (Button) inflater.inflate(R.layout.import_bookmarks_dialog_button,
+                        null);
+                button.setText(context.getString(R.string.import_bookmarks_dialog_import,
+                        accounts[i].name));
+                button.setTag(accounts[i].name);
+                button.setOnClickListener(this);
+                accountList.addView(button);
+            }
+
+            return dialog;
+        }
+
+        @Override
+        public void onClick(View view) {
+            if (view == mCancelButton) {
+                dismiss();
+                return;
+            }
+
+            ContentResolver resolver = getActivity().getContentResolver();
+            SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
+            String accountName;
+            if (view == mRemoveButton) {
+                // The user chose to remove their old bookmarks, delete them now
+                resolver.delete(Bookmarks.CONTENT_URI,
+                        Bookmarks.PARENT + "=1 AND " + Bookmarks.ACCOUNT_NAME + " IS NULL", null);
+                accountName = mDefaultAccount;
+            } else {
+                // The user chose to migrate their old bookmarks to the account they're syncing
+                accountName = view.getTag().toString();
+                migrateBookmarks(resolver, accountName);
+            }
+
+            // Record the fact that we turned on sync
+            BrowserContract.Settings.setSyncEnabled(getActivity(), true);
+            prefs.edit()
+                    .putString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, "com.google")
+                    .putString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, accountName)
+                    .apply();
+
+            // Enable bookmark sync on all accounts
+            Account[] accounts = (Account[]) getArguments().getParcelableArray("accounts");
+            for (Account account : accounts) {
+                ContentResolver.setIsSyncable(account, BrowserContract.AUTHORITY, 1);
+            }
+
+            refreshUi(getActivity());
+            dismiss();
+        }
+
+        /**
+         * Migrates bookmarks to the given account
+         */
+        void migrateBookmarks(ContentResolver resolver, String accountName) {
+            Cursor cursor = null;
+            try {
+                // Re-parent the bookmarks in the default root folder
+                cursor = resolver.query(Bookmarks.CONTENT_URI, new String[] { Bookmarks._ID },
+                        Bookmarks.ACCOUNT_NAME + " =? AND " +
+                            ChromeSyncColumns.SERVER_UNIQUE + " =?",
+                        new String[] { accountName,
+                            ChromeSyncColumns.FOLDER_NAME_BOOKMARKS_BAR },
+                        null);
+                ContentValues values = new ContentValues();
+                if (cursor == null || !cursor.moveToFirst()) {
+                    // The root folders don't exist for the account, create them now
+                    ArrayList<ContentProviderOperation> ops =
+                            new ArrayList<ContentProviderOperation>();
+
+                    // Chrome sync root folder
+                    values.clear();
+                    values.put(ChromeSyncColumns.SERVER_UNIQUE, ChromeSyncColumns.FOLDER_NAME_ROOT);
+                    values.put(Bookmarks.TITLE, "Google Chrome");
+                    values.put(Bookmarks.POSITION, 0);
+                    values.put(Bookmarks.IS_FOLDER, true);
+                    values.put(Bookmarks.DIRTY, true);
+                    ops.add(ContentProviderOperation.newInsert(
+                            Bookmarks.CONTENT_URI.buildUpon().appendQueryParameter(
+                                    BrowserContract.CALLER_IS_SYNCADAPTER, "true").build())
+                            .withValues(values)
+                            .build());
+
+                    // Bookmarks folder
+                    values.clear();
+                    values.put(ChromeSyncColumns.SERVER_UNIQUE,
+                            ChromeSyncColumns.FOLDER_NAME_BOOKMARKS);
+                    values.put(Bookmarks.TITLE, "Bookmarks");
+                    values.put(Bookmarks.POSITION, 0);
+                    values.put(Bookmarks.IS_FOLDER, true);
+                    values.put(Bookmarks.DIRTY, true);
+                    ops.add(ContentProviderOperation.newInsert(Bookmarks.CONTENT_URI)
+                            .withValues(values)
+                            .withValueBackReference(Bookmarks.PARENT, 0)
+                            .build());
+
+                    // Bookmarks Bar folder
+                    values.clear();
+                    values.put(ChromeSyncColumns.SERVER_UNIQUE,
+                            ChromeSyncColumns.FOLDER_NAME_BOOKMARKS_BAR);
+                    values.put(Bookmarks.TITLE, "Bookmarks Bar");
+                    values.put(Bookmarks.POSITION, 0);
+                    values.put(Bookmarks.IS_FOLDER, true);
+                    values.put(Bookmarks.DIRTY, true);
+                    ops.add(ContentProviderOperation.newInsert(Bookmarks.CONTENT_URI)
+                            .withValues(values)
+                            .withValueBackReference(Bookmarks.PARENT, 1)
+                            .build());
+
+                    // Other Bookmarks folder
+                    values.clear();
+                    values.put(ChromeSyncColumns.SERVER_UNIQUE,
+                            ChromeSyncColumns.FOLDER_NAME_OTHER_BOOKMARKS);
+                    values.put(Bookmarks.TITLE, "Other Bookmarks");
+                    values.put(Bookmarks.POSITION, 1000);
+                    values.put(Bookmarks.IS_FOLDER, true);
+                    values.put(Bookmarks.DIRTY, true);
+                    ops.add(ContentProviderOperation.newInsert(Bookmarks.CONTENT_URI)
+                            .withValues(values)
+                            .withValueBackReference(Bookmarks.PARENT, 1)
+                            .build());
+
+                    // Re-parent the existing bookmarks to the newly create bookmarks bar folder
+                    ops.add(ContentProviderOperation.newUpdate(Bookmarks.CONTENT_URI)
+                            .withValueBackReference(Bookmarks.PARENT, 2)
+                            .withSelection(Bookmarks.PARENT + "=?",
+                                        new String[] { Integer.toString(1) })
+                            .build());
+
+                    // Mark all non-root folder items as belonging to the new account
+                    values.clear();
+                    values.put(Bookmarks.ACCOUNT_TYPE, "com.google");
+                    values.put(Bookmarks.ACCOUNT_NAME, accountName);
+                    ops.add(ContentProviderOperation.newUpdate(Bookmarks.CONTENT_URI)
+                            .withValues(values)
+                            .withSelection(Bookmarks.ACCOUNT_NAME + " IS NULL AND " +
+                                    Bookmarks._ID + "<>1", null)
+                            .build());
+                    
+                    try {
+                        resolver.applyBatch(BrowserContract.AUTHORITY, ops);
+                    } catch (RemoteException e) {
+                        Log.e(TAG, "failed to create root folder for account " + accountName, e);
+                        return;
+                    } catch (OperationApplicationException e) {
+                        Log.e(TAG, "failed to create root folder for account " + accountName, e);
+                        return;
+                    }
+                } else {
+                    values.put(Bookmarks.PARENT, cursor.getLong(0));
+                    resolver.update(Bookmarks.CONTENT_URI, values, Bookmarks.PARENT + "=?",
+                            new String[] { Integer.toString(1) });
+
+                    // Mark all bookmarks at all levels as part of the new account
+                    values.clear();
+                    values.put(Bookmarks.ACCOUNT_TYPE, "com.google");
+                    values.put(Bookmarks.ACCOUNT_NAME, accountName);
+                    resolver.update(Bookmarks.CONTENT_URI, values,
+                            Bookmarks.ACCOUNT_NAME + " IS NULL AND " + Bookmarks._ID + "<>1",
+                            null);
+                }
+            } finally {
+                if (cursor != null) cursor.close();
+            }
+        }
+    }
+}
diff --git a/src/com/android/browser/preferences/PrivacyPreferencesFragment.java b/src/com/android/browser/preferences/PrivacyPreferencesFragment.java
new file mode 100644
index 0000000..79f2084
--- /dev/null
+++ b/src/com/android/browser/preferences/PrivacyPreferencesFragment.java
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserSettings;
+import com.android.browser.R;
+
+import android.app.Activity;
+import android.content.Intent;
+import android.os.Bundle;
+import android.preference.Preference;
+import android.preference.PreferenceFragment;
+
+public class PrivacyPreferencesFragment extends PreferenceFragment
+        implements Preference.OnPreferenceChangeListener {
+
+    @Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+
+        // Load the preferences from an XML resource
+        addPreferencesFromResource(R.xml.privacy_preferences);
+
+        Preference e = findPreference(BrowserSettings.PREF_CLEAR_HISTORY);
+        e.setOnPreferenceChangeListener(this);
+    }
+
+    @Override
+    public boolean onPreferenceChange(Preference pref, Object objValue) {
+        if (pref.getKey().equals(BrowserSettings.PREF_CLEAR_HISTORY)
+                && ((Boolean) objValue).booleanValue() == true) {
+            // Need to tell the browser to remove the parent/child relationship
+            // between tabs
+            getActivity().setResult(Activity.RESULT_OK, (new Intent()).putExtra(Intent.EXTRA_TEXT,
+                    pref.getKey()));
+            return true;
+        }
+        
+        return false;
+    }
+}
diff --git a/src/com/android/browser/preferences/SecurityPreferencesFragment.java b/src/com/android/browser/preferences/SecurityPreferencesFragment.java
new file mode 100644
index 0000000..d20a50c
--- /dev/null
+++ b/src/com/android/browser/preferences/SecurityPreferencesFragment.java
@@ -0,0 +1,32 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.R;
+
+import android.os.Bundle;
+import android.preference.PreferenceFragment;
+
+public class SecurityPreferencesFragment extends PreferenceFragment {
+    @Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+
+        // Load the XML preferences file
+        addPreferencesFromResource(R.xml.security_preferences);
+    }
+}
diff --git a/src/com/android/browser/provider/BrowserProvider2.java b/src/com/android/browser/provider/BrowserProvider2.java
new file mode 100644
index 0000000..c909d70
--- /dev/null
+++ b/src/com/android/browser/provider/BrowserProvider2.java
@@ -0,0 +1,1122 @@
+/*
+ * Copyright (C) 2010 he Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.provider;
+
+import com.android.browser.R;
+import com.android.common.content.SyncStateContentProviderHelper;
+
+import android.accounts.Account;
+import android.content.ContentResolver;
+import android.content.ContentUris;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.UriMatcher;
+import android.database.Cursor;
+import android.database.DatabaseUtils;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteOpenHelper;
+import android.database.sqlite.SQLiteQueryBuilder;
+import android.net.Uri;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Accounts;
+import android.provider.BrowserContract.Bookmarks;
+import android.provider.BrowserContract.ChromeSyncColumns;
+import android.provider.BrowserContract.Combined;
+import android.provider.BrowserContract.History;
+import android.provider.BrowserContract.Images;
+import android.provider.BrowserContract.Searches;
+import android.provider.BrowserContract.Settings;
+import android.provider.BrowserContract.SyncState;
+import android.provider.ContactsContract.RawContacts;
+import android.provider.SyncStateContract;
+import android.text.TextUtils;
+
+import java.util.HashMap;
+
+public class BrowserProvider2 extends SQLiteContentProvider {
+
+    static final String LEGACY_AUTHORITY = "browser";
+    static final Uri LEGACY_AUTHORITY_URI = new Uri.Builder().authority(LEGACY_AUTHORITY).build();
+
+    static final String TABLE_BOOKMARKS = "bookmarks";
+    static final String TABLE_HISTORY = "history";
+    static final String TABLE_IMAGES = "images";
+    static final String TABLE_SEARCHES = "searches";
+    static final String TABLE_SYNC_STATE = "syncstate";
+    static final String TABLE_SETTINGS = "settings";
+    static final String VIEW_COMBINED = "combined";
+
+    static final String TABLE_BOOKMARKS_JOIN_IMAGES = "bookmarks LEFT OUTER JOIN images " +
+            "ON bookmarks.url = images." + Images.URL;
+    static final String TABLE_HISTORY_JOIN_IMAGES = "history LEFT OUTER JOIN images " +
+            "ON history.url = images." + Images.URL;
+
+    static final String DEFAULT_SORT_HISTORY = History.DATE_LAST_VISITED + " DESC";
+
+    static final String DEFAULT_SORT_SEARCHES = Searches.DATE + " DESC";
+
+    static final int BOOKMARKS = 1000;
+    static final int BOOKMARKS_ID = 1001;
+    static final int BOOKMARKS_FOLDER = 1002;
+    static final int BOOKMARKS_FOLDER_ID = 1003;
+
+    static final int HISTORY = 2000;
+    static final int HISTORY_ID = 2001;
+
+    static final int SEARCHES = 3000;
+    static final int SEARCHES_ID = 3001;
+
+    static final int SYNCSTATE = 4000;
+    static final int SYNCSTATE_ID = 4001;
+
+    static final int IMAGES = 5000;
+
+    static final int COMBINED = 6000;
+    static final int COMBINED_ID = 6001;
+
+    static final int ACCOUNTS = 7000;
+
+    static final int SETTINGS = 8000;
+
+    public static final long FIXED_ID_ROOT = 1;
+
+    static final String DEFAULT_BOOKMARKS_SORT_ORDER = "position ASC, _id ASC";
+
+    static final UriMatcher URI_MATCHER = new UriMatcher(UriMatcher.NO_MATCH);
+
+    static final HashMap<String, String> ACCOUNTS_PROJECTION_MAP = new HashMap<String, String>();
+    static final HashMap<String, String> BOOKMARKS_PROJECTION_MAP = new HashMap<String, String>();
+    static final HashMap<String, String> OTHER_BOOKMARKS_PROJECTION_MAP =
+            new HashMap<String, String>();
+    static final HashMap<String, String> HISTORY_PROJECTION_MAP = new HashMap<String, String>();
+    static final HashMap<String, String> SYNC_STATE_PROJECTION_MAP = new HashMap<String, String>();
+    static final HashMap<String, String> IMAGES_PROJECTION_MAP = new HashMap<String, String>();
+    static final HashMap<String, String> COMBINED_PROJECTION_MAP = new HashMap<String, String>();
+    static final HashMap<String, String> SEARCHES_PROJECTION_MAP = new HashMap<String, String>();
+    static final HashMap<String, String> SETTINGS_PROJECTION_MAP = new HashMap<String, String>();
+
+    static {
+        final UriMatcher matcher = URI_MATCHER;
+        final String authority = BrowserContract.AUTHORITY;
+        matcher.addURI(authority, "accounts", ACCOUNTS);
+        matcher.addURI(authority, "bookmarks", BOOKMARKS);
+        matcher.addURI(authority, "bookmarks/#", BOOKMARKS_ID);
+        matcher.addURI(authority, "bookmarks/folder", BOOKMARKS_FOLDER);
+        matcher.addURI(authority, "bookmarks/folder/#", BOOKMARKS_FOLDER_ID);
+        matcher.addURI(authority, "history", HISTORY);
+        matcher.addURI(authority, "history/#", HISTORY_ID);
+        matcher.addURI(authority, "searches", SEARCHES);
+        matcher.addURI(authority, "searches/#", SEARCHES_ID);
+        matcher.addURI(authority, "syncstate", SYNCSTATE);
+        matcher.addURI(authority, "syncstate/#", SYNCSTATE_ID);
+        matcher.addURI(authority, "images", IMAGES);
+        matcher.addURI(authority, "combined", COMBINED);
+        matcher.addURI(authority, "combined/#", COMBINED_ID);
+        matcher.addURI(authority, "settings", SETTINGS);
+
+        // Projection maps
+        HashMap<String, String> map;
+
+        // Accounts
+        map = ACCOUNTS_PROJECTION_MAP;
+        map.put(Accounts.ACCOUNT_TYPE, Accounts.ACCOUNT_TYPE);
+        map.put(Accounts.ACCOUNT_NAME, Accounts.ACCOUNT_NAME);
+
+        // Bookmarks
+        map = BOOKMARKS_PROJECTION_MAP;
+        map.put(Bookmarks._ID, qualifyColumn(TABLE_BOOKMARKS, Bookmarks._ID));
+        map.put(Bookmarks.TITLE, Bookmarks.TITLE);
+        map.put(Bookmarks.URL, Bookmarks.URL);
+        map.put(Bookmarks.FAVICON, Bookmarks.FAVICON);
+        map.put(Bookmarks.THUMBNAIL, Bookmarks.THUMBNAIL);
+        map.put(Bookmarks.TOUCH_ICON, Bookmarks.TOUCH_ICON);
+        map.put(Bookmarks.IS_FOLDER, Bookmarks.IS_FOLDER);
+        map.put(Bookmarks.PARENT, Bookmarks.PARENT);
+        map.put(Bookmarks.POSITION, Bookmarks.POSITION);
+        map.put(Bookmarks.INSERT_AFTER, Bookmarks.INSERT_AFTER);
+        map.put(Bookmarks.IS_DELETED, Bookmarks.IS_DELETED);
+        map.put(Bookmarks.ACCOUNT_NAME, Bookmarks.ACCOUNT_NAME);
+        map.put(Bookmarks.ACCOUNT_TYPE, Bookmarks.ACCOUNT_TYPE);
+        map.put(Bookmarks.SOURCE_ID, Bookmarks.SOURCE_ID);
+        map.put(Bookmarks.VERSION, Bookmarks.VERSION);
+        map.put(Bookmarks.DATE_CREATED, Bookmarks.DATE_CREATED);
+        map.put(Bookmarks.DATE_MODIFIED, Bookmarks.DATE_MODIFIED);
+        map.put(Bookmarks.DIRTY, Bookmarks.DIRTY);
+        map.put(Bookmarks.SYNC1, Bookmarks.SYNC1);
+        map.put(Bookmarks.SYNC2, Bookmarks.SYNC2);
+        map.put(Bookmarks.SYNC3, Bookmarks.SYNC3);
+        map.put(Bookmarks.SYNC4, Bookmarks.SYNC4);
+        map.put(Bookmarks.SYNC5, Bookmarks.SYNC5);
+        map.put(Bookmarks.PARENT_SOURCE_ID, "(SELECT " + Bookmarks.SOURCE_ID +
+                " FROM " + TABLE_BOOKMARKS + " A WHERE " +
+                "A." + Bookmarks._ID + "=" + TABLE_BOOKMARKS + "." + Bookmarks.PARENT +
+                ") AS " + Bookmarks.PARENT_SOURCE_ID);
+        map.put(Bookmarks.INSERT_AFTER_SOURCE_ID, "(SELECT " + Bookmarks.SOURCE_ID +
+                " FROM " + TABLE_BOOKMARKS + " A WHERE " +
+                "A." + Bookmarks._ID + "=" + TABLE_BOOKMARKS + "." + Bookmarks.INSERT_AFTER +
+                ") AS " + Bookmarks.INSERT_AFTER_SOURCE_ID);
+
+        // Other bookmarks
+        OTHER_BOOKMARKS_PROJECTION_MAP.putAll(BOOKMARKS_PROJECTION_MAP);
+        OTHER_BOOKMARKS_PROJECTION_MAP.put(Bookmarks.POSITION,
+                Long.toString(Long.MAX_VALUE) + " AS " + Bookmarks.POSITION);
+
+        // History
+        map = HISTORY_PROJECTION_MAP;
+        map.put(History._ID, qualifyColumn(TABLE_HISTORY, History._ID));
+        map.put(History.TITLE, History.TITLE);
+        map.put(History.URL, History.URL);
+        map.put(History.FAVICON, History.FAVICON);
+        map.put(History.THUMBNAIL, History.THUMBNAIL);
+        map.put(History.TOUCH_ICON, History.TOUCH_ICON);
+        map.put(History.DATE_CREATED, History.DATE_CREATED);
+        map.put(History.DATE_LAST_VISITED, History.DATE_LAST_VISITED);
+        map.put(History.VISITS, History.VISITS);
+        map.put(History.USER_ENTERED, History.USER_ENTERED);
+
+        // Sync state
+        map = SYNC_STATE_PROJECTION_MAP;
+        map.put(SyncState._ID, SyncState._ID);
+        map.put(SyncState.ACCOUNT_NAME, SyncState.ACCOUNT_NAME);
+        map.put(SyncState.ACCOUNT_TYPE, SyncState.ACCOUNT_TYPE);
+        map.put(SyncState.DATA, SyncState.DATA);
+
+        // Images
+        map = IMAGES_PROJECTION_MAP;
+        map.put(Images.URL, Images.URL);
+        map.put(Images.FAVICON, Images.FAVICON);
+        map.put(Images.THUMBNAIL, Images.THUMBNAIL);
+        map.put(Images.TOUCH_ICON, Images.TOUCH_ICON);
+
+        // Combined history half
+        map = COMBINED_PROJECTION_MAP;
+        map.put(Combined._ID, Combined._ID);
+        map.put(Combined.TITLE, Combined.TITLE);
+        map.put(Combined.URL, Combined.URL);
+        map.put(Combined.DATE_CREATED, Combined.DATE_CREATED);
+        map.put(Combined.DATE_LAST_VISITED, Combined.DATE_LAST_VISITED);
+        map.put(Combined.IS_BOOKMARK, Combined.IS_BOOKMARK);
+        map.put(Combined.VISITS, Combined.VISITS);
+        map.put(Combined.FAVICON, Combined.FAVICON);
+        map.put(Combined.THUMBNAIL, Combined.THUMBNAIL);
+        map.put(Combined.TOUCH_ICON, Combined.TOUCH_ICON);
+        map.put(Combined.USER_ENTERED, Combined.USER_ENTERED);
+
+        // Searches
+        map = SEARCHES_PROJECTION_MAP;
+        map.put(Searches._ID, Searches._ID);
+        map.put(Searches.SEARCH, Searches.SEARCH);
+        map.put(Searches.DATE, Searches.DATE);
+
+        // Settings
+        map = SETTINGS_PROJECTION_MAP;
+        map.put(Settings.KEY, Settings.KEY);
+        map.put(Settings.VALUE, Settings.VALUE);
+    }
+
+    static final String bookmarkOrHistoryColumn(String column) {
+        return "CASE WHEN bookmarks." + column + " IS NOT NULL THEN " +
+                "bookmarks." + column + " ELSE history." + column + " END AS " + column;
+    }
+
+    static final String qualifyColumn(String table, String column) {
+        return table + "." + column + " AS " + column;
+    }
+
+    DatabaseHelper mOpenHelper;
+    SyncStateContentProviderHelper mSyncHelper = new SyncStateContentProviderHelper();
+
+    final class DatabaseHelper extends SQLiteOpenHelper {
+        static final String DATABASE_NAME = "browser2.db";
+        static final int DATABASE_VERSION = 25;
+        public DatabaseHelper(Context context) {
+            super(context, DATABASE_NAME, null, DATABASE_VERSION);
+        }
+
+        @Override
+        public void onCreate(SQLiteDatabase db) {
+            db.execSQL("CREATE TABLE " + TABLE_BOOKMARKS + "(" +
+                    Bookmarks._ID + " INTEGER PRIMARY KEY AUTOINCREMENT," +
+                    Bookmarks.TITLE + " TEXT," +
+                    Bookmarks.URL + " TEXT," +
+                    Bookmarks.IS_FOLDER + " INTEGER NOT NULL DEFAULT 0," +
+                    Bookmarks.PARENT + " INTEGER," +
+                    Bookmarks.POSITION + " INTEGER NOT NULL," +
+                    Bookmarks.INSERT_AFTER + " INTEGER," +
+                    Bookmarks.IS_DELETED + " INTEGER NOT NULL DEFAULT 0," +
+                    Bookmarks.ACCOUNT_NAME + " TEXT," +
+                    Bookmarks.ACCOUNT_TYPE + " TEXT," +
+                    Bookmarks.SOURCE_ID + " TEXT," +
+                    Bookmarks.VERSION + " INTEGER NOT NULL DEFAULT 1," +
+                    Bookmarks.DATE_CREATED + " INTEGER," +
+                    Bookmarks.DATE_MODIFIED + " INTEGER," +
+                    Bookmarks.DIRTY + " INTEGER NOT NULL DEFAULT 0," +
+                    Bookmarks.SYNC1 + " TEXT," +
+                    Bookmarks.SYNC2 + " TEXT," +
+                    Bookmarks.SYNC3 + " TEXT," +
+                    Bookmarks.SYNC4 + " TEXT," +
+                    Bookmarks.SYNC5 + " TEXT" +
+                    ");");
+
+            // TODO indices
+
+            createDefaultBookmarks(db);
+
+            db.execSQL("CREATE TABLE " + TABLE_HISTORY + "(" +
+                    History._ID + " INTEGER PRIMARY KEY AUTOINCREMENT," +
+                    History.TITLE + " TEXT," +
+                    History.URL + " TEXT NOT NULL," +
+                    History.DATE_CREATED + " INTEGER," +
+                    History.DATE_LAST_VISITED + " INTEGER," +
+                    History.VISITS + " INTEGER NOT NULL DEFAULT 0," +
+                    History.USER_ENTERED + " INTEGER" +
+                    ");");
+
+            db.execSQL("CREATE TABLE " + TABLE_IMAGES + " (" +
+                    Images.URL + " TEXT UNIQUE NOT NULL," +
+                    Images.FAVICON + " BLOB," +
+                    Images.THUMBNAIL + " BLOB," +
+                    Images.TOUCH_ICON + " BLOB" +
+                    ");");
+            db.execSQL("CREATE INDEX imagesUrlIndex ON " + TABLE_IMAGES +
+                    "(" + Images.URL + ")");
+
+            db.execSQL("CREATE TABLE " + TABLE_SEARCHES + " (" +
+                    Searches._ID + " INTEGER PRIMARY KEY AUTOINCREMENT," +
+                    Searches.SEARCH + " TEXT," +
+                    Searches.DATE + " LONG" +
+                    ");");
+
+            db.execSQL("CREATE TABLE " + TABLE_SETTINGS + " (" +
+                    Settings.KEY + " TEXT PRIMARY KEY," +
+                    Settings.VALUE + " TEXT NOT NULL" +
+                    ");");
+
+            db.execSQL("CREATE VIEW " + VIEW_COMBINED + " AS " +
+                "SELECT " +
+                    bookmarkOrHistoryColumn(Combined._ID) + ", " +
+                    bookmarkOrHistoryColumn(Combined.TITLE) + ", " +
+                    qualifyColumn(TABLE_HISTORY, Combined.URL) + ", " +
+                    qualifyColumn(TABLE_HISTORY, Combined.DATE_CREATED) + ", " +
+                    Combined.DATE_LAST_VISITED + ", " +
+                    "CASE WHEN bookmarks._id IS NOT NULL THEN 1 ELSE 0 END AS " + Combined.IS_BOOKMARK + ", " +
+                    Combined.VISITS + ", " +
+                    Combined.FAVICON + ", " +
+                    Combined.THUMBNAIL + ", " +
+                    Combined.TOUCH_ICON + ", " +
+                    "NULL AS " + Combined.USER_ENTERED + " "+
+                "FROM history LEFT OUTER JOIN bookmarks ON history.url = bookmarks.url LEFT OUTER JOIN images ON history.url = images.url_key " +
+
+                "UNION ALL " +
+
+                "SELECT " +
+                    Combined._ID + ", " +
+                    Combined.TITLE + ", " +
+                    Combined.URL + ", " +
+                    Combined.DATE_CREATED + ", " +
+                    "NULL AS " + Combined.DATE_LAST_VISITED + ", "+
+                    "1 AS " + Combined.IS_BOOKMARK + ", " +
+                    "0 AS " + Combined.VISITS + ", "+
+                    Combined.FAVICON + ", " +
+                    Combined.THUMBNAIL + ", " +
+                    Combined.TOUCH_ICON + ", " +
+                    "NULL AS " + Combined.USER_ENTERED + " "+
+                "FROM bookmarks LEFT OUTER JOIN images ON bookmarks.url = images.url_key WHERE url NOT IN (SELECT url FROM history)");
+
+            mSyncHelper.createDatabase(db);
+        }
+
+        @Override
+        public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
+            // TODO write upgrade logic
+            db.execSQL("DROP TABLE IF EXISTS " + TABLE_BOOKMARKS);
+            db.execSQL("DROP TABLE IF EXISTS " + TABLE_HISTORY);
+            db.execSQL("DROP TABLE IF EXISTS " + TABLE_SEARCHES);
+            db.execSQL("DROP TABLE IF EXISTS " + TABLE_IMAGES);
+            db.execSQL("DROP TABLE IF EXISTS " + TABLE_SETTINGS);
+            db.execSQL("DROP VIEW IF EXISTS " + VIEW_COMBINED);
+            mSyncHelper.onAccountsChanged(db, new Account[] {}); // remove all sync info
+            onCreate(db);
+        }
+
+        @Override
+        public void onOpen(SQLiteDatabase db) {
+            mSyncHelper.onDatabaseOpened(db);
+        }
+
+        private void createDefaultBookmarks(SQLiteDatabase db) {
+            ContentValues values = new ContentValues();
+            // TODO figure out how to deal with localization for the defaults
+
+            // Bookmarks folder
+            values.put(Bookmarks._ID, FIXED_ID_ROOT);
+            values.put(ChromeSyncColumns.SERVER_UNIQUE, ChromeSyncColumns.FOLDER_NAME_BOOKMARKS);
+            values.put(Bookmarks.TITLE, "Bookmarks");
+            values.putNull(Bookmarks.PARENT);
+            values.put(Bookmarks.POSITION, 0);
+            values.put(Bookmarks.IS_FOLDER, true);
+            values.put(Bookmarks.DIRTY, true);
+            db.insertOrThrow(TABLE_BOOKMARKS, null, values);
+
+            addDefaultBookmarks(db, FIXED_ID_ROOT);
+        }
+
+        private void addDefaultBookmarks(SQLiteDatabase db, long parentId) {
+            final CharSequence[] bookmarks = getContext().getResources().getTextArray(
+                    R.array.bookmarks);
+            int size = bookmarks.length;
+            try {
+                String parent = Long.toString(parentId);
+                String now = Long.toString(System.currentTimeMillis());
+                for (int i = 0; i < size; i = i + 2) {
+                    CharSequence bookmarkDestination = replaceSystemPropertyInString(getContext(),
+                            bookmarks[i + 1]);
+                    db.execSQL("INSERT INTO bookmarks (" +
+                            Bookmarks.TITLE + ", " +
+                            Bookmarks.URL + ", " +
+                            Bookmarks.IS_FOLDER + "," +
+                            Bookmarks.PARENT + "," +
+                            Bookmarks.POSITION + "," +
+                            Bookmarks.DATE_CREATED +
+                        ") VALUES (" +
+                            "'" + bookmarks[i] + "', " +
+                            "'" + bookmarkDestination + "', " +
+                            "0," +
+                            parent + "," +
+                            Integer.toString(i) + "," +
+                            now +
+                            ");");
+                }
+            } catch (ArrayIndexOutOfBoundsException e) {
+            }
+        }
+
+        // XXX: This is a major hack to remove our dependency on gsf constants and
+        // its content provider. http://b/issue?id=2425179
+        private String getClientId(ContentResolver cr) {
+            String ret = "android-google";
+            Cursor c = null;
+            try {
+                c = cr.query(Uri.parse("content://com.google.settings/partner"),
+                        new String[] { "value" }, "name='client_id'", null, null);
+                if (c != null && c.moveToNext()) {
+                    ret = c.getString(0);
+                }
+            } catch (RuntimeException ex) {
+                // fall through to return the default
+            } finally {
+                if (c != null) {
+                    c.close();
+                }
+            }
+            return ret;
+        }
+
+        private CharSequence replaceSystemPropertyInString(Context context, CharSequence srcString) {
+            StringBuffer sb = new StringBuffer();
+            int lastCharLoc = 0;
+
+            final String client_id = getClientId(context.getContentResolver());
+
+            for (int i = 0; i < srcString.length(); ++i) {
+                char c = srcString.charAt(i);
+                if (c == '{') {
+                    sb.append(srcString.subSequence(lastCharLoc, i));
+                    lastCharLoc = i;
+              inner:
+                    for (int j = i; j < srcString.length(); ++j) {
+                        char k = srcString.charAt(j);
+                        if (k == '}') {
+                            String propertyKeyValue = srcString.subSequence(i + 1, j).toString();
+                            if (propertyKeyValue.equals("CLIENT_ID")) {
+                                sb.append(client_id);
+                            } else {
+                                sb.append("unknown");
+                            }
+                            lastCharLoc = j + 1;
+                            i = j;
+                            break inner;
+                        }
+                    }
+                }
+            }
+            if (srcString.length() - lastCharLoc > 0) {
+                // Put on the tail, if there is one
+                sb.append(srcString.subSequence(lastCharLoc, srcString.length()));
+            }
+            return sb;
+        }
+    }
+
+    @Override
+    public SQLiteOpenHelper getDatabaseHelper(Context context) {
+        synchronized (this) {
+            if (mOpenHelper == null) {
+                mOpenHelper = new DatabaseHelper(context);
+            }
+            return mOpenHelper;
+        }
+    }
+
+    @Override
+    public boolean isCallerSyncAdapter(Uri uri) {
+        return uri.getBooleanQueryParameter(BrowserContract.CALLER_IS_SYNCADAPTER, false);
+    }
+
+    @Override
+    public void notifyChange(boolean callerIsSyncAdapter) {
+        ContentResolver resolver = getContext().getContentResolver();
+        resolver.notifyChange(BrowserContract.AUTHORITY_URI, null, !callerIsSyncAdapter);
+        resolver.notifyChange(LEGACY_AUTHORITY_URI, null, !callerIsSyncAdapter);
+    }
+
+    @Override
+    public String getType(Uri uri) {
+        final int match = URI_MATCHER.match(uri);
+        switch (match) {
+            case BOOKMARKS:
+                return Bookmarks.CONTENT_TYPE;
+            case BOOKMARKS_ID:
+                return Bookmarks.CONTENT_ITEM_TYPE;
+            case HISTORY:
+                return History.CONTENT_TYPE;
+            case HISTORY_ID:
+                return History.CONTENT_ITEM_TYPE;
+            case SEARCHES:
+                return Searches.CONTENT_TYPE;
+            case SEARCHES_ID:
+                return Searches.CONTENT_ITEM_TYPE;
+//            case SUGGEST:
+//                return SearchManager.SUGGEST_MIME_TYPE;
+        }
+        return null;
+    }
+
+    @Override
+    public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs,
+            String sortOrder) {
+        SQLiteDatabase db = mOpenHelper.getReadableDatabase();
+        final int match = URI_MATCHER.match(uri);
+        SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
+        String limit = uri.getQueryParameter(BrowserContract.PARAM_LIMIT);
+        switch (match) {
+            case ACCOUNTS: {
+                qb.setTables(TABLE_BOOKMARKS);
+                qb.setProjectionMap(ACCOUNTS_PROJECTION_MAP);
+                qb.setDistinct(true);
+                qb.appendWhere(Bookmarks.ACCOUNT_NAME + " IS NOT NULL");
+                break;
+            }
+
+            case BOOKMARKS_FOLDER_ID:
+            case BOOKMARKS_ID:
+            case BOOKMARKS: {
+                // Only show deleted bookmarks if requested to do so
+                if (!uri.getBooleanQueryParameter(Bookmarks.QUERY_PARAMETER_SHOW_DELETED, false)) {
+                    selection = DatabaseUtils.concatenateWhere(
+                            Bookmarks.IS_DELETED + "=0", selection);
+                }
+
+                if (match == BOOKMARKS_ID) {
+                    // Tack on the ID of the specific bookmark requested
+                    selection = DatabaseUtils.concatenateWhere(selection,
+                            TABLE_BOOKMARKS + "." + Bookmarks._ID + "=?");
+                    selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                            new String[] { Long.toString(ContentUris.parseId(uri)) });
+                } else if (match == BOOKMARKS_FOLDER_ID) {
+                    // Tack on the ID of the specific folder requested
+                    selection = DatabaseUtils.concatenateWhere(selection,
+                            TABLE_BOOKMARKS + "." + Bookmarks.PARENT + "=?");
+                    selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                            new String[] { Long.toString(ContentUris.parseId(uri)) });
+                }
+
+                // Look for account info
+                String accountType = uri.getQueryParameter(Bookmarks.PARAM_ACCOUNT_TYPE);
+                String accountName = uri.getQueryParameter(Bookmarks.PARAM_ACCOUNT_NAME);
+                if (!TextUtils.isEmpty(accountType) && !TextUtils.isEmpty(accountName)) {
+                    selection = DatabaseUtils.concatenateWhere(selection,
+                            Bookmarks.ACCOUNT_TYPE + "=? AND " + Bookmarks.ACCOUNT_NAME + "=? ");
+                    selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                            new String[] { accountType, accountName });
+                }
+
+                // Set a default sort order if one isn't specified
+                if (TextUtils.isEmpty(sortOrder)) {
+                    sortOrder = DEFAULT_BOOKMARKS_SORT_ORDER;
+                }
+
+                qb.setProjectionMap(BOOKMARKS_PROJECTION_MAP);
+                qb.setTables(TABLE_BOOKMARKS_JOIN_IMAGES);
+                break;
+            }
+
+            case BOOKMARKS_FOLDER: {
+                // Don't allow selections to be applied to the default folder
+                if (!TextUtils.isEmpty(selection) || selectionArgs != null) {
+                    throw new UnsupportedOperationException(
+                            "selections aren't supported on this URI");
+                }
+
+                // Look for an account
+                boolean useAccount = false;
+                String accountType = uri.getQueryParameter(Bookmarks.PARAM_ACCOUNT_TYPE);
+                String accountName = uri.getQueryParameter(Bookmarks.PARAM_ACCOUNT_NAME);
+                if (!TextUtils.isEmpty(accountType) && !TextUtils.isEmpty(accountName)) {
+                    useAccount = true;
+                }
+
+                qb.setTables(TABLE_BOOKMARKS_JOIN_IMAGES);
+                String[] args;
+                String query;
+                if (!useAccount) {
+                    qb.setProjectionMap(BOOKMARKS_PROJECTION_MAP);
+                    query = qb.buildQuery(projection,
+                            Bookmarks.PARENT + "=? AND " + Bookmarks.IS_DELETED + "=0",
+                            null, null, null, DEFAULT_BOOKMARKS_SORT_ORDER, null);
+
+                    args = new String[] { Long.toString(FIXED_ID_ROOT) };
+                } else {
+                    qb.setProjectionMap(BOOKMARKS_PROJECTION_MAP);
+                    String bookmarksBarQuery = qb.buildQuery(projection,
+                            Bookmarks.ACCOUNT_TYPE + "=? AND " + Bookmarks.ACCOUNT_NAME + "=? " +
+                                    "AND parent = " +
+                                        "(SELECT _id FROM " + TABLE_BOOKMARKS + " WHERE " +
+                                        ChromeSyncColumns.SERVER_UNIQUE + "=" +
+                                        "'" + ChromeSyncColumns.FOLDER_NAME_BOOKMARKS_BAR + "' " +
+                                        "AND account_type = ? AND account_name = ?) " +
+                                    "AND " + Bookmarks.IS_DELETED + "=0",
+                            null, null, null, null, null);
+
+                    qb.setProjectionMap(OTHER_BOOKMARKS_PROJECTION_MAP);
+                    String otherBookmarksQuery = qb.buildQuery(projection,
+                            Bookmarks.ACCOUNT_TYPE + "=? AND " + Bookmarks.ACCOUNT_NAME + "=?" +
+                                    " AND " + ChromeSyncColumns.SERVER_UNIQUE + "=?",
+                            null, null, null, null, null);
+
+                    query = qb.buildUnionQuery(
+                            new String[] { bookmarksBarQuery, otherBookmarksQuery },
+                            DEFAULT_BOOKMARKS_SORT_ORDER, limit);
+
+                    args = new String[] {
+                            accountType, accountName, accountType, accountName,
+                            accountType, accountName, ChromeSyncColumns.FOLDER_NAME_OTHER_BOOKMARKS,
+                            };
+                }
+
+                Cursor cursor = db.rawQuery(query, args);
+                if (cursor != null) {
+                    cursor.setNotificationUri(getContext().getContentResolver(),
+                            BrowserContract.AUTHORITY_URI);
+                }
+                return cursor;
+            }
+
+            case HISTORY_ID: {
+                selection = DatabaseUtils.concatenateWhere(selection, TABLE_HISTORY + "._id=?");
+                selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                        new String[] { Long.toString(ContentUris.parseId(uri)) });
+                // fall through
+            }
+            case HISTORY: {
+                if (sortOrder == null) {
+                    sortOrder = DEFAULT_SORT_HISTORY;
+                }
+                qb.setProjectionMap(HISTORY_PROJECTION_MAP);
+                qb.setTables(TABLE_HISTORY_JOIN_IMAGES);
+                break;
+            }
+
+            case SEARCHES_ID: {
+                selection = DatabaseUtils.concatenateWhere(selection, TABLE_SEARCHES + "._id=?");
+                selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                        new String[] { Long.toString(ContentUris.parseId(uri)) });
+                // fall through
+            }
+            case SEARCHES: {
+                if (sortOrder == null) {
+                    sortOrder = DEFAULT_SORT_SEARCHES;
+                }
+                qb.setTables(TABLE_SEARCHES);
+                qb.setProjectionMap(SEARCHES_PROJECTION_MAP);
+                break;
+            }
+
+            case SYNCSTATE: {
+                return mSyncHelper.query(db, projection, selection, selectionArgs, sortOrder);
+            }
+
+            case SYNCSTATE_ID: {
+                selection = appendAccountToSelection(uri, selection);
+                String selectionWithId =
+                        (SyncStateContract.Columns._ID + "=" + ContentUris.parseId(uri) + " ")
+                        + (selection == null ? "" : " AND (" + selection + ")");
+                return mSyncHelper.query(db, projection, selectionWithId, selectionArgs, sortOrder);
+            }
+
+            case IMAGES: {
+                qb.setTables(TABLE_IMAGES);
+                qb.setProjectionMap(IMAGES_PROJECTION_MAP);
+                break;
+            }
+
+            case COMBINED_ID: {
+                selection = DatabaseUtils.concatenateWhere(selection, VIEW_COMBINED + "._id=?");
+                selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                        new String[] { Long.toString(ContentUris.parseId(uri)) });
+                // fall through
+            }
+            case COMBINED: {
+                qb.setTables(VIEW_COMBINED);
+                qb.setProjectionMap(COMBINED_PROJECTION_MAP);
+                break;
+            }
+
+            case SETTINGS: {
+                qb.setTables(TABLE_SETTINGS);
+                qb.setProjectionMap(SETTINGS_PROJECTION_MAP);
+                break;
+            }
+
+            default: {
+                throw new UnsupportedOperationException("Unknown URL " + uri.toString());
+            }
+        }
+
+        Cursor cursor = qb.query(db, projection, selection, selectionArgs, null, null, sortOrder,
+                limit);
+        cursor.setNotificationUri(getContext().getContentResolver(), BrowserContract.AUTHORITY_URI);
+        return cursor;
+    }
+
+    @Override
+    public int deleteInTransaction(Uri uri, String selection, String[] selectionArgs,
+            boolean callerIsSyncAdapter) {
+        final int match = URI_MATCHER.match(uri);
+        final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+        switch (match) {
+            case BOOKMARKS_ID:
+            case BOOKMARKS: {
+                //TODO cascade deletes down from folders
+                if (!callerIsSyncAdapter) {
+                    // If the caller isn't a sync adapter just go through and update all the
+                    // bookmarks to have the deleted flag set.
+                    ContentValues values = new ContentValues();
+                    values.put(Bookmarks.DATE_MODIFIED, System.currentTimeMillis());
+                    values.put(Bookmarks.IS_DELETED, 1);
+                    return updateInTransaction(uri, values, selection, selectionArgs,
+                            callerIsSyncAdapter);
+                } else {
+                    // Sync adapters are allowed to actually delete things
+                    if (match == BOOKMARKS_ID) {
+                        selection = DatabaseUtils.concatenateWhere(selection,
+                                TABLE_BOOKMARKS + "._id=?");
+                        selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                                new String[] { Long.toString(ContentUris.parseId(uri)) });
+                    }
+                    return db.delete(TABLE_BOOKMARKS, selection, selectionArgs);
+                }
+            }
+
+            case HISTORY_ID: {
+                selection = DatabaseUtils.concatenateWhere(selection, TABLE_HISTORY + "._id=?");
+                selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                        new String[] { Long.toString(ContentUris.parseId(uri)) });
+                // fall through
+            }
+            case HISTORY: {
+                return db.delete(TABLE_HISTORY, selection, selectionArgs);
+            }
+
+            case SEARCHES_ID: {
+                selection = DatabaseUtils.concatenateWhere(selection, TABLE_SEARCHES + "._id=?");
+                selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                        new String[] { Long.toString(ContentUris.parseId(uri)) });
+                // fall through
+            }
+            case SEARCHES: {
+                return db.delete(TABLE_SEARCHES, selection, selectionArgs);
+            }
+
+            case SYNCSTATE: {
+                return mSyncHelper.delete(db, selection, selectionArgs);
+            }
+            case SYNCSTATE_ID: {
+                String selectionWithId =
+                        (SyncStateContract.Columns._ID + "=" + ContentUris.parseId(uri) + " ")
+                        + (selection == null ? "" : " AND (" + selection + ")");
+                return mSyncHelper.delete(db, selectionWithId, selectionArgs);
+            }
+        }
+        throw new UnsupportedOperationException("Unknown update URI " + uri);
+    }
+
+    @Override
+    public Uri insertInTransaction(Uri uri, ContentValues values, boolean callerIsSyncAdapter) {
+        final int match = URI_MATCHER.match(uri);
+        final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+        long id = -1;
+        switch (match) {
+            case BOOKMARKS: {
+                // Mark rows dirty if they're not coming from a sync adapter
+                if (!callerIsSyncAdapter) {
+                    long now = System.currentTimeMillis();
+                    values.put(Bookmarks.DATE_CREATED, now);
+                    values.put(Bookmarks.DATE_MODIFIED, now);
+                    values.put(Bookmarks.DIRTY, 1);
+
+                    // If no parent is set default to the "Bookmarks Bar" folder
+                    // TODO set the parent based on the account info
+                    if (!values.containsKey(Bookmarks.PARENT)) {
+                        values.put(Bookmarks.PARENT, FIXED_ID_ROOT);
+                    }
+                }
+
+                // If no position is requested put the bookmark at the beginning of the list
+                if (!values.containsKey(Bookmarks.POSITION)) {
+                    values.put(Bookmarks.POSITION, Long.toString(Long.MIN_VALUE));
+                }
+
+                // Extract out the image values so they can be inserted into the images table
+                String url = values.getAsString(Bookmarks.URL);
+                ContentValues imageValues = extractImageValues(values, url);
+                Boolean isFolder = values.getAsBoolean(Bookmarks.IS_FOLDER);
+                if ((isFolder == null || !isFolder)
+                        && imageValues != null && !TextUtils.isEmpty(url)) {
+                    int count = db.update(TABLE_IMAGES, imageValues, Images.URL + "=?",
+                            new String[] { url });
+                    if (count == 0) {
+                        db.insertOrThrow(TABLE_IMAGES, Images.FAVICON, imageValues);
+                    }
+                }
+
+                id = db.insertOrThrow(TABLE_BOOKMARKS, Bookmarks.DIRTY, values);
+                break;
+            }
+
+            case HISTORY: {
+                // If no created time is specified set it to now
+                if (!values.containsKey(History.DATE_CREATED)) {
+                    values.put(History.DATE_CREATED, System.currentTimeMillis());
+                }
+
+                // Extract out the image values so they can be inserted into the images table
+                ContentValues imageValues = extractImageValues(values,
+                        values.getAsString(History.URL));
+                if (imageValues != null) {
+                    db.insertOrThrow(TABLE_IMAGES, Images.FAVICON, imageValues);
+                }
+
+                id = db.insertOrThrow(TABLE_HISTORY, History.VISITS, values);
+                break;
+            }
+
+            case SEARCHES: {
+                id = insertSearchesInTransaction(db, values);
+                break;
+            }
+
+            case SYNCSTATE: {
+                id = mSyncHelper.insert(db, values);
+                break;
+            }
+
+            case SETTINGS: {
+                id = 0;
+                insertSettingsInTransaction(db, values);
+                break;
+            }
+            
+            default: {
+                throw new UnsupportedOperationException("Unknown insert URI " + uri);
+            }
+        }
+
+        if (id >= 0) {
+            return ContentUris.withAppendedId(uri, id);
+        } else {
+            return null;
+        }
+    }
+
+    /**
+     * Searches are unique, so perform an UPSERT manually since SQLite doesn't support them.
+     */
+    private long insertSearchesInTransaction(SQLiteDatabase db, ContentValues values) {
+        String search = values.getAsString(Searches.SEARCH);
+        if (TextUtils.isEmpty(search)) {
+            throw new IllegalArgumentException("Must include the SEARCH field");
+        }
+        Cursor cursor = null;
+        try {
+            cursor = db.query(TABLE_SEARCHES, new String[] { Searches._ID },
+                    Searches.SEARCH + "=?", new String[] { search }, null, null, null);
+            if (cursor.moveToNext()) {
+                long id = cursor.getLong(0);
+                db.update(TABLE_SEARCHES, values, Searches._ID + "=?",
+                        new String[] { Long.toString(id) });
+                return id;
+            } else {
+                return db.insertOrThrow(TABLE_SEARCHES, Searches.SEARCH, values);
+            }
+        } finally {
+            if (cursor != null) cursor.close();
+        }
+    }
+
+    /**
+     * Settings are unique, so perform an UPSERT manually since SQLite doesn't support them.
+     */
+    private long insertSettingsInTransaction(SQLiteDatabase db, ContentValues values) {
+        String key = values.getAsString(Settings.KEY);
+        if (TextUtils.isEmpty(key)) {
+            throw new IllegalArgumentException("Must include the KEY field");
+        }
+        String[] keyArray = new String[] { key };
+        Cursor cursor = null;
+        try {
+            cursor = db.query(TABLE_SETTINGS, new String[] { Settings.KEY },
+                    Settings.KEY + "=?", keyArray, null, null, null);
+            if (cursor.moveToNext()) {
+                long id = cursor.getLong(0);
+                db.update(TABLE_SETTINGS, values, Settings.KEY + "=?", keyArray);
+                return id;
+            } else {
+                return db.insertOrThrow(TABLE_SETTINGS, Settings.VALUE, values);
+            }
+        } finally {
+            if (cursor != null) cursor.close();
+        }
+    }
+
+    @Override
+    public int updateInTransaction(Uri uri, ContentValues values, String selection,
+            String[] selectionArgs, boolean callerIsSyncAdapter) {
+        final int match = URI_MATCHER.match(uri);
+        final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+        switch (match) {
+            case BOOKMARKS_ID: {
+                selection = DatabaseUtils.concatenateWhere(selection,
+                        TABLE_BOOKMARKS + "._id=?");
+                selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                        new String[] { Long.toString(ContentUris.parseId(uri)) });
+                // fall through
+            }
+            case BOOKMARKS: {
+                return updateBookmarksInTransaction(values, selection, selectionArgs,
+                        callerIsSyncAdapter);
+            }
+
+            case HISTORY_ID: {
+                selection = DatabaseUtils.concatenateWhere(selection, TABLE_HISTORY + "._id=?");
+                selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+                        new String[] { Long.toString(ContentUris.parseId(uri)) });
+                // fall through
+            }
+            case HISTORY: {
+                return updateHistoryInTransaction(values, selection, selectionArgs);
+            }
+
+            case SYNCSTATE: {
+                return mSyncHelper.update(mDb, values,
+                        appendAccountToSelection(uri, selection), selectionArgs);
+            }
+
+            case SYNCSTATE_ID: {
+                selection = appendAccountToSelection(uri, selection);
+                String selectionWithId =
+                        (SyncStateContract.Columns._ID + "=" + ContentUris.parseId(uri) + " ")
+                        + (selection == null ? "" : " AND (" + selection + ")");
+                return mSyncHelper.update(mDb, values,
+                        selectionWithId, selectionArgs);
+            }
+
+            case IMAGES: {
+                String url = values.getAsString(Images.URL);
+                if (TextUtils.isEmpty(url)) {
+                    throw new IllegalArgumentException("Images.URL is required");
+                }
+                int count = db.update(TABLE_IMAGES, values, Images.URL + "=?",
+                        new String[] { url });
+                if (count == 0) {
+                    db.insertOrThrow(TABLE_IMAGES, Images.FAVICON, values);
+                    count = 1;
+                }
+                return count;
+            }
+        }
+        throw new UnsupportedOperationException("Unknown update URI " + uri);
+    }
+
+    /**
+     * Does a query to find the matching bookmarks and updates each one with the provided values.
+     */
+    int updateBookmarksInTransaction(ContentValues values, String selection,
+            String[] selectionArgs, boolean callerIsSyncAdapter) {
+        int count = 0;
+        final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+        Cursor cursor = query(Bookmarks.CONTENT_URI,
+                new String[] { Bookmarks._ID, Bookmarks.VERSION, Bookmarks.URL },
+                selection, selectionArgs, null);
+        try {
+            String[] args = new String[1];
+            // Mark the bookmark dirty if the caller isn't a sync adapter
+            if (!callerIsSyncAdapter) {
+                values.put(Bookmarks.DATE_MODIFIED, System.currentTimeMillis());
+                values.put(Bookmarks.DIRTY, 1);
+            }
+
+            boolean updatingUrl = values.containsKey(Bookmarks.URL);
+            String url = null;
+            if (updatingUrl) {
+                url = values.getAsString(Bookmarks.URL);
+            }
+            ContentValues imageValues = extractImageValues(values, url);
+
+            while (cursor.moveToNext()) {
+                args[0] = cursor.getString(0);
+                if (!callerIsSyncAdapter) {
+                    // increase the local version for non-sync changes
+                    values.put(Bookmarks.VERSION, cursor.getLong(1) + 1);
+                }
+                count += db.update(TABLE_BOOKMARKS, values, "_id=?", args);
+
+                // Update the images over in their table
+                if (imageValues != null) {
+                    if (!updatingUrl) {
+                        url = cursor.getString(2);
+                        imageValues.put(Images.URL, url);
+                    }
+
+                    if (!TextUtils.isEmpty(url)) {
+                        args[0] = url;
+                        if (db.update(TABLE_IMAGES, imageValues, Images.URL + "=?", args) == 0) {
+                            db.insert(TABLE_IMAGES, Images.FAVICON, imageValues);
+                        }
+                    }
+                }
+            }
+        } finally {
+            if (cursor != null) cursor.close();
+        }
+        return count;
+    }
+
+    /**
+     * Does a query to find the matching bookmarks and updates each one with the provided values.
+     */
+    int updateHistoryInTransaction(ContentValues values, String selection, String[] selectionArgs) {
+        int count = 0;
+        final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+        Cursor cursor = query(History.CONTENT_URI,
+                new String[] { History._ID, History.URL },
+                selection, selectionArgs, null);
+        try {
+            String[] args = new String[1];
+
+            boolean updatingUrl = values.containsKey(History.URL);
+            String url = null;
+            if (updatingUrl) {
+                url = values.getAsString(History.URL);
+            }
+            ContentValues imageValues = extractImageValues(values, url);
+
+            while (cursor.moveToNext()) {
+                args[0] = cursor.getString(0);
+                count += db.update(TABLE_HISTORY, values, "_id=?", args);
+
+                // Update the images over in their table
+                if (imageValues != null) {
+                    if (!updatingUrl) {
+                        url = cursor.getString(1);
+                        imageValues.put(Images.URL, url);
+                    }
+                    args[0] = url;
+                    if (db.update(TABLE_IMAGES, imageValues, Images.URL + "=?", args) == 0) {
+                        db.insert(TABLE_IMAGES, Images.FAVICON, imageValues);
+                    }
+                }
+            }
+        } finally {
+            if (cursor != null) cursor.close();
+        }
+        return count;
+    }
+
+    String appendAccountToSelection(Uri uri, String selection) {
+        final String accountName = uri.getQueryParameter(RawContacts.ACCOUNT_NAME);
+        final String accountType = uri.getQueryParameter(RawContacts.ACCOUNT_TYPE);
+
+        final boolean partialUri = TextUtils.isEmpty(accountName) ^ TextUtils.isEmpty(accountType);
+        if (partialUri) {
+            // Throw when either account is incomplete
+            throw new IllegalArgumentException(
+                    "Must specify both or neither of ACCOUNT_NAME and ACCOUNT_TYPE for " + uri);
+        }
+
+        // Accounts are valid by only checking one parameter, since we've
+        // already ruled out partial accounts.
+        final boolean validAccount = !TextUtils.isEmpty(accountName);
+        if (validAccount) {
+            StringBuilder selectionSb = new StringBuilder(RawContacts.ACCOUNT_NAME + "="
+                    + DatabaseUtils.sqlEscapeString(accountName) + " AND "
+                    + RawContacts.ACCOUNT_TYPE + "="
+                    + DatabaseUtils.sqlEscapeString(accountType));
+            if (!TextUtils.isEmpty(selection)) {
+                selectionSb.append(" AND (");
+                selectionSb.append(selection);
+                selectionSb.append(')');
+            }
+            return selectionSb.toString();
+        } else {
+            return selection;
+        }
+    }
+
+    ContentValues extractImageValues(ContentValues values, String url) {
+        ContentValues imageValues = null;
+        // favicon
+        if (values.containsKey(Bookmarks.FAVICON)) {
+            imageValues = new ContentValues();
+            imageValues.put(Images.FAVICON, values.getAsByteArray(Bookmarks.FAVICON));
+            values.remove(Bookmarks.FAVICON);
+        }
+
+        // thumbnail
+        if (values.containsKey(Bookmarks.THUMBNAIL)) {
+            if (imageValues == null) {
+                imageValues = new ContentValues();
+            }
+            imageValues.put(Images.THUMBNAIL, values.getAsByteArray(Bookmarks.THUMBNAIL));
+            values.remove(Bookmarks.THUMBNAIL);
+        }
+
+        // touch icon
+        if (values.containsKey(Bookmarks.TOUCH_ICON)) {
+            if (imageValues == null) {
+                imageValues = new ContentValues();
+            }
+            imageValues.put(Images.TOUCH_ICON, values.getAsByteArray(Bookmarks.TOUCH_ICON));
+            values.remove(Bookmarks.TOUCH_ICON);
+        }
+
+        if (imageValues != null) {
+            imageValues.put(Images.URL,  url);
+        }
+        return imageValues;
+    }
+}
diff --git a/src/com/android/browser/provider/SQLiteContentProvider.java b/src/com/android/browser/provider/SQLiteContentProvider.java
new file mode 100644
index 0000000..a50894a
--- /dev/null
+++ b/src/com/android/browser/provider/SQLiteContentProvider.java
@@ -0,0 +1,276 @@
+/*
+ * Copyright (C) 2009 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.provider;
+
+import android.content.ContentProvider;
+import android.content.ContentProviderOperation;
+import android.content.ContentProviderResult;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.OperationApplicationException;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteOpenHelper;
+import android.database.sqlite.SQLiteTransactionListener;
+import android.net.Uri;
+
+import java.util.ArrayList;
+
+/**
+ * General purpose {@link ContentProvider} base class that uses SQLiteDatabase for storage.
+ */
+public abstract class SQLiteContentProvider extends ContentProvider
+        implements SQLiteTransactionListener {
+
+    private static final String TAG = "SQLiteContentProvider";
+
+    private SQLiteOpenHelper mOpenHelper;
+    private volatile boolean mNotifyChange;
+    protected SQLiteDatabase mDb;
+
+    private final ThreadLocal<Boolean> mApplyingBatch = new ThreadLocal<Boolean>();
+    private static final int SLEEP_AFTER_YIELD_DELAY = 4000;
+
+    /**
+     * Maximum number of operations allowed in a batch between yield points.
+     */
+    private static final int MAX_OPERATIONS_PER_YIELD_POINT = 500;
+
+    @Override
+    public boolean onCreate() {
+        Context context = getContext();
+        mOpenHelper = getDatabaseHelper(context);
+        return true;
+    }
+
+    /**
+     * Returns a {@link SQLiteOpenHelper} that can open the database.
+     */
+    public abstract SQLiteOpenHelper getDatabaseHelper(Context context);
+
+    /**
+     * The equivalent of the {@link #insert} method, but invoked within a transaction.
+     */
+    public abstract Uri insertInTransaction(Uri uri, ContentValues values,
+            boolean callerIsSyncAdapter);
+
+    /**
+     * The equivalent of the {@link #update} method, but invoked within a transaction.
+     */
+    public abstract int updateInTransaction(Uri uri, ContentValues values, String selection,
+            String[] selectionArgs, boolean callerIsSyncAdapter);
+
+    /**
+     * The equivalent of the {@link #delete} method, but invoked within a transaction.
+     */
+    public abstract int deleteInTransaction(Uri uri, String selection, String[] selectionArgs,
+            boolean callerIsSyncAdapter);
+
+    /**
+     * Called when the provider needs to notify the system of a change.
+     * @param callerIsSyncAdapter true if the caller that caused the change was a sync adapter.
+     */
+    public abstract void notifyChange(boolean callerIsSyncAdapter);
+
+    public boolean isCallerSyncAdapter(Uri uri) {
+        return false;
+    }
+
+    public SQLiteOpenHelper getDatabaseHelper() {
+        return mOpenHelper;
+    }
+
+    private boolean applyingBatch() {
+        return mApplyingBatch.get() != null && mApplyingBatch.get();
+    }
+
+    @Override
+    public Uri insert(Uri uri, ContentValues values) {
+        Uri result = null;
+        boolean callerIsSyncAdapter = isCallerSyncAdapter(uri);
+        boolean applyingBatch = applyingBatch();
+        if (!applyingBatch) {
+            mDb = mOpenHelper.getWritableDatabase();
+            mDb.beginTransactionWithListener(this);
+            try {
+                result = insertInTransaction(uri, values, callerIsSyncAdapter);
+                if (result != null) {
+                    mNotifyChange = true;
+                }
+                mDb.setTransactionSuccessful();
+            } finally {
+                mDb.endTransaction();
+            }
+
+            onEndTransaction(callerIsSyncAdapter);
+        } else {
+            result = insertInTransaction(uri, values, callerIsSyncAdapter);
+            if (result != null) {
+                mNotifyChange = true;
+            }
+        }
+        return result;
+    }
+
+    @Override
+    public int bulkInsert(Uri uri, ContentValues[] values) {
+        int numValues = values.length;
+        boolean callerIsSyncAdapter = isCallerSyncAdapter(uri);
+        mDb = mOpenHelper.getWritableDatabase();
+        mDb.beginTransactionWithListener(this);
+        try {
+            for (int i = 0; i < numValues; i++) {
+                Uri result = insertInTransaction(uri, values[i], callerIsSyncAdapter);
+                if (result != null) {
+                    mNotifyChange = true;
+                }
+                mDb.yieldIfContendedSafely();
+            }
+            mDb.setTransactionSuccessful();
+        } finally {
+            mDb.endTransaction();
+        }
+
+        onEndTransaction(callerIsSyncAdapter);
+        return numValues;
+    }
+
+    @Override
+    public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {
+        int count = 0;
+        boolean callerIsSyncAdapter = isCallerSyncAdapter(uri);
+        boolean applyingBatch = applyingBatch();
+        if (!applyingBatch) {
+            mDb = mOpenHelper.getWritableDatabase();
+            mDb.beginTransactionWithListener(this);
+            try {
+                count = updateInTransaction(uri, values, selection, selectionArgs,
+                        callerIsSyncAdapter);
+                if (count > 0) {
+                    mNotifyChange = true;
+                }
+                mDb.setTransactionSuccessful();
+            } finally {
+                mDb.endTransaction();
+            }
+
+            onEndTransaction(callerIsSyncAdapter);
+        } else {
+            count = updateInTransaction(uri, values, selection, selectionArgs, callerIsSyncAdapter);
+            if (count > 0) {
+                mNotifyChange = true;
+            }
+        }
+
+        return count;
+    }
+
+    @Override
+    public int delete(Uri uri, String selection, String[] selectionArgs) {
+        int count = 0;
+        boolean callerIsSyncAdapter = isCallerSyncAdapter(uri);
+        boolean applyingBatch = applyingBatch();
+        if (!applyingBatch) {
+            mDb = mOpenHelper.getWritableDatabase();
+            mDb.beginTransactionWithListener(this);
+            try {
+                count = deleteInTransaction(uri, selection, selectionArgs, callerIsSyncAdapter);
+                if (count > 0) {
+                    mNotifyChange = true;
+                }
+                mDb.setTransactionSuccessful();
+            } finally {
+                mDb.endTransaction();
+            }
+
+            onEndTransaction(callerIsSyncAdapter);
+        } else {
+            count = deleteInTransaction(uri, selection, selectionArgs, callerIsSyncAdapter);
+            if (count > 0) {
+                mNotifyChange = true;
+            }
+        }
+        return count;
+    }
+
+    @Override
+    public ContentProviderResult[] applyBatch(ArrayList<ContentProviderOperation> operations)
+            throws OperationApplicationException {
+        int ypCount = 0;
+        int opCount = 0;
+        boolean callerIsSyncAdapter = false;
+        mDb = mOpenHelper.getWritableDatabase();
+        mDb.beginTransactionWithListener(this);
+        try {
+            mApplyingBatch.set(true);
+            final int numOperations = operations.size();
+            final ContentProviderResult[] results = new ContentProviderResult[numOperations];
+            for (int i = 0; i < numOperations; i++) {
+                if (++opCount >= MAX_OPERATIONS_PER_YIELD_POINT) {
+                    throw new OperationApplicationException(
+                            "Too many content provider operations between yield points. "
+                                    + "The maximum number of operations per yield point is "
+                                    + MAX_OPERATIONS_PER_YIELD_POINT, ypCount);
+                }
+                final ContentProviderOperation operation = operations.get(i);
+                if (!callerIsSyncAdapter && isCallerSyncAdapter(operation.getUri())) {
+                    callerIsSyncAdapter = true;
+                }
+                if (i > 0 && operation.isYieldAllowed()) {
+                    opCount = 0;
+                    if (mDb.yieldIfContendedSafely(SLEEP_AFTER_YIELD_DELAY)) {
+                        ypCount++;
+                    }
+                }
+                results[i] = operation.apply(this, results, i);
+            }
+            mDb.setTransactionSuccessful();
+            return results;
+        } finally {
+            mApplyingBatch.set(false);
+            mDb.endTransaction();
+            onEndTransaction(callerIsSyncAdapter);
+        }
+    }
+
+    @Override
+    public void onBegin() {
+        onBeginTransaction();
+    }
+
+    @Override
+    public void onCommit() {
+        beforeTransactionCommit();
+    }
+
+    @Override
+    public void onRollback() {
+        // not used
+    }
+
+    protected void onBeginTransaction() {
+    }
+
+    protected void beforeTransactionCommit() {
+    }
+
+    protected void onEndTransaction(boolean callerIsSyncAdapter) {
+        if (mNotifyChange) {
+            mNotifyChange = false;
+            notifyChange(callerIsSyncAdapter);
+        }
+    }
+}
diff --git a/src/com/android/browser/search/.DefaultSearchEngine.java.swp b/src/com/android/browser/search/.DefaultSearchEngine.java.swp
new file mode 100644
index 0000000..441153c
--- /dev/null
+++ b/src/com/android/browser/search/.DefaultSearchEngine.java.swp
Binary files differ
diff --git a/src/com/android/browser/widget/BookmarkWidgetProvider.java b/src/com/android/browser/widget/BookmarkStackWidgetProvider.java
similarity index 70%
rename from src/com/android/browser/widget/BookmarkWidgetProvider.java
rename to src/com/android/browser/widget/BookmarkStackWidgetProvider.java
index 62b48c0..0684c61 100644
--- a/src/com/android/browser/widget/BookmarkWidgetProvider.java
+++ b/src/com/android/browser/widget/BookmarkStackWidgetProvider.java
@@ -16,34 +16,30 @@
 
 package com.android.browser.widget;
 
-import android.app.PendingIntent;
 import android.appwidget.AppWidgetManager;
 import android.appwidget.AppWidgetProvider;
 import android.content.Context;
 import android.content.Intent;
-import android.util.Log;
 
 /**
  * Widget that shows a preview of the user's bookmarks.
  */
-public class BookmarkWidgetProvider extends AppWidgetProvider {
-
-    static final String TAG = "BookmarkWidgetProvider";
+public class BookmarkStackWidgetProvider extends AppWidgetProvider {
 
     @Override
     public void onUpdate(Context context, AppWidgetManager mngr, int[] ids) {
-        context.startService(new Intent(BookmarkWidgetService.UPDATE, null,
-                    context, BookmarkWidgetService.class));
+        context.startService(new Intent(BookmarkStackWidgetService.UPDATE, null,
+                    context, BookmarkStackWidgetService.class));
     }
 
     @Override
     public void onEnabled(Context context) {
-        context.startService(new Intent(context, BookmarkWidgetService.class));
+        context.startService(new Intent(context, BookmarkStackWidgetService.class));
     }
 
     @Override
     public void onDisabled(Context context) {
-        context.stopService(new Intent(context, BookmarkWidgetService.class));
+        context.stopService(new Intent(context, BookmarkStackWidgetService.class));
     }
-}
 
+}
diff --git a/src/com/android/browser/widget/BookmarkStackWidgetService.java b/src/com/android/browser/widget/BookmarkStackWidgetService.java
new file mode 100644
index 0000000..83b07df
--- /dev/null
+++ b/src/com/android/browser/widget/BookmarkStackWidgetService.java
@@ -0,0 +1,217 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser.widget;
+
+import com.android.browser.R;
+
+import android.app.PendingIntent;
+import android.appwidget.AppWidgetManager;
+import android.content.ComponentName;
+import android.content.Intent;
+import android.database.Cursor;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.net.Uri;
+import android.os.Handler;
+import android.os.Message;
+import android.provider.BrowserContract;
+import android.text.TextUtils;
+import android.util.Log;
+import android.view.View;
+import android.widget.RemoteViews;
+import android.widget.RemoteViewsService;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class BookmarkStackWidgetService extends RemoteViewsService {
+
+    private static final String LOGTAG = "browserwidget";
+
+    /** Force the bookmarks to be re-rendered. */
+    public static final String UPDATE = "com.android.browser.widget.UPDATE";
+
+    /** the adapter intent action */
+    public static final String ADAPTER = "com.android.browser.widget.ADAPTER";
+
+    private static final String[] PROJECTION = new String[] {
+        BrowserContract.Bookmarks._ID,
+        BrowserContract.Bookmarks.TITLE,
+        BrowserContract.Bookmarks.URL,
+        BrowserContract.Bookmarks.THUMBNAIL };
+
+    private static final String WHERE_CLAUSE = BrowserContract.Bookmarks.IS_FOLDER +
+            " == 0";
+
+    // No id specified.
+    private static final int NO_ID = -1;
+
+    private static final int MSG_UPDATE = 0;
+
+    List<RenderResult> mBookmarks;
+
+    private final Handler mHandler = new Handler() {
+        @Override
+        public void handleMessage(Message msg) {
+            switch (msg.what) {
+                case MSG_UPDATE:
+                    updateWidget();
+                    break;
+                default:
+                    break;
+            }
+        }
+    };
+
+    @Override
+    public int onStartCommand(Intent intent, int flags, int startId) {
+        if ((intent == null) || (intent.getAction() != null) && UPDATE.equals(intent.getAction())) {
+            mHandler.sendEmptyMessage(MSG_UPDATE);
+        }
+        return START_STICKY;
+    }
+
+    private void updateWidget() {
+        RemoteViews views = new RemoteViews(getPackageName(),
+                R.layout.bookmarkstackwidget);
+        Intent vi = new Intent(Intent.ACTION_VIEW);
+        vi.addCategory(Intent.CATEGORY_BROWSABLE);
+        views.setPendingIntentTemplate(R.id.stackwidget_stack,
+                PendingIntent.getActivity(BookmarkStackWidgetService.this, 0, vi,
+                        PendingIntent.FLAG_CANCEL_CURRENT));
+        Intent adapter = new Intent(BookmarkStackWidgetService.ADAPTER, null,
+                this, BookmarkStackWidgetService.class);
+        views.setRemoteAdapter(R.id.stackwidget_stack, adapter);
+        AppWidgetManager.getInstance(this).updateAppWidget(
+                new ComponentName(this, BookmarkStackWidgetProvider.class),
+                views);
+    }
+
+    @Override
+    public RemoteViewsFactory onGetViewFactory(Intent intent) {
+        return mViewFactory;
+    }
+
+    RemoteViewsService.RemoteViewsFactory mViewFactory = new RemoteViewsFactory () {
+
+        Intent mFillIntent;
+        
+        @Override
+        public int getCount() {
+            return mBookmarks.size();
+        }
+
+        @Override
+        public long getItemId(int position) {
+            return position;
+        }
+
+        @Override
+        public RemoteViews getLoadingView() {
+            return null;
+        }
+
+        @Override
+        public RemoteViews getViewAt(int position) {
+            RenderResult res = mBookmarks.get(position);
+            RemoteViews views = new RemoteViews(getPackageName(),
+                    R.layout.bookmarkstackwidget_item);
+            mFillIntent.setData(Uri.parse(res.mUrl));
+            views.setOnClickFillInIntent(R.id.stack_item, mFillIntent);
+            // Set the title of the bookmark. Use the url as a backup.
+            String displayTitle = res.mTitle;
+            if (TextUtils.isEmpty(displayTitle)) {
+                displayTitle = res.mUrl;
+            }
+            views.setTextViewText(R.id.label, displayTitle);
+            if (res.mBitmap != null) {
+                views.setImageViewBitmap(R.id.thumb, res.mBitmap);
+                views.setViewVisibility(R.id.label, View.GONE);
+            }
+            return views;
+        }
+
+        @Override
+        public int getViewTypeCount() {
+            return 1;
+        }
+
+        @Override
+        public boolean hasStableIds() {
+            return false;
+        }
+
+        @Override
+        public void onCreate() {
+            mFillIntent = new Intent();
+            update();
+        }
+
+        @Override
+        public void onDestroy() {
+        }
+
+        public void update() {
+            mBookmarks = new ArrayList<RenderResult>();
+            // Look up all the bookmarks
+            Cursor c = null;
+            try {
+                c = getContentResolver().query(BrowserContract.Bookmarks.CONTENT_URI,
+                        PROJECTION, WHERE_CLAUSE, null, null);
+                if (c != null) {
+                    while (c.moveToNext()) {
+                        int id = c.getInt(0);
+                        String title = c.getString(1);
+                        String url = c.getString(2);
+                        RenderResult res = new RenderResult(id, title, url);
+                        byte[] blob = c.getBlob(3);
+                        if (blob != null) {
+                            res.mBitmap = BitmapFactory.decodeByteArray(blob, 0, blob.length);
+                        }
+                        mBookmarks.add(res);
+                    }
+                }
+            } catch (IllegalStateException e) {
+                Log.e(LOGTAG, "update bookmark widget", e);
+            } finally {
+                if (c != null) {
+                    c.close();
+                }
+            }
+        }
+
+        @Override
+        public void onDataSetChanged() {
+        }
+    };
+
+    // Class containing the rendering information for a specific bookmark.
+    private static class RenderResult {
+        final int mId;
+        final String mTitle;
+        final String mUrl;
+        Bitmap mBitmap;
+
+        RenderResult(int id, String title, String url) {
+            mId = id;
+            mTitle = title;
+            mUrl = url;
+        }
+
+    }
+
+}
diff --git a/src/com/android/browser/widget/BookmarkWidgetService.java b/src/com/android/browser/widget/BookmarkWidgetService.java
deleted file mode 100644
index 1fd9163..0000000
--- a/src/com/android/browser/widget/BookmarkWidgetService.java
+++ /dev/null
@@ -1,385 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser.widget;
-
-import android.app.PendingIntent;
-import android.app.Service;
-import android.appwidget.AppWidgetManager;
-import android.content.ComponentName;
-import android.content.Context;
-import android.content.Intent;
-import android.content.ServiceConnection;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.os.Handler;
-import android.os.IBinder;
-import android.os.Message;
-import android.os.ParcelFileDescriptor;
-import android.provider.Browser;
-import android.provider.Browser.BookmarkColumns;
-import android.service.urlrenderer.UrlRenderer;
-import android.service.urlrenderer.UrlRendererService;
-import android.util.Log;
-import android.view.View;
-import android.widget.RemoteViews;
-
-import com.android.browser.R;
-
-import java.io.InputStream;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.HashMap;
-
-public class BookmarkWidgetService extends Service
-        implements UrlRenderer.Callback {
-
-    private static final String TAG = "BookmarkWidgetService";
-
-    /** Force the bookmarks to be re-renderer. */
-    public static final String UPDATE = "com.android.browser.widget.UPDATE";
-
-    /** Change the widget to the next bookmark. */
-    private static final String NEXT = "com.android.browser.widget.NEXT";
-
-    /** Change the widget to the previous bookmark. */
-    private static final String PREV = "com.android.browser.widget.PREV";
-
-    /** Id of the current item displayed in the widget. */
-    private static final String EXTRA_ID =
-            "com.android.browser.widget.extra.ID";
-
-    // XXX: Remove these magic numbers once the dimensions of the widget can be
-    // queried.
-    private static final int WIDTH = 306;
-    private static final int HEIGHT = 386;
-
-    // Limit the number of connection attempts.
-    private static final int MAX_SERVICE_RETRY_COUNT = 5;
-
-    // No id specified.
-    private static final int NO_ID = -1;
-
-    private static final int MSG_UPDATE = 0;
-    private final Handler mHandler = new Handler() {
-        @Override
-        public void handleMessage(Message msg) {
-            switch (msg.what) {
-                case MSG_UPDATE:
-                    if (mRenderer != null) {
-                        queryCursorAndRender();
-                    } else {
-                        if (++mServiceRetryCount <= MAX_SERVICE_RETRY_COUNT) {
-                            // Service is not connected, try again in a second.
-                            mHandler.sendEmptyMessageDelayed(MSG_UPDATE, 1000);
-                        }
-                    }
-                    break;
-                default:
-                    break;
-            }
-        }
-    };
-
-    private final ServiceConnection mConnection = new ServiceConnection() {
-        public void onServiceConnected(ComponentName className,
-                IBinder service) {
-            mRenderer = new UrlRenderer(service);
-        }
-
-        public void onServiceDisconnected(ComponentName className) {
-            mRenderer = null;
-        }
-    };
-
-    // Id -> information map storing db ids and their result.
-    private final HashMap<Integer, RenderResult> mIdsToResults =
-            new HashMap<Integer, RenderResult>();
-
-    // List of ids in order
-    private final ArrayList<Integer> mIdList = new ArrayList<Integer>();
-
-    // Map of urls to ids for when a url is complete.
-    private final HashMap<String, Integer> mUrlsToIds =
-            new HashMap<String, Integer>();
-
-    // The current id used by the widget during an update.
-    private int mCurrentId = NO_ID;
-    // Class that contacts the service on the phone to render bookmarks.
-    private UrlRenderer mRenderer;
-    // Number of service retries. Stop trying to connect after
-    // MAX_SERVICE_RETRY_COUNT
-    private int mServiceRetryCount;
-
-    @Override
-    public void onCreate() {
-        bindService(new Intent(UrlRendererService.SERVICE_INTERFACE),
-                mConnection, Context.BIND_AUTO_CREATE);
-    }
-
-    @Override
-    public void onDestroy() {
-        unbindService(mConnection);
-    }
-
-    @Override
-    public android.os.IBinder onBind(Intent intent) {
-        return null;
-    }
-
-    @Override
-    public int onStartCommand(Intent intent, int flags, int startId) {
-        final String action = intent.getAction();
-        if (UPDATE.equals(action)) {
-            mHandler.sendEmptyMessage(MSG_UPDATE);
-        } else if (PREV.equals(action) && mIdList.size() > 1) {
-            int prev = getPreviousId(intent);
-            if (prev == NO_ID) {
-                Log.d(TAG, "Could not determine previous id");
-                return START_NOT_STICKY;
-            }
-            RenderResult res = mIdsToResults.get(prev);
-            if (res != null) {
-                updateWidget(res);
-            }
-        } else if (NEXT.equals(action) && mIdList.size() > 1) {
-            int next = getNextId(intent);
-            if (next == NO_ID) {
-                Log.d(TAG, "Could not determine next id");
-                return START_NOT_STICKY;
-            }
-            RenderResult res = mIdsToResults.get(next);
-            if (res != null) {
-                updateWidget(res);
-            }
-        }
-        return START_STICKY;
-    }
-
-    private int getPreviousId(Intent intent) {
-        int listSize = mIdList.size();
-        // If the list contains 1 or fewer entries, return NO_ID so that the
-        // widget does not update.
-        if (listSize <= 1) {
-            return NO_ID;
-        }
-
-        int curr = intent.getIntExtra(EXTRA_ID, NO_ID);
-        if (curr == NO_ID) {
-            return NO_ID;
-        }
-
-        // Check if the current id is the beginning of the list so we can skip
-        // iterating through.
-        if (mIdList.get(0) == curr) {
-            return mIdList.get(listSize - 1);
-        }
-
-        // Search for the current id and remember the previous id.
-        int prev = NO_ID;
-        for (int id : mIdList) {
-            if (id == curr) {
-                break;
-            }
-            prev = id;
-        }
-        return prev;
-    }
-
-    private int getNextId(Intent intent) {
-        int listSize = mIdList.size();
-        // If the list contains 1 or fewer entries, return NO_ID so that the
-        // widget does not update.
-        if (listSize <= 1) {
-            return NO_ID;
-        }
-
-        int curr = intent.getIntExtra(EXTRA_ID, NO_ID);
-        if (curr == NO_ID) {
-            return NO_ID;
-        }
-
-        // Check if the current id is at the end of the list so we can skip
-        // iterating through.
-        if (mIdList.get(listSize - 1) == curr) {
-            return mIdList.get(0);
-        }
-
-        // Iterate through the ids. i is set to the current index + 1.
-        int i = 1;
-        for (int id : mIdList) {
-            if (id == curr) {
-                break;
-            }
-            i++;
-        }
-        return mIdList.get(i);
-    }
-
-    private void updateWidget(RenderResult res) {
-        RemoteViews views = new RemoteViews(getPackageName(),
-                R.layout.bookmarkwidget);
-
-        Intent prev = new Intent(PREV, null, this, BookmarkWidgetService.class);
-        prev.putExtra(EXTRA_ID, res.mId);
-        views.setOnClickPendingIntent(R.id.previous,
-                PendingIntent.getService(this, 0, prev,
-                    PendingIntent.FLAG_CANCEL_CURRENT));
-
-        Intent next = new Intent(NEXT, null, this, BookmarkWidgetService.class);
-        next.putExtra(EXTRA_ID, res.mId);
-        views.setOnClickPendingIntent(R.id.next,
-                PendingIntent.getService(this, 0, next,
-                    PendingIntent.FLAG_CANCEL_CURRENT));
-
-        // Set the title of the bookmark. Use the url as a backup.
-        String displayTitle = res.mTitle;
-        if (displayTitle == null) {
-            displayTitle = res.mUrl;
-        }
-        views.setTextViewText(R.id.title, displayTitle);
-
-        // Set the image or revert to the progress indicator.
-        if (res.mBitmap != null) {
-            views.setImageViewBitmap(R.id.image, res.mBitmap);
-            views.setViewVisibility(R.id.image, View.VISIBLE);
-            views.setViewVisibility(R.id.progress, View.GONE);
-        } else {
-            views.setViewVisibility(R.id.progress, View.VISIBLE);
-            views.setViewVisibility(R.id.image, View.GONE);
-        }
-
-        // Update the current id.
-        mCurrentId = res.mId;
-
-        AppWidgetManager.getInstance(this).updateAppWidget(
-                new ComponentName(this, BookmarkWidgetProvider.class),
-                views);
-    }
-
-    // Default WHERE clause is all bookmarks.
-    private static final String QUERY_WHERE =
-            BookmarkColumns.BOOKMARK + " == 1";
-    private static final String[] PROJECTION = new String[] {
-            BookmarkColumns._ID, BookmarkColumns.TITLE, BookmarkColumns.URL };
-
-    // Class containing the rendering information for a specific bookmark.
-    private static class RenderResult {
-        final int    mId;
-        final String mTitle;
-        final String mUrl;
-        Bitmap       mBitmap;
-
-        RenderResult(int id, String title, String url) {
-            mId = id;
-            mTitle = title;
-            mUrl = url;
-        }
-    }
-
-    private void queryCursorAndRender() {
-        // Clear the ordered list of ids and the map of ids to bitmaps.
-        mIdList.clear();
-        mIdsToResults.clear();
-
-        // Look up all the bookmarks
-        Cursor c = getContentResolver().query(Browser.BOOKMARKS_URI, PROJECTION,
-                QUERY_WHERE, null, null);
-        if (c != null) {
-            if (c.moveToFirst()) {
-                ArrayList<String> urls = new ArrayList<String>(c.getCount());
-                boolean sawCurrentId = false;
-                do {
-                    int id = c.getInt(0);
-                    String title = c.getString(1);
-                    String url = c.getString(2);
-
-                    // Linear list of ids to obtain the previous and next.
-                    mIdList.add(id);
-
-                    // Map the url to its db id for lookup when complete.
-                    mUrlsToIds.put(url, id);
-
-                    // Is this the current id?
-                    if (mCurrentId == id) {
-                        sawCurrentId = true;
-                    }
-
-                    // Store the current information to at least display the
-                    // title.
-                    RenderResult res = new RenderResult(id, title, url);
-                    mIdsToResults.put(id, res);
-
-                    // Add the url to our list to render.
-                    urls.add(url);
-                } while (c.moveToNext());
-
-                // Request a rendering of the urls. XXX: Hard-coded dimensions
-                // until the view's orientation and size can be determined. Or
-                // in the future the image will be a picture that can be
-                // scaled/zoomed arbitrarily.
-                mRenderer.render(urls, WIDTH, HEIGHT, this);
-
-                // Set the current id to the very first id if we did not see
-                // the current id in the list (the bookmark could have been
-                // deleted or this is the first update).
-                if (!sawCurrentId) {
-                    mCurrentId = mIdList.get(0);
-                }
-            }
-            c.close();
-        }
-    }
-
-    // UrlRenderer.Callback implementation
-    public void complete(String url, ParcelFileDescriptor result) {
-        int id = mUrlsToIds.get(url);
-        if (id == NO_ID) {
-            Log.d(TAG, "No matching id found during completion of "
-                    + url);
-            return;
-        }
-
-        RenderResult res = mIdsToResults.get(id);
-        if (res == null) {
-            Log.d(TAG, "No result found during completion of "
-                    + url);
-            return;
-        }
-
-        // Set the result.
-        if (result != null) {
-            InputStream input =
-                    new ParcelFileDescriptor.AutoCloseInputStream(result);
-            Bitmap orig = BitmapFactory.decodeStream(input, null, null);
-            // XXX: Hard-coded scaled bitmap until I can query the image
-            // dimensions.
-            res.mBitmap = Bitmap.createScaledBitmap(orig, WIDTH, HEIGHT, true);
-            try {
-                input.close();
-            } catch (IOException e) {
-                // oh well...
-            }
-        }
-
-        // If we are currently looking at the bookmark that just finished,
-        // update the widget.
-        if (mCurrentId == id) {
-            updateWidget(res);
-        }
-    }
-}
diff --git a/tests/src/com/android/browser/JNIBindingsTestApp.java b/tests/src/com/android/browser/JNIBindingsTestApp.java
index 4f083f6..4c8802a 100644
--- a/tests/src/com/android/browser/JNIBindingsTestApp.java
+++ b/tests/src/com/android/browser/JNIBindingsTestApp.java
@@ -37,6 +37,9 @@
 /**
  * Adds a JavaScript interface to the webview and calls functions on it to verify variables
  * are passed from JS to Java correctly.
+ * To run this test, execute:
+ * adb shell am instrument -w -e class com.android.browser.JNIBindingsTestApp#testJNIBindings \
+ *     com.android.browser.tests/android.test.InstrumentationTestRunner
  */
 public class JNIBindingsTestApp extends ActivityInstrumentationTestCase2<BrowserActivity> {
 
@@ -89,7 +92,7 @@
                     }
                 }
             };
-            mWebView.documentAsText(mHandler.obtainMessage(MSG_WEBKIT_DATA_READY));
+            mWebView.documentAsText(mHandler.obtainMessage(MSG_WEBKIT_DATA_READY, 1, 0));
             Looper.loop();
         }
     }
diff --git a/tests/src/com/android/browser/TestWebChromeClient.java b/tests/src/com/android/browser/TestWebChromeClient.java
index d78eaed..53f8db3 100644
--- a/tests/src/com/android/browser/TestWebChromeClient.java
+++ b/tests/src/com/android/browser/TestWebChromeClient.java
@@ -195,7 +195,7 @@
 
     /** {@inheritDoc} */
     @Override
-    public void openFileChooser(ValueCallback<Uri> uploadFile) {
-        mWrappedClient.openFileChooser(uploadFile);
+    public void openFileChooser(ValueCallback<Uri> uploadFile, String acceptType) {
+        mWrappedClient.openFileChooser(uploadFile, acceptType);
     }
 }