diff --git a/api/current.txt b/api/current.txt
index cce28a4..13d3228 100644
--- a/api/current.txt
+++ b/api/current.txt
@@ -414,7 +414,7 @@
     field public static final int ems = 16843096; // 0x1010158
     field public static final deprecated int enabled = 16842766; // 0x101000e
     field public static final int endColor = 16843166; // 0x101019e
-    field public static final int endYear = 16843133; // 0x101017d
+    field public static final deprecated int endYear = 16843133; // 0x101017d
     field public static final int enterFadeDuration = 16843532; // 0x101030c
     field public static final int entries = 16842930; // 0x10100b2
     field public static final int entryValues = 16843256; // 0x10101f8
@@ -593,6 +593,7 @@
     field public static final int layerType = 16843604; // 0x1010354
     field public static final int layout = 16842994; // 0x10100f2
     field public static final int layoutAnimation = 16842988; // 0x10100ec
+    field public static final int layoutDirection = 16843689; // 0x10103a9
     field public static final int layout_above = 16843140; // 0x1010184
     field public static final int layout_alignBaseline = 16843142; // 0x1010186
     field public static final int layout_alignBottom = 16843146; // 0x101018a
@@ -614,10 +615,10 @@
     field public static final int layout_height = 16842997; // 0x10100f5
     field public static final int layout_margin = 16842998; // 0x10100f6
     field public static final int layout_marginBottom = 16843002; // 0x10100fa
-    field public static final int layout_marginEnd = 16843692; // 0x10103ac
+    field public static final int layout_marginEnd = 16843693; // 0x10103ad
     field public static final int layout_marginLeft = 16842999; // 0x10100f7
     field public static final int layout_marginRight = 16843001; // 0x10100f9
-    field public static final int layout_marginStart = 16843691; // 0x10103ab
+    field public static final int layout_marginStart = 16843692; // 0x10103ac
     field public static final int layout_marginTop = 16843000; // 0x10100f8
     field public static final int layout_row = 16843643; // 0x101037b
     field public static final int layout_rowSpan = 16843644; // 0x101037c
@@ -713,10 +714,10 @@
     field public static final int packageNames = 16843649; // 0x1010381
     field public static final int padding = 16842965; // 0x10100d5
     field public static final int paddingBottom = 16842969; // 0x10100d9
-    field public static final int paddingEnd = 16843690; // 0x10103aa
+    field public static final int paddingEnd = 16843691; // 0x10103ab
     field public static final int paddingLeft = 16842966; // 0x10100d6
     field public static final int paddingRight = 16842968; // 0x10100d8
-    field public static final int paddingStart = 16843689; // 0x10103a9
+    field public static final int paddingStart = 16843690; // 0x10103aa
     field public static final int paddingTop = 16842967; // 0x10100d7
     field public static final int panelBackground = 16842846; // 0x101005e
     field public static final int panelColorBackground = 16842849; // 0x1010061
@@ -887,7 +888,7 @@
     field public static final int starStyle = 16842882; // 0x1010082
     field public static final int startColor = 16843165; // 0x101019d
     field public static final int startOffset = 16843198; // 0x10101be
-    field public static final int startYear = 16843132; // 0x101017c
+    field public static final deprecated int startYear = 16843132; // 0x101017c
     field public static final int stateNotNeeded = 16842774; // 0x1010016
     field public static final int state_above_anchor = 16842922; // 0x10100aa
     field public static final int state_accelerated = 16843547; // 0x101031b
@@ -7275,6 +7276,7 @@
     method public android.database.sqlite.SQLiteStatement compileStatement(java.lang.String) throws android.database.SQLException;
     method public static android.database.sqlite.SQLiteDatabase create(android.database.sqlite.SQLiteDatabase.CursorFactory);
     method public int delete(java.lang.String, java.lang.String, java.lang.String[]);
+    method public static boolean deleteDatabase(java.io.File);
     method public boolean enableWriteAheadLogging();
     method public void endTransaction();
     method public void execSQL(java.lang.String) throws android.database.SQLException;
@@ -7392,8 +7394,8 @@
     ctor public SQLiteOpenHelper(android.content.Context, java.lang.String, android.database.sqlite.SQLiteDatabase.CursorFactory, int, android.database.DatabaseErrorHandler);
     method public synchronized void close();
     method public java.lang.String getDatabaseName();
-    method public synchronized android.database.sqlite.SQLiteDatabase getReadableDatabase();
-    method public synchronized android.database.sqlite.SQLiteDatabase getWritableDatabase();
+    method public android.database.sqlite.SQLiteDatabase getReadableDatabase();
+    method public android.database.sqlite.SQLiteDatabase getWritableDatabase();
     method public abstract void onCreate(android.database.sqlite.SQLiteDatabase);
     method public void onDowngrade(android.database.sqlite.SQLiteDatabase, int, int);
     method public void onOpen(android.database.sqlite.SQLiteDatabase);
@@ -7580,6 +7582,7 @@
     method public java.lang.String getOriginalMimeType(android.net.Uri);
     method public int openConvertSession(java.lang.String);
     method public int processDrmInfo(android.drm.DrmInfo);
+    method public void release();
     method public int removeAllRights();
     method public int removeRights(java.lang.String);
     method public int removeRights(android.net.Uri);
@@ -15089,7 +15092,7 @@
     field public static final android.os.Parcelable.Creator STRING_CREATOR;
   }
 
-  public class ParcelFileDescriptor implements android.os.Parcelable {
+  public class ParcelFileDescriptor implements java.io.Closeable android.os.Parcelable {
     ctor public ParcelFileDescriptor(android.os.ParcelFileDescriptor);
     method public static android.os.ParcelFileDescriptor adoptFd(int);
     method public void close() throws java.io.IOException;
@@ -15323,6 +15326,7 @@
     method public android.os.StrictMode.VmPolicy.Builder detectActivityLeaks();
     method public android.os.StrictMode.VmPolicy.Builder detectAll();
     method public android.os.StrictMode.VmPolicy.Builder detectLeakedClosableObjects();
+    method public android.os.StrictMode.VmPolicy.Builder detectLeakedRegistrationObjects();
     method public android.os.StrictMode.VmPolicy.Builder detectLeakedSqlLiteObjects();
     method public android.os.StrictMode.VmPolicy.Builder penaltyDeath();
     method public android.os.StrictMode.VmPolicy.Builder penaltyDropBox();
@@ -16000,6 +16004,7 @@
     field public static final java.lang.String CALENDAR_ID = "calendar_id";
     field public static final java.lang.String CAN_INVITE_OTHERS = "canInviteOthers";
     field public static final java.lang.String DESCRIPTION = "description";
+    field public static final java.lang.String DISPLAY_COLOR = "displayColor";
     field public static final java.lang.String DTEND = "dtend";
     field public static final java.lang.String DTSTART = "dtstart";
     field public static final java.lang.String DURATION = "duration";
@@ -23104,6 +23109,7 @@
     method public void buildDrawingCache(boolean);
     method public void buildLayer();
     method public boolean callOnClick();
+    method public boolean canResolveLayoutDirection();
     method public boolean canScrollHorizontally(int);
     method public boolean canScrollVertically(int);
     method public void cancelLongPress();
@@ -23189,6 +23195,7 @@
     method public boolean getKeepScreenOn();
     method public android.view.KeyEvent.DispatcherState getKeyDispatcherState();
     method public int getLayerType();
+    method public int getLayoutDirection();
     method public android.view.ViewGroup.LayoutParams getLayoutParams();
     method public final int getLeft();
     method protected float getLeftFadingEdgeStrength();
@@ -23218,6 +23225,8 @@
     method public final android.view.ViewParent getParent();
     method public float getPivotX();
     method public float getPivotY();
+    method public int getResolvedLayoutDirection();
+    method public int getResolvedLayoutDirection(android.graphics.drawable.Drawable);
     method public int getResolvedTextDirection();
     method public android.content.res.Resources getResources();
     method public final int getRight();
@@ -23261,6 +23270,7 @@
     method public boolean hasFocus();
     method public boolean hasFocusable();
     method public boolean hasOnClickListeners();
+    method public boolean hasTransientState();
     method public boolean hasWindowFocus();
     method public static android.view.View inflate(android.content.Context, int, android.view.ViewGroup);
     method protected void initializeFadingEdge(android.content.res.TypedArray);
@@ -23285,7 +23295,9 @@
     method public boolean isHovered();
     method public boolean isInEditMode();
     method public boolean isInTouchMode();
+    method protected static boolean isLayoutDirectionRtl(java.util.Locale);
     method public boolean isLayoutRequested();
+    method public boolean isLayoutRtl();
     method public boolean isLongClickable();
     method public boolean isOpaque();
     method protected boolean isPaddingOffsetRequired();
@@ -23336,10 +23348,12 @@
     method protected void onLayout(boolean, int, int, int, int);
     method protected void onMeasure(int, int);
     method protected void onOverScrolled(int, int, boolean, boolean);
+    method public void onPaddingChanged(int);
     method public void onPopulateAccessibilityEvent(android.view.accessibility.AccessibilityEvent);
-    method public void onResetResolvedTextDirection();
-    method public void onResolvePadding(int);
-    method public void onResolveTextDirection();
+    method public void onResolvedLayoutDirectionChanged();
+    method public void onResolvedLayoutDirectionReset();
+    method public void onResolvedTextDirectionChanged();
+    method public void onResolvedTextDirectionReset();
     method protected void onRestoreInstanceState(android.os.Parcelable);
     method protected android.os.Parcelable onSaveInstanceState();
     method protected void onScrollChanged(int, int, int, int);
@@ -23374,6 +23388,7 @@
     method public void requestLayout();
     method public boolean requestRectangleOnScreen(android.graphics.Rect);
     method public boolean requestRectangleOnScreen(android.graphics.Rect, boolean);
+    method public void resetResolvedLayoutDirection();
     method public void resetResolvedTextDirection();
     method public void resolvePadding();
     method public static int resolveSize(int, int);
@@ -23408,12 +23423,14 @@
     method public void setFocusable(boolean);
     method public void setFocusableInTouchMode(boolean);
     method public void setHapticFeedbackEnabled(boolean);
+    method public void setHasTransientState(boolean);
     method public void setHorizontalFadingEdgeEnabled(boolean);
     method public void setHorizontalScrollBarEnabled(boolean);
     method public void setHovered(boolean);
     method public void setId(int);
     method public void setKeepScreenOn(boolean);
     method public void setLayerType(int, android.graphics.Paint);
+    method public void setLayoutDirection(int);
     method public void setLayoutParams(android.view.ViewGroup.LayoutParams);
     method public final void setLeft(int);
     method public void setLongClickable(boolean);
@@ -23516,6 +23533,10 @@
     field public static final int LAYER_TYPE_HARDWARE = 2; // 0x2
     field public static final int LAYER_TYPE_NONE = 0; // 0x0
     field public static final int LAYER_TYPE_SOFTWARE = 1; // 0x1
+    field public static final int LAYOUT_DIRECTION_INHERIT = -2147483648; // 0x80000000
+    field public static final int LAYOUT_DIRECTION_LOCALE = -1073741824; // 0xc0000000
+    field public static final int LAYOUT_DIRECTION_LTR = 0; // 0x0
+    field public static final int LAYOUT_DIRECTION_RTL = 1073741824; // 0x40000000
     field public static final int MEASURED_HEIGHT_STATE_SHIFT = 16; // 0x10
     field public static final int MEASURED_SIZE_MASK = 16777215; // 0xffffff
     field public static final int MEASURED_STATE_MASK = -16777216; // 0xff000000
@@ -23830,7 +23851,6 @@
     method public void requestDisallowInterceptTouchEvent(boolean);
     method public boolean requestSendAccessibilityEvent(android.view.View, android.view.accessibility.AccessibilityEvent);
     method public void requestTransparentRegion(android.view.View);
-    method protected void resetResolvedLayoutDirection();
     method public void scheduleLayoutAnimation();
     method public void setAddStatesFromChildren(boolean);
     method public void setAlwaysDrawnWithCacheEnabled(boolean);
@@ -23868,6 +23888,7 @@
     ctor public ViewGroup.LayoutParams(android.content.Context, android.util.AttributeSet);
     ctor public ViewGroup.LayoutParams(int, int);
     ctor public ViewGroup.LayoutParams(android.view.ViewGroup.LayoutParams);
+    method public void onResolveLayoutDirection(int);
     method protected void setBaseAttributes(android.content.res.TypedArray, int, int);
     field public static final deprecated int FILL_PARENT = -1; // 0xffffffff
     field public static final int MATCH_PARENT = -1; // 0xffffffff
@@ -26093,17 +26114,36 @@
     ctor public CalendarView(android.content.Context, android.util.AttributeSet);
     ctor public CalendarView(android.content.Context, android.util.AttributeSet, int);
     method public long getDate();
+    method public int getDateTextAppearance();
     method public int getFirstDayOfWeek();
+    method public int getFocusedMonthDateColor();
     method public long getMaxDate();
     method public long getMinDate();
+    method public android.graphics.drawable.Drawable getSelectedDateVerticalBar();
+    method public int getSelectedWeekBackgroundColor();
     method public boolean getShowWeekNumber();
+    method public int getShownWeekCount();
+    method public int getUnfocusedMonthDateColor();
+    method public int getWeekDayTextAppearance();
+    method public int getWeekNumberColor();
+    method public int getWeekSeparatorLineColor();
     method public void setDate(long);
     method public void setDate(long, boolean, boolean);
+    method public void setDateTextAppearance(int);
     method public void setFirstDayOfWeek(int);
+    method public void setFocusedMonthDateColor(int);
     method public void setMaxDate(long);
     method public void setMinDate(long);
     method public void setOnDateChangeListener(android.widget.CalendarView.OnDateChangeListener);
+    method public void setSelectedDateVerticalBar(int);
+    method public void setSelectedDateVerticalBar(android.graphics.drawable.Drawable);
+    method public void setSelectedWeekBackgroundColor(int);
     method public void setShowWeekNumber(boolean);
+    method public void setShownWeekCount(int);
+    method public void setUnfocusedMonthDateColor(int);
+    method public void setWeekDayTextAppearance(int);
+    method public void setWeekNumberColor(int);
+    method public void setWeekSeparatorLineColor(int);
   }
 
   public static abstract interface CalendarView.OnDateChangeListener {
diff --git a/cmds/dumpstate/dumpstate.c b/cmds/dumpstate/dumpstate.c
index ebe28db..13b63dc 100644
--- a/cmds/dumpstate/dumpstate.c
+++ b/cmds/dumpstate/dumpstate.c
@@ -86,16 +86,18 @@
     dump_file("PAGETYPEINFO", "/proc/pagetypeinfo");
     dump_file("BUDDYINFO", "/proc/buddyinfo");
 
-    if (screenshot_path[0]) {
-        ALOGI("taking screenshot\n");
-        run_command(NULL, 5, SU_PATH, "root", "screenshot", screenshot_path, NULL);
-        ALOGI("wrote screenshot: %s\n", screenshot_path);
-    }
+    print_properties();
 
-    run_command("SYSTEM SETTINGS", 20, SU_PATH, "root", "sqlite3",
-            "/data/data/com.android.providers.settings/databases/settings.db",
-            "pragma user_version; select * from system; select * from secure;", NULL);
-    run_command("SYSTEM LOG", 20, "logcat", "-v", "threadtime", "-d", "*:v", NULL);
+    /* TODO: Make last_kmsg CAP_SYSLOG protected. b/5555691 */
+    dump_file("LAST KMSG", "/proc/last_kmsg");
+    do_dmesg();
+
+    dump_file("KERNEL WAKELOCKS", "/proc/wakelocks");
+    dump_file("KERNEL CPUFREQ", "/sys/devices/system/cpu/cpu0/cpufreq/stats/time_in_state");
+
+    run_command("PROCESSES", 10, "ps", "-P", NULL);
+    run_command("PROCESSES AND THREADS", 10, "ps", "-t", "-p", "-P", NULL);
+    run_command("LIBRANK", 10, "librank", NULL);
 
     /* show the traces we collected in main(), if that was done */
     if (dump_traces_path != NULL) {
@@ -114,11 +116,6 @@
         dump_file("VM TRACES AT LAST ANR", anr_traces_path);
     }
 
-    // dump_file("EVENT LOG TAGS", "/etc/event-log-tags");
-    run_command("EVENT LOG", 20, "logcat", "-b", "events", "-v", "threadtime", "-d", "*:v", NULL);
-    run_command("RADIO LOG", 20, "logcat", "-b", "radio", "-v", "threadtime", "-d", "*:v", NULL);
-
-    run_command("NETWORK INTERFACES", 10, SU_PATH, "root", "netcfg", NULL);
     dump_file("NETWORK DEV INFO", "/proc/net/dev");
     dump_file("QTAGUID NETWORK INTERFACES INFO", "/proc/net/xt_qtaguid/iface_stat_all");
     dump_file("QTAGUID CTRL INFO", "/proc/net/xt_qtaguid/ctrl");
@@ -126,6 +123,23 @@
 
     dump_file("NETWORK ROUTES", "/proc/net/route");
     dump_file("NETWORK ROUTES IPV6", "/proc/net/ipv6_route");
+
+    if (screenshot_path[0]) {
+        ALOGI("taking screenshot\n");
+        run_command(NULL, 5, SU_PATH, "root", "screenshot", screenshot_path, NULL);
+        ALOGI("wrote screenshot: %s\n", screenshot_path);
+    }
+
+    run_command("SYSTEM SETTINGS", 20, SU_PATH, "root", "sqlite3",
+            "/data/data/com.android.providers.settings/databases/settings.db",
+            "pragma user_version; select * from system; select * from secure;", NULL);
+
+    // dump_file("EVENT LOG TAGS", "/etc/event-log-tags");
+    run_command("SYSTEM LOG", 20, "logcat", "-v", "threadtime", "-d", "*:v", NULL);
+    run_command("EVENT LOG", 20, "logcat", "-b", "events", "-v", "threadtime", "-d", "*:v", NULL);
+    run_command("RADIO LOG", 20, "logcat", "-b", "radio", "-v", "threadtime", "-d", "*:v", NULL);
+
+    run_command("NETWORK INTERFACES", 10, SU_PATH, "root", "netcfg", NULL);
     run_command("IP RULES", 10, "ip", "rule", "show", NULL);
     run_command("IP RULES v6", 10, "ip", "-6", "rule", "show", NULL);
     run_command("ROUTE TABLE 60", 10, "ip", "route", "show", "table", "60", NULL);
@@ -172,20 +186,9 @@
         }
     }
 
-    print_properties();
-
-    do_dmesg();
-
-    dump_file("KERNEL WAKELOCKS", "/proc/wakelocks");
-    dump_file("KERNEL CPUFREQ", "/sys/devices/system/cpu/cpu0/cpufreq/stats/time_in_state");
-
     run_command("VOLD DUMP", 10, "vdc", "dump", NULL);
     run_command("SECURE CONTAINERS", 10, "vdc", "asec", "list", NULL);
 
-    run_command("PROCESSES", 10, "ps", "-P", NULL);
-    run_command("PROCESSES AND THREADS", 10, "ps", "-t", "-p", "-P", NULL);
-    run_command("LIBRANK", 10, "librank", NULL);
-
     dump_file("BINDER FAILED TRANSACTION LOG", "/sys/kernel/debug/binder/failed_transaction_log");
     dump_file("BINDER TRANSACTION LOG", "/sys/kernel/debug/binder/transaction_log");
     dump_file("BINDER TRANSACTIONS", "/sys/kernel/debug/binder/transactions");
@@ -197,8 +200,6 @@
     dump_file("PACKAGE SETTINGS", "/data/system/packages.xml");
     dump_file("PACKAGE UID ERRORS", "/data/system/uiderrors.txt");
 
-    /* TODO: Make last_kmsg CAP_SYSLOG protected. b/5555691 */
-    dump_file("LAST KMSG", "/proc/last_kmsg");
     run_command("LAST RADIO LOG", 10, "parse_radio_log", "/proc/last_radio_log", NULL);
     dump_file("LAST PANIC CONSOLE", "/data/dontpanic/apanic_console");
     dump_file("LAST PANIC THREADS", "/data/dontpanic/apanic_threads");
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index 1230c81..aa15f39 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -102,6 +102,8 @@
 import java.util.TimeZone;
 import java.util.regex.Pattern;
 
+import libcore.io.IoUtils;
+
 import dalvik.system.CloseGuard;
 
 final class SuperNotCalledException extends AndroidRuntimeException {
@@ -2357,41 +2359,47 @@
     }
 
     private void handleDumpService(DumpComponentInfo info) {
-        Service s = mServices.get(info.token);
-        if (s != null) {
-            PrintWriter pw = new PrintWriter(new FileOutputStream(info.fd.getFileDescriptor()));
-            s.dump(info.fd.getFileDescriptor(), pw, info.args);
-            pw.flush();
-            try {
-                info.fd.close();
-            } catch (IOException e) {
+        final StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskWrites();
+        try {
+            Service s = mServices.get(info.token);
+            if (s != null) {
+                PrintWriter pw = new PrintWriter(new FileOutputStream(info.fd.getFileDescriptor()));
+                s.dump(info.fd.getFileDescriptor(), pw, info.args);
+                pw.flush();
             }
+        } finally {
+            IoUtils.closeQuietly(info.fd);
+            StrictMode.setThreadPolicy(oldPolicy);
         }
     }
 
     private void handleDumpActivity(DumpComponentInfo info) {
-        ActivityClientRecord r = mActivities.get(info.token);
-        if (r != null && r.activity != null) {
-            PrintWriter pw = new PrintWriter(new FileOutputStream(info.fd.getFileDescriptor()));
-            r.activity.dump(info.prefix, info.fd.getFileDescriptor(), pw, info.args);
-            pw.flush();
-            try {
-                info.fd.close();
-            } catch (IOException e) {
+        final StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskWrites();
+        try {
+            ActivityClientRecord r = mActivities.get(info.token);
+            if (r != null && r.activity != null) {
+                PrintWriter pw = new PrintWriter(new FileOutputStream(info.fd.getFileDescriptor()));
+                r.activity.dump(info.prefix, info.fd.getFileDescriptor(), pw, info.args);
+                pw.flush();
             }
+        } finally {
+            IoUtils.closeQuietly(info.fd);
+            StrictMode.setThreadPolicy(oldPolicy);
         }
     }
 
     private void handleDumpProvider(DumpComponentInfo info) {
-        ProviderClientRecord r = mLocalProviders.get(info.token);
-        if (r != null && r.mLocalProvider != null) {
-            PrintWriter pw = new PrintWriter(new FileOutputStream(info.fd.getFileDescriptor()));
-            r.mLocalProvider.dump(info.fd.getFileDescriptor(), pw, info.args);
-            pw.flush();
-            try {
-                info.fd.close();
-            } catch (IOException e) {
+        final StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskWrites();
+        try {
+            ProviderClientRecord r = mLocalProviders.get(info.token);
+            if (r != null && r.mLocalProvider != null) {
+                PrintWriter pw = new PrintWriter(new FileOutputStream(info.fd.getFileDescriptor()));
+                r.mLocalProvider.dump(info.fd.getFileDescriptor(), pw, info.args);
+                pw.flush();
             }
+        } finally {
+            IoUtils.closeQuietly(info.fd);
+            StrictMode.setThreadPolicy(oldPolicy);
         }
     }
 
@@ -3751,6 +3759,7 @@
     }
 
     final void handleTrimMemory(int level) {
+        WindowManagerImpl.getDefault().trimMemory(level);
         ArrayList<ComponentCallbacks2> callbacks;
 
         synchronized (mPackages) {
@@ -3761,7 +3770,7 @@
         for (int i=0; i<N; i++) {
             callbacks.get(i).onTrimMemory(level);
         }
-        WindowManagerImpl.getDefault().trimMemory(level);
+        WindowManagerImpl.getDefault().terminateEgl();
     }
 
     private void setupGraphicsSupport(LoadedApk info) {
diff --git a/core/java/android/app/ContextImpl.java b/core/java/android/app/ContextImpl.java
index 6d5cce5..e348b87 100644
--- a/core/java/android/app/ContextImpl.java
+++ b/core/java/android/app/ContextImpl.java
@@ -785,7 +785,7 @@
     public boolean deleteDatabase(String name) {
         try {
             File f = validateFilePath(name, false);
-            return f.delete();
+            return SQLiteDatabase.deleteDatabase(f);
         } catch (Exception e) {
         }
         return false;
diff --git a/core/java/android/app/LoadedApk.java b/core/java/android/app/LoadedApk.java
index d9bbb4a..de9470e 100644
--- a/core/java/android/app/LoadedApk.java
+++ b/core/java/android/app/LoadedApk.java
@@ -512,6 +512,7 @@
 
     public void removeContextRegistrations(Context context,
             String who, String what) {
+        final boolean reportRegistrationLeaks = StrictMode.vmRegistrationLeaksEnabled();
         HashMap<BroadcastReceiver, LoadedApk.ReceiverDispatcher> rmap =
             mReceivers.remove(context);
         if (rmap != null) {
@@ -525,6 +526,9 @@
                         "call to unregisterReceiver()?");
                 leak.setStackTrace(rd.getLocation().getStackTrace());
                 Slog.e(ActivityThread.TAG, leak.getMessage(), leak);
+                if (reportRegistrationLeaks) {
+                    StrictMode.onIntentReceiverLeaked(leak);
+                }
                 try {
                     ActivityManagerNative.getDefault().unregisterReceiver(
                             rd.getIIntentReceiver());
@@ -546,6 +550,9 @@
                         + sd.getServiceConnection() + " that was originally bound here");
                 leak.setStackTrace(sd.getLocation().getStackTrace());
                 Slog.e(ActivityThread.TAG, leak.getMessage(), leak);
+                if (reportRegistrationLeaks) {
+                    StrictMode.onServiceConnectionLeaked(leak);
+                }
                 try {
                     ActivityManagerNative.getDefault().unbindService(
                             sd.getIServiceConnection());
diff --git a/core/java/android/content/ContentResolver.java b/core/java/android/content/ContentResolver.java
index 96a65da..7a612bc 100644
--- a/core/java/android/content/ContentResolver.java
+++ b/core/java/android/content/ContentResolver.java
@@ -1080,7 +1080,8 @@
     }
 
     /**
-     * Notify registered observers that a row was updated.
+     * Notify registered observers that a row was updated and attempt to sync changes
+     * to the network.
      * To register, call {@link #registerContentObserver(android.net.Uri , boolean, android.database.ContentObserver) registerContentObserver()}.
      * By default, CursorAdapter objects will get this notification.
      *
@@ -1098,6 +1099,9 @@
      * Notify registered observers that a row was updated.
      * To register, call {@link #registerContentObserver(android.net.Uri , boolean, android.database.ContentObserver) registerContentObserver()}.
      * By default, CursorAdapter objects will get this notification.
+     * If syncToNetwork is true, this will attempt to schedule a local sync using the sync
+     * adapter that's registered for the authority of the provided uri. No account will be
+     * passed to the sync adapter, so all matching accounts will be synchronized.
      *
      * @param uri The uri of the content that was changed.
      * @param observer The observer that originated the change, may be <code>null</null>.
@@ -1105,6 +1109,7 @@
      * has requested to receive self-change notifications by implementing
      * {@link ContentObserver#deliverSelfNotifications()} to return true.
      * @param syncToNetwork If true, attempt to sync the change to the network.
+     * @see #requestSync(android.accounts.Account, String, android.os.Bundle)
      */
     public void notifyChange(Uri uri, ContentObserver observer, boolean syncToNetwork) {
         try {
diff --git a/core/java/android/database/sqlite/SQLiteConnection.java b/core/java/android/database/sqlite/SQLiteConnection.java
index 1900301..d16f29f 100644
--- a/core/java/android/database/sqlite/SQLiteConnection.java
+++ b/core/java/android/database/sqlite/SQLiteConnection.java
@@ -208,11 +208,11 @@
                 mConfiguration.label,
                 SQLiteDebug.DEBUG_SQL_STATEMENTS, SQLiteDebug.DEBUG_SQL_TIME);
 
-        setSyncMode();
         setPageSize();
-        setAutoCheckpointInterval();
-        setJournalSizeLimit();
+        setSyncModeFromConfiguration();
         setJournalModeFromConfiguration();
+        setJournalSizeLimit();
+        setAutoCheckpointInterval();
         setLocaleFromConfiguration();
     }
 
@@ -236,12 +236,6 @@
         }
     }
 
-    private void setSyncMode() {
-        if (!mConfiguration.isInMemoryDb()) {
-            execute("PRAGMA synchronous=" + SQLiteGlobal.getSyncMode(), null, null);
-        }
-    }
-
     private void setPageSize() {
         if (!mConfiguration.isInMemoryDb()) {
             execute("PRAGMA page_size=" + SQLiteGlobal.getDefaultPageSize(), null, null);
@@ -262,6 +256,12 @@
         }
     }
 
+    private void setSyncModeFromConfiguration() {
+        if (!mConfiguration.isInMemoryDb()) {
+            execute("PRAGMA synchronous=" + mConfiguration.syncMode, null, null);
+        }
+    }
+
     private void setJournalModeFromConfiguration() {
         if (!mConfiguration.isInMemoryDb()) {
             String result = executeForString("PRAGMA journal_mode=" + mConfiguration.journalMode,
@@ -290,6 +290,8 @@
         }
 
         // Remember what changed.
+        boolean syncModeChanged = !configuration.syncMode.equalsIgnoreCase(
+                mConfiguration.syncMode);
         boolean journalModeChanged = !configuration.journalMode.equalsIgnoreCase(
                 mConfiguration.journalMode);
         boolean localeChanged = !configuration.locale.equals(mConfiguration.locale);
@@ -300,6 +302,11 @@
         // Update prepared statement cache size.
         mPreparedStatementCache.resize(configuration.maxSqlCacheSize);
 
+        // Update sync mode.
+        if (syncModeChanged) {
+            setSyncModeFromConfiguration();
+        }
+
         // Update journal mode.
         if (journalModeChanged) {
             setJournalModeFromConfiguration();
diff --git a/core/java/android/database/sqlite/SQLiteDatabase.java b/core/java/android/database/sqlite/SQLiteDatabase.java
index 515658f..04ee142 100644
--- a/core/java/android/database/sqlite/SQLiteDatabase.java
+++ b/core/java/android/database/sqlite/SQLiteDatabase.java
@@ -36,6 +36,7 @@
 import dalvik.system.CloseGuard;
 
 import java.io.File;
+import java.io.FileFilter;
 import java.util.ArrayList;
 import java.util.HashMap;
 import java.util.List;
@@ -678,6 +679,40 @@
     }
 
     /**
+     * Deletes a database including its journal file and other auxiliary files
+     * that may have been created by the database engine.
+     *
+     * @param file The database file path.
+     * @return True if the database was successfully deleted.
+     */
+    public static boolean deleteDatabase(File file) {
+        if (file == null) {
+            throw new IllegalArgumentException("file must not be null");
+        }
+
+        boolean deleted = false;
+        deleted |= file.delete();
+        deleted |= new File(file.getPath() + "-journal").delete();
+        deleted |= new File(file.getPath() + "-shm").delete();
+        deleted |= new File(file.getPath() + "-wal").delete();
+
+        File dir = file.getParentFile();
+        if (dir != null) {
+            final String prefix = file.getName() + "-mj";
+            final FileFilter filter = new FileFilter() {
+                @Override
+                public boolean accept(File candidate) {
+                    return candidate.getName().startsWith(prefix);
+                }
+            };
+            for (File masterJournal : dir.listFiles(filter)) {
+                deleted |= masterJournal.delete();
+            }
+        }
+        return deleted;
+    }
+
+    /**
      * Reopens the database in read-write mode.
      * If the database is already read-write, does nothing.
      *
@@ -1746,6 +1781,7 @@
 
             mIsWALEnabledLocked = true;
             mConfigurationLocked.maxConnectionPoolSize = SQLiteGlobal.getWALConnectionPoolSize();
+            mConfigurationLocked.syncMode = SQLiteGlobal.getWALSyncMode();
             mConfigurationLocked.journalMode = "WAL";
             mConnectionPoolLocked.reconfigure(mConfigurationLocked);
         }
@@ -1766,6 +1802,7 @@
 
             mIsWALEnabledLocked = false;
             mConfigurationLocked.maxConnectionPoolSize = 1;
+            mConfigurationLocked.syncMode = SQLiteGlobal.getDefaultSyncMode();
             mConfigurationLocked.journalMode = SQLiteGlobal.getDefaultJournalMode();
             mConnectionPoolLocked.reconfigure(mConfigurationLocked);
         }
diff --git a/core/java/android/database/sqlite/SQLiteDatabaseConfiguration.java b/core/java/android/database/sqlite/SQLiteDatabaseConfiguration.java
index 32a1bcb..efbcaca 100644
--- a/core/java/android/database/sqlite/SQLiteDatabaseConfiguration.java
+++ b/core/java/android/database/sqlite/SQLiteDatabaseConfiguration.java
@@ -85,6 +85,13 @@
     public Locale locale;
 
     /**
+     * The database synchronization mode.
+     *
+     * Default is {@link SQLiteGlobal#getDefaultSyncMode()}.
+     */
+    public String syncMode;
+
+    /**
      * The database journal mode.
      *
      * Default is {@link SQLiteGlobal#getDefaultJournalMode()}.
@@ -117,6 +124,7 @@
         maxConnectionPoolSize = 1;
         maxSqlCacheSize = 25;
         locale = Locale.getDefault();
+        syncMode = SQLiteGlobal.getDefaultSyncMode();
         journalMode = SQLiteGlobal.getDefaultJournalMode();
     }
 
@@ -154,6 +162,7 @@
         maxConnectionPoolSize = other.maxConnectionPoolSize;
         maxSqlCacheSize = other.maxSqlCacheSize;
         locale = other.locale;
+        syncMode = other.syncMode;
         journalMode = other.journalMode;
         customFunctions.clear();
         customFunctions.addAll(other.customFunctions);
diff --git a/core/java/android/database/sqlite/SQLiteGlobal.java b/core/java/android/database/sqlite/SQLiteGlobal.java
index af0cf45..5d8f80e 100644
--- a/core/java/android/database/sqlite/SQLiteGlobal.java
+++ b/core/java/android/database/sqlite/SQLiteGlobal.java
@@ -83,11 +83,19 @@
     }
 
     /**
-     * Gets the database synchronization mode.
+     * Gets the default database synchronization mode when WAL is not in use.
      */
-    public static String getSyncMode() {
+    public static String getDefaultSyncMode() {
         return Resources.getSystem().getString(
-                com.android.internal.R.string.db_sync_mode);
+                com.android.internal.R.string.db_default_sync_mode);
+    }
+
+    /**
+     * Gets the database synchronization mode when in WAL mode.
+     */
+    public static String getWALSyncMode() {
+        return Resources.getSystem().getString(
+                com.android.internal.R.string.db_wal_sync_mode);
     }
 
     /**
@@ -99,7 +107,7 @@
     }
 
     /**
-     * Gets the default connection pool size when in WAL mode.
+     * Gets the connection pool size when in WAL mode.
      */
     public static int getWALConnectionPoolSize() {
         return Math.max(2, Resources.getSystem().getInteger(
diff --git a/core/java/android/nfc/INfcAdapter.aidl b/core/java/android/nfc/INfcAdapter.aidl
index 61bc324..10da9ef 100644
--- a/core/java/android/nfc/INfcAdapter.aidl
+++ b/core/java/android/nfc/INfcAdapter.aidl
@@ -45,4 +45,6 @@
     void setForegroundNdefPush(in NdefMessage msg, in INdefPushCallback callback);
 
     void dispatch(in Tag tag);
+
+    void setP2pModes(int initatorModes, int targetModes);
 }
diff --git a/core/java/android/nfc/NfcAdapter.java b/core/java/android/nfc/NfcAdapter.java
index 5176857..23f96e3 100644
--- a/core/java/android/nfc/NfcAdapter.java
+++ b/core/java/android/nfc/NfcAdapter.java
@@ -903,6 +903,17 @@
     /**
      * @hide
      */
+    public void setP2pModes(int initiatorModes, int targetModes) {
+        try {
+            sService.setP2pModes(initiatorModes, targetModes);
+        } catch (RemoteException e) {
+            attemptDeadServiceRecovery(e);
+        }
+    }
+
+    /**
+     * @hide
+     */
     public INfcAdapterExtras getNfcAdapterExtrasInterface() {
         if (mContext == null) {
             throw new UnsupportedOperationException("You need a context on NfcAdapter to use the "
diff --git a/core/java/android/os/AsyncTask.java b/core/java/android/os/AsyncTask.java
index fd6bed7..97ed235 100644
--- a/core/java/android/os/AsyncTask.java
+++ b/core/java/android/os/AsyncTask.java
@@ -281,9 +281,6 @@
                             e.getCause());
                 } catch (CancellationException e) {
                     postResultIfNotInvoked(null);
-                } catch (Throwable t) {
-                    throw new RuntimeException("An error occured while executing "
-                            + "doInBackground()", t);
                 }
             }
         };
diff --git a/core/java/android/os/ParcelFileDescriptor.java b/core/java/android/os/ParcelFileDescriptor.java
index ac15d9c..3e90dfc 100644
--- a/core/java/android/os/ParcelFileDescriptor.java
+++ b/core/java/android/os/ParcelFileDescriptor.java
@@ -15,6 +15,7 @@
  */
 
 package android.os;
+import java.io.Closeable;
 import java.io.File;
 import java.io.FileDescriptor;
 import java.io.FileInputStream;
@@ -28,7 +29,7 @@
  * The FileDescriptor returned by {@link Parcel#readFileDescriptor}, allowing
  * you to close it when done with it.
  */
-public class ParcelFileDescriptor implements Parcelable {
+public class ParcelFileDescriptor implements Parcelable, Closeable {
     private final FileDescriptor mFileDescriptor;
     private boolean mClosed;
     //this field is to create wrapper for ParcelFileDescriptor using another
diff --git a/core/java/android/os/StrictMode.java b/core/java/android/os/StrictMode.java
index 99f58a0..a0ad9c0 100644
--- a/core/java/android/os/StrictMode.java
+++ b/core/java/android/os/StrictMode.java
@@ -20,7 +20,10 @@
 import android.app.ActivityThread;
 import android.app.ApplicationErrorReport;
 import android.app.IActivityManager;
+import android.content.BroadcastReceiver;
+import android.content.Context;
 import android.content.Intent;
+import android.content.ServiceConnection;
 import android.util.Log;
 import android.util.Printer;
 import android.util.Singleton;
@@ -195,9 +198,15 @@
      */
     private static final int DETECT_VM_INSTANCE_LEAKS = 0x1000;  // for VmPolicy
 
+    /**
+     * @hide
+     */
+    public static final int DETECT_VM_REGISTRATION_LEAKS = 0x2000;  // for VmPolicy
+
     private static final int ALL_VM_DETECT_BITS =
             DETECT_VM_CURSOR_LEAKS | DETECT_VM_CLOSABLE_LEAKS |
-            DETECT_VM_ACTIVITY_LEAKS | DETECT_VM_INSTANCE_LEAKS;
+            DETECT_VM_ACTIVITY_LEAKS | DETECT_VM_INSTANCE_LEAKS |
+            DETECT_VM_REGISTRATION_LEAKS;
 
     /**
      * @hide
@@ -618,8 +627,8 @@
              * but will likely expand in future releases.
              */
             public Builder detectAll() {
-                return enable(DETECT_VM_ACTIVITY_LEAKS |
-                        DETECT_VM_CURSOR_LEAKS | DETECT_VM_CLOSABLE_LEAKS);
+                return enable(DETECT_VM_ACTIVITY_LEAKS | DETECT_VM_CURSOR_LEAKS
+                        | DETECT_VM_CLOSABLE_LEAKS | DETECT_VM_REGISTRATION_LEAKS);
             }
 
             /**
@@ -648,6 +657,15 @@
             }
 
             /**
+             * Detect when a {@link BroadcastReceiver} or
+             * {@link ServiceConnection} is leaked during {@link Context}
+             * teardown.
+             */
+            public Builder detectLeakedRegistrationObjects() {
+                return enable(DETECT_VM_REGISTRATION_LEAKS);
+            }
+
+            /**
              * Crashes the whole process on violation.  This penalty runs at
              * the end of all enabled penalties so yo you'll still get
              * your logging or other violations before the process dies.
@@ -1499,6 +1517,13 @@
     /**
      * @hide
      */
+    public static boolean vmRegistrationLeaksEnabled() {
+        return (sVmPolicyMask & DETECT_VM_REGISTRATION_LEAKS) != 0;
+    }
+
+    /**
+     * @hide
+     */
     public static void onSqliteObjectLeaked(String message, Throwable originStack) {
         onVmPolicyViolation(message, originStack);
     }
@@ -1510,6 +1535,20 @@
         onVmPolicyViolation(null, originStack);
     }
 
+    /**
+     * @hide
+     */
+    public static void onIntentReceiverLeaked(Throwable originStack) {
+        onVmPolicyViolation(null, originStack);
+    }
+
+    /**
+     * @hide
+     */
+    public static void onServiceConnectionLeaked(Throwable originStack) {
+        onVmPolicyViolation(null, originStack);
+    }
+
     // Map from VM violation fingerprint to uptime millis.
     private static final HashMap<Integer, Long> sLastVmViolationTime = new HashMap<Integer, Long>();
 
diff --git a/core/java/android/provider/CalendarContract.java b/core/java/android/provider/CalendarContract.java
index fa59b32..83799c4 100644
--- a/core/java/android/provider/CalendarContract.java
+++ b/core/java/android/provider/CalendarContract.java
@@ -856,6 +856,17 @@
         public static final String EVENT_COLOR_KEY = "eventColor_index";
 
         /**
+         * This will be {@link #EVENT_COLOR} if it is not null; otherwise, this will be
+         * {@link Calendars#CALENDAR_COLOR}.
+         * Read-only value. To modify, write to {@link #EVENT_COLOR} or
+         * {@link Calendars#CALENDAR_COLOR} directly.
+         *<P>
+         *     Type: INTEGER
+         *</P>
+         */
+        public static final String DISPLAY_COLOR = "displayColor";
+
+        /**
          * The event status. Column name.
          * <P>Type: INTEGER (one of {@link #STATUS_TENTATIVE}...)</P>
          */
diff --git a/core/java/android/provider/MediaStore.java b/core/java/android/provider/MediaStore.java
index d3ad63d..6c6b118 100644
--- a/core/java/android/provider/MediaStore.java
+++ b/core/java/android/provider/MediaStore.java
@@ -1833,19 +1833,19 @@
             public static final String LANGUAGE = "language";
 
             /**
-             * The latitude where the image was captured.
+             * The latitude where the video was captured.
              * <P>Type: DOUBLE</P>
              */
             public static final String LATITUDE = "latitude";
 
             /**
-             * The longitude where the image was captured.
+             * The longitude where the video was captured.
              * <P>Type: DOUBLE</P>
              */
             public static final String LONGITUDE = "longitude";
 
             /**
-             * The date & time that the image was taken in units
+             * The date & time that the video was taken in units
              * of milliseconds since jan 1, 1970.
              * <P>Type: INTEGER</P>
              */
diff --git a/core/java/android/view/LayoutInflater.java b/core/java/android/view/LayoutInflater.java
index 9628d6b..3c0ee12 100644
--- a/core/java/android/view/LayoutInflater.java
+++ b/core/java/android/view/LayoutInflater.java
@@ -34,8 +34,8 @@
 import java.util.HashMap;
 
 /**
- * This class is used to instantiate layout XML file into its corresponding View
- * objects. It is never be used directly -- use
+ * Instantiates a layout XML file into its corresponding {@link android.view.View}
+ * objects. It is never used directly. Instead, use
  * {@link android.app.Activity#getLayoutInflater()} or
  * {@link Context#getSystemService} to retrieve a standard LayoutInflater instance
  * that is already hooked up to the current context and correctly configured
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java
index 294c31d..49f6023 100644
--- a/core/java/android/view/View.java
+++ b/core/java/android/view/View.java
@@ -956,28 +956,24 @@
     /**
      * Horizontal direction of this view is from Left to Right.
      * Use with {@link #setLayoutDirection}.
-     * {@hide}
      */
     public static final int LAYOUT_DIRECTION_LTR = 0x00000000;
 
     /**
      * Horizontal direction of this view is from Right to Left.
      * Use with {@link #setLayoutDirection}.
-     * {@hide}
      */
     public static final int LAYOUT_DIRECTION_RTL = 0x40000000;
 
     /**
      * Horizontal direction of this view is inherited from its parent.
      * Use with {@link #setLayoutDirection}.
-     * {@hide}
      */
     public static final int LAYOUT_DIRECTION_INHERIT = 0x80000000;
 
     /**
      * Horizontal direction of this view is from deduced from the default language
      * script for the locale. Use with {@link #setLayoutDirection}.
-     * {@hide}
      */
     public static final int LAYOUT_DIRECTION_LOCALE = 0xC0000000;
 
@@ -4833,8 +4829,6 @@
      *   {@link #LAYOUT_DIRECTION_INHERIT} or
      *   {@link #LAYOUT_DIRECTION_LOCALE}.
      * @attr ref android.R.styleable#View_layoutDirection
-     *
-     * @hide
      */
     @ViewDebug.ExportedProperty(category = "layout", mapping = {
         @ViewDebug.IntToString(from = LAYOUT_DIRECTION_LTR,     to = "LTR"),
@@ -4856,8 +4850,6 @@
      *   {@link #LAYOUT_DIRECTION_LOCALE}.
      *
      * @attr ref android.R.styleable#View_layoutDirection
-     *
-     * @hide
      */
     @RemotableViewMethod
     public void setLayoutDirection(int layoutDirection) {
@@ -4873,8 +4865,6 @@
      *
      * @return {@link #LAYOUT_DIRECTION_RTL} if the layout direction is RTL or returns
      * {@link #LAYOUT_DIRECTION_LTR} id the layout direction is not RTL.
-     *
-     * @hide
      */
     @ViewDebug.ExportedProperty(category = "layout", mapping = {
         @ViewDebug.IntToString(from = LAYOUT_DIRECTION_LTR,     to = "RESOLVED_DIRECTION_LTR"),
@@ -4891,8 +4881,6 @@
      * layout attribute and/or the inherited value from the parent.</p>
      *
      * @return true if the layout is right-to-left.
-     *
-     * @hide
      */
     @ViewDebug.ExportedProperty(category = "layout")
     public boolean isLayoutRtl() {
@@ -4905,8 +4893,6 @@
      * the framework should take special note to preserve when possible.
      *
      * @return true if the view has transient state
-     *
-     * @hide
      */
     @ViewDebug.ExportedProperty(category = "layout")
     public boolean hasTransientState() {
@@ -4918,8 +4904,6 @@
      * framework should attempt to preserve when possible.
      *
      * @param hasTransientState true if this view has transient state
-     *
-     * @hide
      */
     public void setHasTransientState(boolean hasTransientState) {
         if (hasTransientState() == hasTransientState) return;
@@ -9610,10 +9594,19 @@
 
         // Set to resolved
         mPrivateFlags2 |= LAYOUT_DIRECTION_RESOLVED;
+        onResolvedLayoutDirectionChanged();
     }
 
     /**
-     * Force padding depending on layout direction.
+     * Called when layout direction has been resolved.
+     *
+     * The default implementation does nothing.
+     */
+    public void onResolvedLayoutDirectionChanged() {
+    }
+
+    /**
+     * Resolve padding depending on layout direction.
      */
     public void resolvePadding() {
         // If the user specified the absolute padding (either with android:padding or
@@ -9657,7 +9650,7 @@
         mUserPaddingBottom = (mUserPaddingBottom >= 0) ? mUserPaddingBottom : mPaddingBottom;
 
         recomputePadding();
-        onResolvePadding(resolvedLayoutDirection);
+        onPaddingChanged(resolvedLayoutDirection);
     }
 
     /**
@@ -9668,15 +9661,15 @@
      * @param layoutDirection the direction of the layout
      *
      */
-    public void onResolvePadding(int layoutDirection) {
+    public void onPaddingChanged(int layoutDirection) {
     }
 
     /**
-     * Return true if layout direction resolution can be done
+     * Check if layout direction resolution can be done.
      *
-     * @hide
+     * @return true if layout direction resolution can be done otherwise return false.
      */
-    protected boolean canResolveLayoutDirection() {
+    public boolean canResolveLayoutDirection() {
         switch (getLayoutDirection()) {
             case LAYOUT_DIRECTION_INHERIT:
                 return (mParent != null);
@@ -9686,28 +9679,33 @@
     }
 
     /**
-     * Reset the resolved layout direction.
-     *
-     * Subclasses need to override this method to clear cached information that depends on the
-     * resolved layout direction, or to inform child views that inherit their layout direction.
-     * Overrides must also call the superclass implementation at the start of their implementation.
-     *
-     * @hide
+     * Reset the resolved layout direction. Will call {@link View#onResolvedLayoutDirectionReset}
+     * when reset is done.
      */
-    protected void resetResolvedLayoutDirection() {
-        // Reset the layout direction resolution
+    public void resetResolvedLayoutDirection() {
+        // Reset the current View resolution
         mPrivateFlags2 &= ~LAYOUT_DIRECTION_RESOLVED;
+        onResolvedLayoutDirectionReset();
         // Reset also the text direction
         resetResolvedTextDirection();
     }
 
     /**
-     * Check if a Locale is corresponding to a RTL script.
+     * Called during reset of resolved layout direction.
+     *
+     * Subclasses need to override this method to clear cached information that depends on the
+     * resolved layout direction, or to inform child views that inherit their layout direction.
+     *
+     * The default implementation does nothing.
+     */
+    public void onResolvedLayoutDirectionReset() {
+    }
+
+    /**
+     * Check if a Locale uses an RTL script.
      *
      * @param locale Locale to check
-     * @return true if a Locale is corresponding to a RTL script.
-     *
-     * @hide
+     * @return true if the Locale uses an RTL script.
      */
     protected static boolean isLayoutDirectionRtl(Locale locale) {
         return (LAYOUT_DIRECTION_RTL == LocaleUtil.getLayoutDirectionFromLocale(locale));
@@ -11856,8 +11854,6 @@
     * Return the layout direction of a given Drawable.
     *
     * @param who the Drawable to query
-    *
-    * @hide
     */
     public int getResolvedLayoutDirection(Drawable who) {
         return (who == mBGDrawable) ? getResolvedLayoutDirection() : LAYOUT_DIRECTION_DEFAULT;
@@ -13050,7 +13046,7 @@
 
         if (mParent != null) {
             if (mLayoutParams != null) {
-                mLayoutParams.resolveWithDirection(getResolvedLayoutDirection());
+                mLayoutParams.onResolveLayoutDirection(getResolvedLayoutDirection());
             }
             if (!mParent.isLayoutRequested()) {
                 mParent.requestLayout();
@@ -14146,8 +14142,8 @@
     }
 
     /**
-     * Resolve the text direction. Will call {@link View#onResolveTextDirection()} when resolution
-     * is done.
+     * Resolve the text direction. Will call {@link View#onResolvedTextDirectionChanged} when
+     * resolution is done.
      */
     public void resolveTextDirection() {
         if (mResolvedTextDirection != TEXT_DIRECTION_INHERIT) {
@@ -14161,24 +14157,26 @@
         } else {
             mResolvedTextDirection = TEXT_DIRECTION_FIRST_STRONG;
         }
-        onResolveTextDirection();
+        onResolvedTextDirectionChanged();
     }
 
     /**
      * Called when text direction has been resolved. Subclasses that care about text direction
-     * resolution should override this method. The default implementation does nothing.
+     * resolution should override this method.
+     *
+     * The default implementation does nothing.
      */
-    public void onResolveTextDirection() {
+    public void onResolvedTextDirectionChanged() {
     }
 
     /**
      * Reset resolved text direction. Text direction can be resolved with a call to
-     * getResolvedTextDirection(). Will call {@link View#onResetResolvedTextDirection()} when
+     * getResolvedTextDirection(). Will call {@link View#onResolvedTextDirectionReset} when
      * reset is done.
      */
     public void resetResolvedTextDirection() {
         mResolvedTextDirection = TEXT_DIRECTION_INHERIT;
-        onResetResolvedTextDirection();
+        onResolvedTextDirectionReset();
     }
 
     /**
@@ -14186,7 +14184,7 @@
      * override this method and do a reset of the text direction of their children. The default
      * implementation does nothing.
      */
-    public void onResetResolvedTextDirection() {
+    public void onResolvedTextDirectionReset() {
     }
 
     //
diff --git a/core/java/android/view/ViewGroup.java b/core/java/android/view/ViewGroup.java
index 05c2b57..0c63286 100644
--- a/core/java/android/view/ViewGroup.java
+++ b/core/java/android/view/ViewGroup.java
@@ -1041,9 +1041,8 @@
 
     /**
      * {@inheritDoc}
-     *
-     * !!! TODO: write real docs
      */
+    // TODO: Write real docs
     @Override
     public boolean dispatchDragEvent(DragEvent event) {
         boolean retval = false;
@@ -4921,9 +4920,7 @@
     }
 
     @Override
-    protected void resetResolvedLayoutDirection() {
-        super.resetResolvedLayoutDirection();
-
+    public void onResolvedLayoutDirectionReset() {
         // Take care of resetting the children resolution too
         final int count = getChildCount();
         for (int i = 0; i < count; i++) {
@@ -4935,7 +4932,7 @@
     }
 
     @Override
-    public void onResetResolvedTextDirection() {
+    public void onResolvedTextDirectionReset() {
         // Take care of resetting the children resolution too
         final int count = getChildCount();
         for (int i = 0; i < count; i++) {
@@ -5124,10 +5121,8 @@
          *
          * {@link View#LAYOUT_DIRECTION_LTR}
          * {@link View#LAYOUT_DIRECTION_RTL}
-         *
-         * @hide
          */
-        protected void resolveWithDirection(int layoutDirection) {
+        public void onResolveLayoutDirection(int layoutDirection) {
         }
 
         /**
@@ -5378,12 +5373,10 @@
 
         /**
          * This will be called by {@link android.view.View#requestLayout()}. Left and Right margins
-         * maybe overriden depending on layout direction.
-         *
-         * @hide
+         * may be overridden depending on layout direction.
          */
         @Override
-        protected void resolveWithDirection(int layoutDirection) {
+        public void onResolveLayoutDirection(int layoutDirection) {
             switch(layoutDirection) {
                 case View.LAYOUT_DIRECTION_RTL:
                     leftMargin = (endMargin > DEFAULT_RELATIVE) ? endMargin : leftMargin;
diff --git a/core/java/android/view/WindowManagerImpl.java b/core/java/android/view/WindowManagerImpl.java
index 6dbdedb..d482b35 100644
--- a/core/java/android/view/WindowManagerImpl.java
+++ b/core/java/android/view/WindowManagerImpl.java
@@ -105,6 +105,7 @@
     private View[] mViews;
     private ViewRootImpl[] mRoots;
     private WindowManager.LayoutParams[] mParams;
+    private boolean mNeedsEglTerminate;
 
     private final static Object sLock = new Object();
     private final static WindowManagerImpl sWindowManager = new WindowManagerImpl();
@@ -436,8 +437,6 @@
                 case ComponentCallbacks2.TRIM_MEMORY_MODERATE:
                     // On low and medium end gfx devices
                     if (!ActivityManager.isHighEndGfx(getDefaultDisplay())) {
-                        // Force a full memory flush
-                        HardwareRenderer.trimMemory(ComponentCallbacks2.TRIM_MEMORY_COMPLETE);
                         // Destroy all hardware surfaces and resources associated to
                         // known windows
                         synchronized (this) {
@@ -447,8 +446,9 @@
                                 mRoots[i].terminateHardwareResources();
                             }
                         }
-                        // Terminate the hardware renderer to free all resources
-                        ManagedEGLContext.doTerminate();
+                        // Force a full memory flush
+                        HardwareRenderer.trimMemory(ComponentCallbacks2.TRIM_MEMORY_COMPLETE);
+                        mNeedsEglTerminate = true;
                         break;
                     }
                     // high end gfx devices fall through to next case
@@ -461,6 +461,16 @@
     /**
      * @hide
      */
+    public void terminateEgl() {
+        if (mNeedsEglTerminate) {
+            ManagedEGLContext.doTerminate();
+            mNeedsEglTerminate = false;
+        }
+    }
+
+    /**
+     * @hide
+     */
     public void trimLocalMemory() {
         synchronized (this) {
             if (mViews == null) return;
diff --git a/core/java/android/webkit/AccessibilityInjector.java b/core/java/android/webkit/AccessibilityInjector.java
index db66305..11bd815 100644
--- a/core/java/android/webkit/AccessibilityInjector.java
+++ b/core/java/android/webkit/AccessibilityInjector.java
@@ -79,8 +79,8 @@
     private static ArrayList<AccessibilityWebContentKeyBinding> sBindings =
         new ArrayList<AccessibilityWebContentKeyBinding>();
 
-    // handle to the WebView this injector is associated with.
-    private final WebView mWebView;
+    // handle to the WebViewClassic this injector is associated with.
+    private final WebViewClassic mWebView;
 
     // events scheduled for sending as soon as we receive the selected text
     private final Stack<AccessibilityEvent> mScheduledEventStack = new Stack<AccessibilityEvent>();
@@ -98,11 +98,11 @@
     private int mLastDirection;
 
     /**
-     * Creates a new injector associated with a given {@link WebView}.
+     * Creates a new injector associated with a given {@link WebViewClassic}.
      *
-     * @param webView The associated WebView.
+     * @param webView The associated WebViewClassic.
      */
-    public AccessibilityInjector(WebView webView) {
+    public AccessibilityInjector(WebViewClassic webView) {
         mWebView = webView;
         ensureWebContentKeyBindings();
     }
@@ -327,7 +327,7 @@
         AccessibilityEvent event = AccessibilityEvent.obtain(AccessibilityEvent.TYPE_VIEW_SELECTED);
         event.setClassName(mWebView.getClass().getName());
         event.setPackageName(mWebView.getContext().getPackageName());
-        event.setEnabled(mWebView.isEnabled());
+        event.setEnabled(mWebView.getWebView().isEnabled());
         return event;
     }
 
diff --git a/core/java/android/webkit/BrowserFrame.java b/core/java/android/webkit/BrowserFrame.java
index 8ccc59c7..f09e29d 100644
--- a/core/java/android/webkit/BrowserFrame.java
+++ b/core/java/android/webkit/BrowserFrame.java
@@ -70,7 +70,7 @@
     private final static int MAX_OUTSTANDING_REQUESTS = 300;
 
     private final CallbackProxy mCallbackProxy;
-    private final WebSettings mSettings;
+    private final WebSettingsClassic mSettings;
     private final Context mContext;
     private final WebViewDatabase mDatabase;
     private final WebViewCore mWebViewCore;
@@ -200,7 +200,7 @@
      * XXX: Called by WebCore thread.
      */
     public BrowserFrame(Context context, WebViewCore w, CallbackProxy proxy,
-            WebSettings settings, Map<String, Object> javascriptInterfaces) {
+            WebSettingsClassic settings, Map<String, Object> javascriptInterfaces) {
 
         Context appContext = context.getApplicationContext();
 
diff --git a/core/java/android/webkit/CallbackProxy.java b/core/java/android/webkit/CallbackProxy.java
index 3a05bca..2afb841 100644
--- a/core/java/android/webkit/CallbackProxy.java
+++ b/core/java/android/webkit/CallbackProxy.java
@@ -61,8 +61,8 @@
     private volatile WebViewClient mWebViewClient;
     // Instance of WebChromeClient for handling all chrome functions.
     private volatile WebChromeClient mWebChromeClient;
-    // Instance of WebView for handling UI requests.
-    private final WebView mWebView;
+    // Instance of WebViewClassic for handling UI requests.
+    private final WebViewClassic mWebView;
     // Client registered callback listener for download events
     private volatile DownloadListener mDownloadListener;
     // Keep track of multiple progress updates.
@@ -148,13 +148,19 @@
     /**
      * Construct a new CallbackProxy.
      */
-    public CallbackProxy(Context context, WebView w) {
+    public CallbackProxy(Context context, WebViewClassic w) {
         // Used to start a default activity.
         mContext = context;
         mWebView = w;
         mBackForwardList = new WebBackForwardList(this);
     }
 
+    protected void shutdown() {
+        setWebViewClient(null);
+        setWebChromeClient(null);
+        removeCallbacksAndMessages(null);
+    }
+
     /**
      * Set the WebViewClient.
      * @param client An implementation of WebViewClient.
@@ -221,7 +227,7 @@
         }
         boolean override = false;
         if (mWebViewClient != null) {
-            override = mWebViewClient.shouldOverrideUrlLoading(mWebView,
+            override = mWebViewClient.shouldOverrideUrlLoading(mWebView.getWebView(),
                     overrideUrl);
         } else {
             Intent intent = new Intent(Intent.ACTION_VIEW,
@@ -248,7 +254,7 @@
      */
     public boolean uiOverrideKeyEvent(KeyEvent event) {
         if (mWebViewClient != null) {
-            return mWebViewClient.shouldOverrideKeyEvent(mWebView, event);
+            return mWebViewClient.shouldOverrideKeyEvent(mWebView.getWebView(), event);
         }
         return false;
     }
@@ -264,7 +270,8 @@
                 String startedUrl = msg.getData().getString("url");
                 mWebView.onPageStarted(startedUrl);
                 if (mWebViewClient != null) {
-                    mWebViewClient.onPageStarted(mWebView, startedUrl, (Bitmap) msg.obj);
+                    mWebViewClient.onPageStarted(mWebView.getWebView(), startedUrl,
+                            (Bitmap) msg.obj);
                 }
                 break;
 
@@ -272,26 +279,26 @@
                 String finishedUrl = (String) msg.obj;
                 mWebView.onPageFinished(finishedUrl);
                 if (mWebViewClient != null) {
-                    mWebViewClient.onPageFinished(mWebView, finishedUrl);
+                    mWebViewClient.onPageFinished(mWebView.getWebView(), finishedUrl);
                 }
                 break;
 
             case RECEIVED_ICON:
                 if (mWebChromeClient != null) {
-                    mWebChromeClient.onReceivedIcon(mWebView, (Bitmap) msg.obj);
+                    mWebChromeClient.onReceivedIcon(mWebView.getWebView(), (Bitmap) msg.obj);
                 }
                 break;
 
             case RECEIVED_TOUCH_ICON_URL:
                 if (mWebChromeClient != null) {
-                    mWebChromeClient.onReceivedTouchIconUrl(mWebView,
+                    mWebChromeClient.onReceivedTouchIconUrl(mWebView.getWebView(),
                             (String) msg.obj, msg.arg1 == 1);
                 }
                 break;
 
             case RECEIVED_TITLE:
                 if (mWebChromeClient != null) {
-                    mWebChromeClient.onReceivedTitle(mWebView,
+                    mWebChromeClient.onReceivedTitle(mWebView.getWebView(),
                             (String) msg.obj);
                 }
                 break;
@@ -301,7 +308,7 @@
                     int reasonCode = msg.arg1;
                     final String description  = msg.getData().getString("description");
                     final String failUrl  = msg.getData().getString("failingUrl");
-                    mWebViewClient.onReceivedError(mWebView, reasonCode,
+                    mWebViewClient.onReceivedError(mWebView.getWebView(), reasonCode,
                             description, failUrl);
                 }
                 break;
@@ -312,7 +319,7 @@
                 Message dontResend =
                         (Message) msg.getData().getParcelable("dontResend");
                 if (mWebViewClient != null) {
-                    mWebViewClient.onFormResubmission(mWebView, dontResend,
+                    mWebViewClient.onFormResubmission(mWebView.getWebView(), dontResend,
                             resend);
                 } else {
                     dontResend.sendToTarget();
@@ -335,7 +342,7 @@
                     HttpAuthHandler handler = (HttpAuthHandler) msg.obj;
                     String host = msg.getData().getString("host");
                     String realm = msg.getData().getString("realm");
-                    mWebViewClient.onReceivedHttpAuthRequest(mWebView, handler,
+                    mWebViewClient.onReceivedHttpAuthRequest(mWebView.getWebView(), handler,
                             host, realm);
                 }
                 break;
@@ -344,7 +351,7 @@
                 if (mWebViewClient != null) {
                     HashMap<String, Object> map =
                         (HashMap<String, Object>) msg.obj;
-                    mWebViewClient.onReceivedSslError(mWebView,
+                    mWebViewClient.onReceivedSslError(mWebView.getWebView(),
                             (SslErrorHandler) map.get("handler"),
                             (SslError) map.get("error"));
                 }
@@ -352,7 +359,7 @@
 
             case PROCEEDED_AFTER_SSL_ERROR:
                 if (mWebViewClient != null) {
-                    mWebViewClient.onProceededAfterSslError(mWebView,
+                    mWebViewClient.onProceededAfterSslError(mWebView.getWebView(),
                             (SslError) msg.obj);
                 }
                 break;
@@ -361,7 +368,7 @@
                 if (mWebViewClient != null) {
                     HashMap<String, Object> map =
                         (HashMap<String, Object>) msg.obj;
-                    mWebViewClient.onReceivedClientCertRequest(mWebView,
+                    mWebViewClient.onReceivedClientCertRequest(mWebView.getWebView(),
                             (ClientCertRequestHandler) map.get("handler"),
                             (String) map.get("host_and_port"));
                 }
@@ -373,7 +380,7 @@
                 // changed.
                 synchronized (this) {
                     if (mWebChromeClient != null) {
-                        mWebChromeClient.onProgressChanged(mWebView,
+                        mWebChromeClient.onProgressChanged(mWebView.getWebView(),
                                 mLatestProgress);
                     }
                     mProgressUpdatePending = false;
@@ -382,14 +389,14 @@
 
             case UPDATE_VISITED:
                 if (mWebViewClient != null) {
-                    mWebViewClient.doUpdateVisitedHistory(mWebView,
+                    mWebViewClient.doUpdateVisitedHistory(mWebView.getWebView(),
                             (String) msg.obj, msg.arg1 != 0);
                 }
                 break;
 
             case LOAD_RESOURCE:
                 if (mWebViewClient != null) {
-                    mWebViewClient.onLoadResource(mWebView, (String) msg.obj);
+                    mWebViewClient.onLoadResource(mWebView.getWebView(), (String) msg.obj);
                 }
                 break;
 
@@ -409,7 +416,7 @@
 
             case CREATE_WINDOW:
                 if (mWebChromeClient != null) {
-                    if (!mWebChromeClient.onCreateWindow(mWebView,
+                    if (!mWebChromeClient.onCreateWindow(mWebView.getWebView(),
                                 msg.arg1 == 1, msg.arg2 == 1,
                                 (Message) msg.obj)) {
                         synchronized (this) {
@@ -422,13 +429,13 @@
 
             case REQUEST_FOCUS:
                 if (mWebChromeClient != null) {
-                    mWebChromeClient.onRequestFocus(mWebView);
+                    mWebChromeClient.onRequestFocus(mWebView.getWebView());
                 }
                 break;
 
             case CLOSE_WINDOW:
                 if (mWebChromeClient != null) {
-                    mWebChromeClient.onCloseWindow((WebView) msg.obj);
+                    mWebChromeClient.onCloseWindow(((WebViewClassic) msg.obj).getWebView());
                 }
                 break;
 
@@ -449,7 +456,7 @@
 
             case ASYNC_KEYEVENTS:
                 if (mWebViewClient != null) {
-                    mWebViewClient.onUnhandledKeyEvent(mWebView,
+                    mWebViewClient.onUnhandledKeyEvent(mWebView.getWebView(),
                             (KeyEvent) msg.obj);
                 }
                 break;
@@ -516,7 +523,7 @@
                     final JsResult res = (JsResult) msg.obj;
                     String message = msg.getData().getString("message");
                     String url = msg.getData().getString("url");
-                    if (!mWebChromeClient.onJsAlert(mWebView, url, message,
+                    if (!mWebChromeClient.onJsAlert(mWebView.getWebView(), url, message,
                             res)) {
                         if (!canShowAlertDialog()) {
                             res.cancel();
@@ -552,7 +559,7 @@
                     final JsResult res = (JsResult) msg.obj;
                     String message = msg.getData().getString("message");
                     String url = msg.getData().getString("url");
-                    if (!mWebChromeClient.onJsConfirm(mWebView, url, message,
+                    if (!mWebChromeClient.onJsConfirm(mWebView.getWebView(), url, message,
                             res)) {
                         if (!canShowAlertDialog()) {
                             res.cancel();
@@ -597,7 +604,7 @@
                     String message = msg.getData().getString("message");
                     String defaultVal = msg.getData().getString("default");
                     String url = msg.getData().getString("url");
-                    if (!mWebChromeClient.onJsPrompt(mWebView, url, message,
+                    if (!mWebChromeClient.onJsPrompt(mWebView.getWebView(), url, message,
                                 defaultVal, res)) {
                         if (!canShowAlertDialog()) {
                             res.cancel();
@@ -653,7 +660,7 @@
                     final JsResult res = (JsResult) msg.obj;
                     String message = msg.getData().getString("message");
                     String url = msg.getData().getString("url");
-                    if (!mWebChromeClient.onJsBeforeUnload(mWebView, url,
+                    if (!mWebChromeClient.onJsBeforeUnload(mWebView.getWebView(), url,
                             message, res)) {
                         if (!canShowAlertDialog()) {
                             res.cancel();
@@ -710,7 +717,7 @@
 
             case SCALE_CHANGED:
                 if (mWebViewClient != null) {
-                    mWebViewClient.onScaleChanged(mWebView, msg.getData()
+                    mWebViewClient.onScaleChanged(mWebView.getWebView(), msg.getData()
                             .getFloat("old"), msg.getData().getFloat("new"));
                 }
                 break;
@@ -817,7 +824,7 @@
                     String realm = msg.getData().getString("realm");
                     String account = msg.getData().getString("account");
                     String args = msg.getData().getString("args");
-                    mWebViewClient.onReceivedLoginRequest(mWebView, realm,
+                    mWebViewClient.onReceivedLoginRequest(mWebView.getWebView(), realm,
                             account, args);
                 }
                 break;
@@ -1074,7 +1081,7 @@
         }
         // Note: This method does _not_ send a message.
         WebResourceResponse r =
-                mWebViewClient.shouldInterceptRequest(mWebView, url);
+                mWebViewClient.shouldInterceptRequest(mWebView.getWebView(), url);
         if (r == null) {
             sendMessage(obtainMessage(LOAD_RESOURCE, url));
         }
@@ -1219,7 +1226,8 @@
             return null;
         }
 
-        WebView.WebViewTransport transport = mWebView.new WebViewTransport();
+        WebView.WebViewTransport transport =
+            mWebView.getWebView().new WebViewTransport();
         final Message msg = obtainMessage(NOTIFY);
         msg.obj = transport;
         synchronized (this) {
@@ -1234,7 +1242,7 @@
             }
         }
 
-        WebView w = transport.getWebView();
+        WebViewClassic w = WebViewClassic.fromWebView(transport.getWebView());
         if (w != null) {
             WebViewCore core = w.getWebViewCore();
             // If WebView.destroy() has been called, core may be null.  Skip
@@ -1257,7 +1265,7 @@
         sendEmptyMessage(REQUEST_FOCUS);
     }
 
-    public void onCloseWindow(WebView window) {
+    public void onCloseWindow(WebViewClassic window) {
         // Do an unsynchronized quick check to avoid posting if no callback has
         // been set.
         if (mWebChromeClient == null) {
diff --git a/core/java/android/webkit/FindActionModeCallback.java b/core/java/android/webkit/FindActionModeCallback.java
index 10b0885..964cf3e 100644
--- a/core/java/android/webkit/FindActionModeCallback.java
+++ b/core/java/android/webkit/FindActionModeCallback.java
@@ -38,7 +38,7 @@
     private View mCustomView;
     private EditText mEditText;
     private TextView mMatches;
-    private WebView mWebView;
+    private WebViewClassic mWebView;
     private InputMethodManager mInput;
     private Resources mResources;
     private boolean mMatchesFound;
@@ -90,7 +90,7 @@
      * Set the WebView to search.  Must be non null, and set before calling
      * startActionMode.
      */
-    void setWebView(WebView webView) {
+    void setWebView(WebViewClassic webView) {
         if (null == webView) {
             throw new AssertionError("WebView supplied to "
                     + "FindActionModeCallback cannot be null");
@@ -218,7 +218,7 @@
     public void onDestroyActionMode(ActionMode mode) {
         mActionMode = null;
         mWebView.notifyFindDialogDismissed();
-        mInput.hideSoftInputFromWindow(mWebView.getWindowToken(), 0);
+        mInput.hideSoftInputFromWindow(mWebView.getWebView().getWindowToken(), 0);
     }
 
     @Override
@@ -232,7 +232,7 @@
             throw new AssertionError(
                     "No WebView for FindActionModeCallback::onActionItemClicked");
         }
-        mInput.hideSoftInputFromWindow(mWebView.getWindowToken(), 0);
+        mInput.hideSoftInputFromWindow(mWebView.getWebView().getWindowToken(), 0);
         switch(item.getItemId()) {
             case com.android.internal.R.id.find_prev:
                 findNext(false);
diff --git a/core/java/android/webkit/GeolocationService.java b/core/java/android/webkit/GeolocationService.java
index 91de1d8..225053b 100755
--- a/core/java/android/webkit/GeolocationService.java
+++ b/core/java/android/webkit/GeolocationService.java
@@ -24,7 +24,6 @@
 import android.location.LocationProvider;
 import android.os.Bundle;
 import android.util.Log;
-import android.webkit.WebView;
 import android.webkit.WebViewCore;
 
 
diff --git a/core/java/android/webkit/HTML5Audio.java b/core/java/android/webkit/HTML5Audio.java
index aedecf0..8e1f573 100644
--- a/core/java/android/webkit/HTML5Audio.java
+++ b/core/java/android/webkit/HTML5Audio.java
@@ -92,7 +92,7 @@
     private class IsPrivateBrowsingEnabledGetter {
         private boolean mIsReady;
         private boolean mIsPrivateBrowsingEnabled;
-        IsPrivateBrowsingEnabledGetter(Looper uiThreadLooper, final WebView webView) {
+        IsPrivateBrowsingEnabledGetter(Looper uiThreadLooper, final WebViewClassic webView) {
             new Handler(uiThreadLooper).post(new Runnable() {
                 @Override
                 public void run() {
diff --git a/core/java/android/webkit/HTML5VideoFullScreen.java b/core/java/android/webkit/HTML5VideoFullScreen.java
index bc0557e..fac549d 100644
--- a/core/java/android/webkit/HTML5VideoFullScreen.java
+++ b/core/java/android/webkit/HTML5VideoFullScreen.java
@@ -236,7 +236,7 @@
 
     @Override
     public void enterFullScreenVideoState(int layerId,
-            HTML5VideoViewProxy proxy, WebView webView) {
+            HTML5VideoViewProxy proxy, WebViewClassic webView) {
         mFullScreenMode = FULLSCREEN_SURFACECREATING;
         mCurrentBufferPercentage = 0;
         mPlayer.setOnBufferingUpdateListener(mBufferingUpdateListener);
diff --git a/core/java/android/webkit/HTML5VideoView.java b/core/java/android/webkit/HTML5VideoView.java
index 73166cb..0d3b755 100644
--- a/core/java/android/webkit/HTML5VideoView.java
+++ b/core/java/android/webkit/HTML5VideoView.java
@@ -280,7 +280,7 @@
     // screen mode. Some are specific to one type, but currently are called
     // directly from the proxy.
     public void enterFullScreenVideoState(int layerId,
-            HTML5VideoViewProxy proxy, WebView webView) {
+            HTML5VideoViewProxy proxy, WebViewClassic webView) {
     }
 
     public boolean isFullScreenMode() {
diff --git a/core/java/android/webkit/HTML5VideoViewProxy.java b/core/java/android/webkit/HTML5VideoViewProxy.java
index d306c86..1644b06 100644
--- a/core/java/android/webkit/HTML5VideoViewProxy.java
+++ b/core/java/android/webkit/HTML5VideoViewProxy.java
@@ -75,8 +75,8 @@
     int mNativePointer;
     // The handler for WebCore thread messages;
     private Handler mWebCoreHandler;
-    // The WebView instance that created this view.
-    private WebView mWebView;
+    // The WebViewClassic instance that created this view.
+    private WebViewClassic mWebView;
     // The poster image to be shown when the video is not playing.
     // This ref prevents the bitmap from being GC'ed.
     private Bitmap mPoster;
@@ -142,7 +142,7 @@
         }
 
         public static void enterFullScreenVideo(int layerId, String url,
-                HTML5VideoViewProxy proxy, WebView webView) {
+                HTML5VideoViewProxy proxy, WebViewClassic webView) {
                 // Save the inline video info and inherit it in the full screen
                 int savePosition = 0;
                 if (mHTML5VideoView != null) {
@@ -163,7 +163,7 @@
         }
 
         public static void exitFullScreenVideo(HTML5VideoViewProxy proxy,
-                WebView webView) {
+                WebViewClassic webView) {
             if (!mHTML5VideoView.fullScreenExited() && mHTML5VideoView.isFullScreenMode()) {
                 WebChromeClient client = webView.getWebChromeClient();
                 if (client != null) {
@@ -551,7 +551,7 @@
      * @param webView is the WebView that hosts the video.
      * @param nativePtr is the C++ pointer to the MediaPlayerPrivate object.
      */
-    private HTML5VideoViewProxy(WebView webView, int nativePtr) {
+    private HTML5VideoViewProxy(WebViewClassic webView, int nativePtr) {
         // This handler is for the main (UI) thread.
         super(Looper.getMainLooper());
         // Save the WebView object.
@@ -721,7 +721,7 @@
         return new HTML5VideoViewProxy(webViewCore.getWebView(), nativePtr);
     }
 
-    /* package */ WebView getWebView() {
+    /* package */ WebViewClassic getWebView() {
         return mWebView;
     }
 
diff --git a/core/java/android/webkit/JWebCoreJavaBridge.java b/core/java/android/webkit/JWebCoreJavaBridge.java
index b498435..e6eaa14 100644
--- a/core/java/android/webkit/JWebCoreJavaBridge.java
+++ b/core/java/android/webkit/JWebCoreJavaBridge.java
@@ -43,10 +43,10 @@
     private boolean mTimerPaused;
     private boolean mHasDeferredTimers;
 
-    // keep track of the main WebView attached to the current window so that we
+    // keep track of the main WebViewClassic attached to the current window so that we
     // can get the proper Context.
-    private static WeakReference<WebView> sCurrentMainWebView =
-            new WeakReference<WebView>(null);
+    private static WeakReference<WebViewClassic> sCurrentMainWebView =
+            new WeakReference<WebViewClassic>(null);
 
     /* package */
     static final int REFRESH_PLUGINS = 100;
@@ -67,15 +67,15 @@
         nativeFinalize();
     }
 
-    static synchronized void setActiveWebView(WebView webview) {
+    static synchronized void setActiveWebView(WebViewClassic webview) {
         if (sCurrentMainWebView.get() != null) {
             // it is possible if there is a sub-WebView. Do nothing.
             return;
         }
-        sCurrentMainWebView = new WeakReference<WebView>(webview);
+        sCurrentMainWebView = new WeakReference<WebViewClassic>(webview);
     }
 
-    static synchronized void removeActiveWebView(WebView webview) {
+    static synchronized void removeActiveWebView(WebViewClassic webview) {
         if (sCurrentMainWebView.get() != webview) {
             // it is possible if there is a sub-WebView. Do nothing.
             return;
@@ -259,7 +259,7 @@
 
     synchronized private String getSignedPublicKey(int index, String challenge,
             String url) {
-        WebView current = sCurrentMainWebView.get();
+        WebViewClassic current = sCurrentMainWebView.get();
         if (current != null) {
             // generateKeyPair expects organizations which we don't have. Ignore
             // url.
diff --git a/core/java/android/webkit/OverScrollGlow.java b/core/java/android/webkit/OverScrollGlow.java
index e906f7f..d91f860 100644
--- a/core/java/android/webkit/OverScrollGlow.java
+++ b/core/java/android/webkit/OverScrollGlow.java
@@ -29,7 +29,7 @@
  * @hide
  */
 public class OverScrollGlow {
-    private WebView mHostView;
+    private WebViewClassic mHostView;
 
     private EdgeEffect mEdgeGlowTop;
     private EdgeEffect mEdgeGlowBottom;
@@ -39,7 +39,7 @@
     private int mOverScrollDeltaX;
     private int mOverScrollDeltaY;
 
-    public OverScrollGlow(WebView host) {
+    public OverScrollGlow(WebViewClassic host) {
         mHostView = host;
         Context context = host.getContext();
         mEdgeGlowTop = new EdgeEffect(context);
@@ -80,7 +80,7 @@
                 mOverScrollDeltaX = 0;
             }
 
-            if (maxY > 0 || mHostView.getOverScrollMode() == View.OVER_SCROLL_ALWAYS) {
+            if (maxY > 0 || mHostView.getWebView().getOverScrollMode() == View.OVER_SCROLL_ALWAYS) {
                 final int pulledToY = oldY + mOverScrollDeltaY;
                 if (pulledToY < 0) {
                     mEdgeGlowTop.onPull((float) mOverScrollDeltaY / mHostView.getHeight());
@@ -120,7 +120,7 @@
      * @param rangeY Maximum range for vertical scrolling
      */
     public void absorbGlow(int x, int y, int oldX, int oldY, int rangeX, int rangeY) {
-        if (rangeY > 0 || mHostView.getOverScrollMode() == View.OVER_SCROLL_ALWAYS) {
+        if (rangeY > 0 || mHostView.getWebView().getOverScrollMode() == View.OVER_SCROLL_ALWAYS) {
             if (y < 0 && oldY >= 0) {
                 mEdgeGlowTop.onAbsorb((int) mHostView.mScroller.getCurrVelocity());
                 if (!mEdgeGlowBottom.isFinished()) {
diff --git a/core/java/android/webkit/PluginFullScreenHolder.java b/core/java/android/webkit/PluginFullScreenHolder.java
index 42ba7c9..665cd9d 100644
--- a/core/java/android/webkit/PluginFullScreenHolder.java
+++ b/core/java/android/webkit/PluginFullScreenHolder.java
@@ -35,7 +35,7 @@
 
 class PluginFullScreenHolder {
 
-    private final WebView mWebView;
+    private final WebViewClassic mWebView;
     private final int mNpp;
     private final int mOrientation;
 
@@ -44,7 +44,7 @@
 
     private View mContentView;
 
-    PluginFullScreenHolder(WebView webView, int orientation, int npp) {
+    PluginFullScreenHolder(WebViewClassic webView, int orientation, int npp) {
         mWebView = webView;
         mNpp = npp;
         mOrientation = orientation;
@@ -134,7 +134,7 @@
         new WebChromeClient.CustomViewCallback() {
             public void onCustomViewHidden() {
 
-                mWebView.mPrivateHandler.obtainMessage(WebView.HIDE_FULLSCREEN)
+                mWebView.mPrivateHandler.obtainMessage(WebViewClassic.HIDE_FULLSCREEN)
                     .sendToTarget();
 
                 mWebView.getWebViewCore().sendMessage(
diff --git a/core/java/android/webkit/PluginManager.java b/core/java/android/webkit/PluginManager.java
index ab3b6d5..fe40156 100644
--- a/core/java/android/webkit/PluginManager.java
+++ b/core/java/android/webkit/PluginManager.java
@@ -34,7 +34,7 @@
 import android.util.Log;
 
 /**
- * Class for managing the relationship between the {@link WebView} and installed
+ * Class for managing the relationship between the {@link WebViewClassic} and installed
  * plugins in the system. You can find this class through
  * {@link PluginManager#getInstance}.
  * 
diff --git a/core/java/android/webkit/SelectActionModeCallback.java b/core/java/android/webkit/SelectActionModeCallback.java
index 2a770f5..57628d3 100644
--- a/core/java/android/webkit/SelectActionModeCallback.java
+++ b/core/java/android/webkit/SelectActionModeCallback.java
@@ -26,11 +26,11 @@
 import android.view.MenuItem;
 
 class SelectActionModeCallback implements ActionMode.Callback {
-    private WebView mWebView;
+    private WebViewClassic mWebView;
     private ActionMode mActionMode;
     private boolean mIsTextSelected = true;
 
-    void setWebView(WebView webView) {
+    void setWebView(WebViewClassic webView) {
         mWebView = webView;
     }
 
diff --git a/core/java/android/webkit/ViewManager.java b/core/java/android/webkit/ViewManager.java
index 153c1c2..34065a1 100644
--- a/core/java/android/webkit/ViewManager.java
+++ b/core/java/android/webkit/ViewManager.java
@@ -16,6 +16,7 @@
 
 package android.webkit;
 
+import android.util.DisplayMetrics;
 import android.view.SurfaceView;
 import android.view.View;
 import android.view.ViewGroup;
@@ -24,7 +25,7 @@
 import java.util.ArrayList;
 
 class ViewManager {
-    private final WebView mWebView;
+    private final WebViewClassic mWebView;
     private final ArrayList<ChildView> mChildren = new ArrayList<ChildView>();
     private boolean mHidden;
     private boolean mReadyToDraw;
@@ -74,7 +75,7 @@
         }
 
         private void attachViewOnUIThread() {
-            mWebView.addView(mView);
+            mWebView.getWebView().addView(mView);
             mChildren.add(this);
             if (!mReadyToDraw) {
                 mView.setVisibility(View.GONE);
@@ -93,16 +94,15 @@
         }
 
         private void removeViewOnUIThread() {
-            mWebView.removeView(mView);
+            mWebView.getWebView().removeView(mView);
             mChildren.remove(this);
         }
     }
 
-    ViewManager(WebView w) {
+    ViewManager(WebViewClassic w) {
         mWebView = w;
-
-        int pixelArea = w.getResources().getDisplayMetrics().widthPixels *
-                        w.getResources().getDisplayMetrics().heightPixels;
+        DisplayMetrics metrics = w.getWebView().getResources().getDisplayMetrics();
+        int pixelArea = metrics.widthPixels * metrics.heightPixels;
         /* set the threshold to be 275% larger than the screen size. The
            percentage is simply an estimation and is not based on anything but
            basic trial-and-error tests run on multiple devices.
diff --git a/core/java/android/webkit/ViewStateSerializer.java b/core/java/android/webkit/ViewStateSerializer.java
index 5f91ed3..a22fc26 100644
--- a/core/java/android/webkit/ViewStateSerializer.java
+++ b/core/java/android/webkit/ViewStateSerializer.java
@@ -34,7 +34,7 @@
 
     static final int VERSION = 1;
 
-    static boolean serializeViewState(OutputStream stream, WebView web)
+    static boolean serializeViewState(OutputStream stream, WebViewClassic web)
             throws IOException {
         int baseLayer = web.getBaseLayer();
         if (baseLayer == 0) {
@@ -48,7 +48,7 @@
                 new byte[WORKING_STREAM_STORAGE]);
     }
 
-    static DrawData deserializeViewState(InputStream stream, WebView web)
+    static DrawData deserializeViewState(InputStream stream, WebViewClassic web)
             throws IOException {
         DataInputStream dis = new DataInputStream(stream);
         int version = dis.readInt();
diff --git a/core/java/android/webkit/WebSettings.java b/core/java/android/webkit/WebSettings.java
index c463b40..cddd7ab 100644
--- a/core/java/android/webkit/WebSettings.java
+++ b/core/java/android/webkit/WebSettings.java
@@ -16,16 +16,7 @@
 
 package android.webkit;
 
-import android.content.Context;
-import android.content.SharedPreferences;
-import android.content.pm.PackageManager;
-import android.os.Build;
-import android.os.Handler;
 import android.os.Message;
-import android.util.DisplayMetrics;
-import android.util.EventLog;
-
-import java.util.Locale;
 
 /**
  * Manages settings state for a WebView. When a WebView is first created, it
@@ -35,7 +26,18 @@
  * been destroyed, any method call on WebSettings will throw an
  * IllegalStateException.
  */
+// This is (effectively) an abstract base class; concrete WebViewProviders must
+// create a class derived from this, and return an instance of it in the
+// WebViewProvider.getWebSettingsProvider() method implementation.
 public class WebSettings {
+    // TODO: Remove MustOverrideException and make all methods throwing it abstract instead;
+    // needs API file update.
+    private static class MustOverrideException extends RuntimeException {
+        MustOverrideException() {
+            super("abstract function called: must be overriden!");
+        }
+    }
+
     /**
      * Enum for controlling the layout of html.
      * NORMAL means no rendering changes.
@@ -141,379 +143,12 @@
         OFF
     }
 
-    // TODO: Keep this up to date
-    private static final String PREVIOUS_VERSION = "4.0.3";
-
-    // WebView associated with this WebSettings.
-    private WebView mWebView;
-    // BrowserFrame used to access the native frame pointer.
-    private BrowserFrame mBrowserFrame;
-    // Flag to prevent multiple SYNC messages at one time.
-    private boolean mSyncPending = false;
-    // Custom handler that queues messages until the WebCore thread is active.
-    private final EventHandler mEventHandler;
-
-    // Private settings so we don't have to go into native code to
-    // retrieve the values. After setXXX, postSync() needs to be called.
-    //
-    // The default values need to match those in WebSettings.cpp
-    // If the defaults change, please also update the JavaDocs so developers
-    // know what they are.
-    private LayoutAlgorithm mLayoutAlgorithm = LayoutAlgorithm.NARROW_COLUMNS;
-    private Context         mContext;
-    private int             mTextSize = 100;
-    private String          mStandardFontFamily = "sans-serif";
-    private String          mFixedFontFamily = "monospace";
-    private String          mSansSerifFontFamily = "sans-serif";
-    private String          mSerifFontFamily = "serif";
-    private String          mCursiveFontFamily = "cursive";
-    private String          mFantasyFontFamily = "fantasy";
-    private String          mDefaultTextEncoding;
-    private String          mUserAgent;
-    private boolean         mUseDefaultUserAgent;
-    private String          mAcceptLanguage;
-    private int             mMinimumFontSize = 8;
-    private int             mMinimumLogicalFontSize = 8;
-    private int             mDefaultFontSize = 16;
-    private int             mDefaultFixedFontSize = 13;
-    private int             mPageCacheCapacity = 0;
-    private boolean         mLoadsImagesAutomatically = true;
-    private boolean         mBlockNetworkImage = false;
-    private boolean         mBlockNetworkLoads;
-    private boolean         mJavaScriptEnabled = false;
-    private boolean         mHardwareAccelSkia = false;
-    private boolean         mShowVisualIndicator = false;
-    private PluginState     mPluginState = PluginState.OFF;
-    private boolean         mJavaScriptCanOpenWindowsAutomatically = false;
-    private boolean         mUseDoubleTree = false;
-    private boolean         mUseWideViewport = false;
-    private boolean         mSupportMultipleWindows = false;
-    private boolean         mShrinksStandaloneImagesToFit = false;
-    private long            mMaximumDecodedImageSize = 0; // 0 means default
-    private boolean         mPrivateBrowsingEnabled = false;
-    private boolean         mSyntheticLinksEnabled = true;
-    // HTML5 API flags
-    private boolean         mAppCacheEnabled = false;
-    private boolean         mDatabaseEnabled = false;
-    private boolean         mDomStorageEnabled = false;
-    private boolean         mWorkersEnabled = false;  // only affects V8.
-    private boolean         mGeolocationEnabled = true;
-    private boolean         mXSSAuditorEnabled = false;
-    // HTML5 configuration parameters
-    private long            mAppCacheMaxSize = Long.MAX_VALUE;
-    private String          mAppCachePath = null;
-    private String          mDatabasePath = "";
-    // The WebCore DatabaseTracker only allows the database path to be set
-    // once. Keep track of when the path has been set.
-    private boolean         mDatabasePathHasBeenSet = false;
-    private String          mGeolocationDatabasePath = "";
-    // Don't need to synchronize the get/set methods as they
-    // are basic types, also none of these values are used in
-    // native WebCore code.
-    private ZoomDensity     mDefaultZoom = ZoomDensity.MEDIUM;
-    private RenderPriority  mRenderPriority = RenderPriority.NORMAL;
-    private int             mOverrideCacheMode = LOAD_DEFAULT;
-    private int             mDoubleTapZoom = 100;
-    private boolean         mSaveFormData = true;
-    private boolean         mAutoFillEnabled = false;
-    private boolean         mSavePassword = true;
-    private boolean         mLightTouchEnabled = false;
-    private boolean         mNeedInitialFocus = true;
-    private boolean         mNavDump = false;
-    private boolean         mSupportZoom = true;
-    private boolean         mBuiltInZoomControls = false;
-    private boolean         mDisplayZoomControls = true;
-    private boolean         mAllowFileAccess = true;
-    private boolean         mAllowContentAccess = true;
-    private boolean         mLoadWithOverviewMode = false;
-    private boolean         mEnableSmoothTransition = false;
-    private boolean         mForceUserScalable = false;
-
-    // AutoFill Profile data
     /**
-     * @hide for now, pending API council approval.
+     * Hidden constructor to prevent clients from creating a new settings
+     * instance or deriving the class.
+     * @hide
      */
-    public static class AutoFillProfile {
-        private int mUniqueId;
-        private String mFullName;
-        private String mEmailAddress;
-        private String mCompanyName;
-        private String mAddressLine1;
-        private String mAddressLine2;
-        private String mCity;
-        private String mState;
-        private String mZipCode;
-        private String mCountry;
-        private String mPhoneNumber;
-
-        public AutoFillProfile(int uniqueId, String fullName, String email,
-                String companyName, String addressLine1, String addressLine2,
-                String city, String state, String zipCode, String country,
-                String phoneNumber) {
-            mUniqueId = uniqueId;
-            mFullName = fullName;
-            mEmailAddress = email;
-            mCompanyName = companyName;
-            mAddressLine1 = addressLine1;
-            mAddressLine2 = addressLine2;
-            mCity = city;
-            mState = state;
-            mZipCode = zipCode;
-            mCountry = country;
-            mPhoneNumber = phoneNumber;
-        }
-
-        public int getUniqueId() { return mUniqueId; }
-        public String getFullName() { return mFullName; }
-        public String getEmailAddress() { return mEmailAddress; }
-        public String getCompanyName() { return mCompanyName; }
-        public String getAddressLine1() { return mAddressLine1; }
-        public String getAddressLine2() { return mAddressLine2; }
-        public String getCity() { return mCity; }
-        public String getState() { return mState; }
-        public String getZipCode() { return mZipCode; }
-        public String getCountry() { return mCountry; }
-        public String getPhoneNumber() { return mPhoneNumber; }
-    }
-
-
-    private AutoFillProfile mAutoFillProfile;
-
-    private boolean         mUseWebViewBackgroundForOverscroll = true;
-
-    // private WebSettings, not accessible by the host activity
-    static private int      mDoubleTapToastCount = 3;
-
-    private static final String PREF_FILE = "WebViewSettings";
-    private static final String DOUBLE_TAP_TOAST_COUNT = "double_tap_toast_count";
-
-    // Class to handle messages before WebCore is ready.
-    private class EventHandler {
-        // Message id for syncing
-        static final int SYNC = 0;
-        // Message id for setting priority
-        static final int PRIORITY = 1;
-        // Message id for writing double-tap toast count
-        static final int SET_DOUBLE_TAP_TOAST_COUNT = 2;
-        // Actual WebCore thread handler
-        private Handler mHandler;
-
-        private synchronized void createHandler() {
-            // as mRenderPriority can be set before thread is running, sync up
-            setRenderPriority();
-
-            // create a new handler
-            mHandler = new Handler() {
-                @Override
-                public void handleMessage(Message msg) {
-                    switch (msg.what) {
-                        case SYNC:
-                            synchronized (WebSettings.this) {
-                                if (mBrowserFrame.mNativeFrame != 0) {
-                                    nativeSync(mBrowserFrame.mNativeFrame);
-                                }
-                                mSyncPending = false;
-                            }
-                            break;
-
-                        case PRIORITY: {
-                            setRenderPriority();
-                            break;
-                        }
-
-                        case SET_DOUBLE_TAP_TOAST_COUNT: {
-                            SharedPreferences.Editor editor = mContext
-                                    .getSharedPreferences(PREF_FILE,
-                                            Context.MODE_PRIVATE).edit();
-                            editor.putInt(DOUBLE_TAP_TOAST_COUNT,
-                                    mDoubleTapToastCount);
-                            editor.commit();
-                            break;
-                        }
-                    }
-                }
-            };
-        }
-
-        private void setRenderPriority() {
-            synchronized (WebSettings.this) {
-                if (mRenderPriority == RenderPriority.NORMAL) {
-                    android.os.Process.setThreadPriority(
-                            android.os.Process.THREAD_PRIORITY_DEFAULT);
-                } else if (mRenderPriority == RenderPriority.HIGH) {
-                    android.os.Process.setThreadPriority(
-                            android.os.Process.THREAD_PRIORITY_FOREGROUND +
-                            android.os.Process.THREAD_PRIORITY_LESS_FAVORABLE);
-                } else if (mRenderPriority == RenderPriority.LOW) {
-                    android.os.Process.setThreadPriority(
-                            android.os.Process.THREAD_PRIORITY_BACKGROUND);
-                }
-            }
-        }
-
-        /**
-         * Send a message to the private queue or handler.
-         */
-        private synchronized boolean sendMessage(Message msg) {
-            if (mHandler != null) {
-                mHandler.sendMessage(msg);
-                return true;
-            } else {
-                return false;
-            }
-        }
-    }
-
-    // User agent strings.
-    private static final String DESKTOP_USERAGENT = "Mozilla/5.0 (X11; " +
-        "Linux x86_64) AppleWebKit/534.24 (KHTML, like Gecko) " +
-        "Chrome/11.0.696.34 Safari/534.24";
-    private static final String IPHONE_USERAGENT =
-            "Mozilla/5.0 (iPhone; U; CPU iPhone OS 3_0 like Mac OS X; en-us)"
-            + " AppleWebKit/528.18 (KHTML, like Gecko) Version/4.0"
-            + " Mobile/7A341 Safari/528.16";
-    private static Locale sLocale;
-    private static Object sLockForLocaleSettings;
-
-    /**
-     * Package constructor to prevent clients from creating a new settings
-     * instance.
-     */
-    WebSettings(Context context, WebView webview) {
-        mEventHandler = new EventHandler();
-        mContext = context;
-        mWebView = webview;
-        mDefaultTextEncoding = context.getString(com.android.internal.
-                                                 R.string.default_text_encoding);
-
-        if (sLockForLocaleSettings == null) {
-            sLockForLocaleSettings = new Object();
-            sLocale = Locale.getDefault();
-        }
-        mAcceptLanguage = getCurrentAcceptLanguage();
-        mUserAgent = getCurrentUserAgent();
-        mUseDefaultUserAgent = true;
-
-        mBlockNetworkLoads = mContext.checkPermission(
-                "android.permission.INTERNET", android.os.Process.myPid(),
-                android.os.Process.myUid()) != PackageManager.PERMISSION_GRANTED;
-    }
-
-    private static final String ACCEPT_LANG_FOR_US_LOCALE = "en-US";
-
-    /**
-     * Looks at sLocale and returns current AcceptLanguage String.
-     * @return Current AcceptLanguage String.
-     */
-    private String getCurrentAcceptLanguage() {
-        Locale locale;
-        synchronized(sLockForLocaleSettings) {
-            locale = sLocale;
-        }
-        StringBuilder buffer = new StringBuilder();
-        addLocaleToHttpAcceptLanguage(buffer, locale);
-
-        if (!Locale.US.equals(locale)) {
-            if (buffer.length() > 0) {
-                buffer.append(", ");
-            }
-            buffer.append(ACCEPT_LANG_FOR_US_LOCALE);
-        }
-
-        return buffer.toString();
-    }
-
-    /**
-     * Convert obsolete language codes, including Hebrew/Indonesian/Yiddish,
-     * to new standard.
-     */
-    private static String convertObsoleteLanguageCodeToNew(String langCode) {
-        if (langCode == null) {
-            return null;
-        }
-        if ("iw".equals(langCode)) {
-            // Hebrew
-            return "he";
-        } else if ("in".equals(langCode)) {
-            // Indonesian
-            return "id";
-        } else if ("ji".equals(langCode)) {
-            // Yiddish
-            return "yi";
-        }
-        return langCode;
-    }
-
-    private static void addLocaleToHttpAcceptLanguage(StringBuilder builder,
-                                                      Locale locale) {
-        String language = convertObsoleteLanguageCodeToNew(locale.getLanguage());
-        if (language != null) {
-            builder.append(language);
-            String country = locale.getCountry();
-            if (country != null) {
-                builder.append("-");
-                builder.append(country);
-            }
-        }
-    }
-
-    /**
-     * Looks at sLocale and mContext and returns current UserAgent String.
-     * @return Current UserAgent String.
-     */
-    private synchronized String getCurrentUserAgent() {
-        Locale locale;
-        synchronized(sLockForLocaleSettings) {
-            locale = sLocale;
-        }
-        StringBuffer buffer = new StringBuffer();
-        // Add version
-        final String version = Build.VERSION.RELEASE;
-        if (version.length() > 0) {
-            if (Character.isDigit(version.charAt(0))) {
-                // Release is a version, eg "3.1"
-                buffer.append(version);
-            } else {
-                // Release is a codename, eg "Honeycomb"
-                // In this case, use the previous release's version
-                buffer.append(PREVIOUS_VERSION);
-            }
-        } else {
-            // default to "1.0"
-            buffer.append("1.0");
-        }
-        buffer.append("; ");
-        final String language = locale.getLanguage();
-        if (language != null) {
-            buffer.append(convertObsoleteLanguageCodeToNew(language));
-            final String country = locale.getCountry();
-            if (country != null) {
-                buffer.append("-");
-                buffer.append(country.toLowerCase());
-            }
-        } else {
-            // default to "en"
-            buffer.append("en");
-        }
-        buffer.append(";");
-        // add the model for the release build
-        if ("REL".equals(Build.VERSION.CODENAME)) {
-            final String model = Build.MODEL;
-            if (model.length() > 0) {
-                buffer.append(" ");
-                buffer.append(model);
-            }
-        }
-        final String id = Build.ID;
-        if (id.length() > 0) {
-            buffer.append(" Build/");
-            buffer.append(id);
-        }
-        String mobile = mContext.getResources().getText(
-            com.android.internal.R.string.web_user_agent_target_content).toString();
-        final String base = mContext.getResources().getText(
-                com.android.internal.R.string.web_user_agent).toString();
-        return String.format(base, buffer, mobile);
+    protected WebSettings() {
     }
 
     /**
@@ -522,7 +157,7 @@
      */
     @Deprecated
     public void setNavDump(boolean enabled) {
-        mNavDump = enabled;
+        throw new MustOverrideException();
     }
 
     /**
@@ -531,37 +166,35 @@
      */
     @Deprecated
     public boolean getNavDump() {
-        return mNavDump;
+        throw new MustOverrideException();
     }
 
     /**
      * Set whether the WebView supports zoom
      */
     public void setSupportZoom(boolean support) {
-        mSupportZoom = support;
-        mWebView.updateMultiTouchSupport(mContext);
+        throw new MustOverrideException();
     }
 
     /**
      * Returns whether the WebView supports zoom
      */
     public boolean supportZoom() {
-        return mSupportZoom;
+        throw new MustOverrideException();
     }
 
     /**
      * Sets whether the zoom mechanism built into WebView is used.
      */
     public void setBuiltInZoomControls(boolean enabled) {
-        mBuiltInZoomControls = enabled;
-        mWebView.updateMultiTouchSupport(mContext);
+        throw new MustOverrideException();
     }
 
     /**
      * Returns true if the zoom mechanism built into WebView is being used.
      */
     public boolean getBuiltInZoomControls() {
-        return mBuiltInZoomControls;
+        throw new MustOverrideException();
     }
 
     /**
@@ -571,15 +204,14 @@
      * to work without the on screen controls
      */
     public void setDisplayZoomControls(boolean enabled) {
-        mDisplayZoomControls = enabled;
-        mWebView.updateMultiTouchSupport(mContext);
+        throw new MustOverrideException();
     }
 
     /**
      * Returns true if the on screen zoom buttons are being used.
      */
     public boolean getDisplayZoomControls() {
-        return mDisplayZoomControls;
+        throw new MustOverrideException();
     }
 
     /**
@@ -589,14 +221,14 @@
      * file:///android_res.
      */
     public void setAllowFileAccess(boolean allow) {
-        mAllowFileAccess = allow;
+        throw new MustOverrideException();
     }
 
     /**
      * Returns true if this WebView supports file access.
      */
     public boolean getAllowFileAccess() {
-        return mAllowFileAccess;
+        throw new MustOverrideException();
     }
 
     /**
@@ -605,28 +237,28 @@
      * system.  The default is enabled.
      */
     public void setAllowContentAccess(boolean allow) {
-        mAllowContentAccess = allow;
+        throw new MustOverrideException();
     }
 
     /**
      * Returns true if this WebView supports content url access.
      */
     public boolean getAllowContentAccess() {
-        return mAllowContentAccess;
+        throw new MustOverrideException();
     }
 
     /**
      * Set whether the WebView loads a page with overview mode.
      */
     public void setLoadWithOverviewMode(boolean overview) {
-        mLoadWithOverviewMode = overview;
+        throw new MustOverrideException();
     }
 
     /**
      * Returns true if this WebView loads page with overview mode
      */
     public boolean getLoadWithOverviewMode() {
-        return mLoadWithOverviewMode;
+        throw new MustOverrideException();
     }
 
     /**
@@ -637,15 +269,14 @@
      * If it is false, WebView will keep its fidelity. The default value is false.
      */
     public void setEnableSmoothTransition(boolean enable) {
-        mEnableSmoothTransition = enable;
+        throw new MustOverrideException();
     }
-
     /**
      * Returns true if the WebView enables smooth transition while panning or
      * zooming.
      */
     public boolean enableSmoothTransition() {
-        return mEnableSmoothTransition;
+        throw new MustOverrideException();
     }
 
     /**
@@ -656,7 +287,7 @@
      */
     @Deprecated
     public void setUseWebViewBackgroundForOverscrollBackground(boolean view) {
-        mUseWebViewBackgroundForOverscroll = view;
+        throw new MustOverrideException();
     }
 
     /**
@@ -666,14 +297,14 @@
      */
     @Deprecated
     public boolean getUseWebViewBackgroundForOverscrollBackground() {
-        return mUseWebViewBackgroundForOverscroll;
+        throw new MustOverrideException();
     }
 
     /**
      * Store whether the WebView is saving form data.
      */
     public void setSaveFormData(boolean save) {
-        mSaveFormData = save;
+        throw new MustOverrideException();
     }
 
     /**
@@ -681,21 +312,21 @@
      *  entries/autofill++.  Always false in private browsing mode.
      */
     public boolean getSaveFormData() {
-        return mSaveFormData && !mPrivateBrowsingEnabled;
+        throw new MustOverrideException();
     }
 
     /**
      *  Store whether the WebView is saving password.
      */
     public void setSavePassword(boolean save) {
-        mSavePassword = save;
+        throw new MustOverrideException();
     }
 
     /**
      *  Return whether the WebView is saving password.
      */
     public boolean getSavePassword() {
-        return mSavePassword;
+        throw new MustOverrideException();
     }
 
     /**
@@ -703,14 +334,7 @@
      * @param textZoom A percent value for increasing or decreasing the text.
      */
     public synchronized void setTextZoom(int textZoom) {
-        if (mTextSize != textZoom) {
-            if (WebView.mLogEvent) {
-                EventLog.writeEvent(EventLogTags.BROWSER_TEXT_SIZE_CHANGE,
-                        mTextSize, textZoom);
-            }
-            mTextSize = textZoom;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -719,7 +343,7 @@
      * @see setTextSizeZoom
      */
     public synchronized int getTextZoom() {
-        return mTextSize;
+        throw new MustOverrideException();
     }
 
     /**
@@ -729,7 +353,7 @@
      * @deprecated Use {@link #setTextZoom(int)} instead
      */
     public synchronized void setTextSize(TextSize t) {
-        setTextZoom(t.value);
+        throw new MustOverrideException();
     }
 
     /**
@@ -741,40 +365,7 @@
      * @deprecated Use {@link #getTextZoom()} instead
      */
     public synchronized TextSize getTextSize() {
-        TextSize closestSize = null;
-        int smallestDelta = Integer.MAX_VALUE;
-        for (TextSize size : TextSize.values()) {
-            int delta = Math.abs(mTextSize - size.value);
-            if (delta == 0) {
-                return size;
-            }
-            if (delta < smallestDelta) {
-                smallestDelta = delta;
-                closestSize = size;
-            }
-        }
-        return closestSize != null ? closestSize : TextSize.NORMAL;
-    }
-
-    /**
-     * Set the double-tap zoom of the page in percent. Default is 100.
-     * @param doubleTapZoom A percent value for increasing or decreasing the double-tap zoom.
-     * @hide
-     */
-    public void setDoubleTapZoom(int doubleTapZoom) {
-        if (mDoubleTapZoom != doubleTapZoom) {
-            mDoubleTapZoom = doubleTapZoom;
-            mWebView.updateDoubleTapZoom(doubleTapZoom);
-        }
-    }
-
-    /**
-     * Get the double-tap zoom of the page in percent.
-     * @return A percent value describing the double-tap zoom.
-     * @hide
-     */
-    public int getDoubleTapZoom() {
-        return mDoubleTapZoom;
+        throw new MustOverrideException();
     }
 
     /**
@@ -784,10 +375,7 @@
      * @see WebSettings.ZoomDensity
      */
     public void setDefaultZoom(ZoomDensity zoom) {
-        if (mDefaultZoom != zoom) {
-            mDefaultZoom = zoom;
-            mWebView.adjustDefaultZoomDensity(zoom.value);
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -797,21 +385,21 @@
      * @see WebSettings.ZoomDensity
      */
     public ZoomDensity getDefaultZoom() {
-        return mDefaultZoom;
+        throw new MustOverrideException();
     }
 
     /**
      * Enables using light touches to make a selection and activate mouseovers.
      */
     public void setLightTouchEnabled(boolean enabled) {
-        mLightTouchEnabled = enabled;
+        throw new MustOverrideException();
     }
 
     /**
      * Returns true if light touches are enabled.
      */
     public boolean getLightTouchEnabled() {
-        return mLightTouchEnabled;
+        throw new MustOverrideException();
     }
 
     /**
@@ -820,7 +408,7 @@
      */
     @Deprecated
     public synchronized void setUseDoubleTree(boolean use) {
-        return;
+        // Specified to do nothing, so no need for derived classes to override.
     }
 
     /**
@@ -829,6 +417,7 @@
      */
     @Deprecated
     public synchronized boolean getUseDoubleTree() {
+        // Returns false unconditionally, so no need for derived classes to override.
         return false;
     }
 
@@ -841,23 +430,7 @@
      */
     @Deprecated
     public synchronized void setUserAgent(int ua) {
-        String uaString = null;
-        if (ua == 1) {
-            if (DESKTOP_USERAGENT.equals(mUserAgent)) {
-                return; // do nothing
-            } else {
-                uaString = DESKTOP_USERAGENT;
-            }
-        } else if (ua == 2) {
-            if (IPHONE_USERAGENT.equals(mUserAgent)) {
-                return; // do nothing
-            } else {
-                uaString = IPHONE_USERAGENT;
-            }
-        } else if (ua != 0) {
-            return; // do nothing
-        }
-        setUserAgentString(uaString);
+        throw new MustOverrideException();
     }
 
     /**
@@ -870,31 +443,21 @@
      */
     @Deprecated
     public synchronized int getUserAgent() {
-        if (DESKTOP_USERAGENT.equals(mUserAgent)) {
-            return 1;
-        } else if (IPHONE_USERAGENT.equals(mUserAgent)) {
-            return 2;
-        } else if (mUseDefaultUserAgent) {
-            return 0;
-        }
-        return -1;
+        throw new MustOverrideException();
     }
 
     /**
      * Tell the WebView to use the wide viewport
      */
     public synchronized void setUseWideViewPort(boolean use) {
-        if (mUseWideViewport != use) {
-            mUseWideViewport = use;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
      * @return True if the WebView is using a wide viewport
      */
     public synchronized boolean getUseWideViewPort() {
-        return mUseWideViewport;
+        throw new MustOverrideException();
     }
 
     /**
@@ -903,10 +466,7 @@
      *         boolean, Message)} is implemented by the host application.
      */
     public synchronized void setSupportMultipleWindows(boolean support) {
-        if (mSupportMultipleWindows != support) {
-            mSupportMultipleWindows = support;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -915,7 +475,7 @@
      *         boolean, Message)} is implemented by the host application.
      */
     public synchronized boolean supportMultipleWindows() {
-        return mSupportMultipleWindows;
+        throw new MustOverrideException();
     }
 
     /**
@@ -925,12 +485,7 @@
      * @see WebSettings.LayoutAlgorithm
      */
     public synchronized void setLayoutAlgorithm(LayoutAlgorithm l) {
-        // XXX: This will only be affective if libwebcore was built with
-        // ANDROID_LAYOUT defined.
-        if (mLayoutAlgorithm != l) {
-            mLayoutAlgorithm = l;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -940,7 +495,7 @@
      * @see WebSettings.LayoutAlgorithm
      */
     public synchronized LayoutAlgorithm getLayoutAlgorithm() {
-        return mLayoutAlgorithm;
+        throw new MustOverrideException();
     }
 
     /**
@@ -948,10 +503,7 @@
      * @param font A font family name.
      */
     public synchronized void setStandardFontFamily(String font) {
-        if (font != null && !font.equals(mStandardFontFamily)) {
-            mStandardFontFamily = font;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -959,7 +511,7 @@
      * @return The standard font family name as a string.
      */
     public synchronized String getStandardFontFamily() {
-        return mStandardFontFamily;
+        throw new MustOverrideException();
     }
 
     /**
@@ -967,10 +519,7 @@
      * @param font A font family name.
      */
     public synchronized void setFixedFontFamily(String font) {
-        if (font != null && !font.equals(mFixedFontFamily)) {
-            mFixedFontFamily = font;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -978,7 +527,7 @@
      * @return The fixed font family name as a string.
      */
     public synchronized String getFixedFontFamily() {
-        return mFixedFontFamily;
+        throw new MustOverrideException();
     }
 
     /**
@@ -986,10 +535,7 @@
      * @param font A font family name.
      */
     public synchronized void setSansSerifFontFamily(String font) {
-        if (font != null && !font.equals(mSansSerifFontFamily)) {
-            mSansSerifFontFamily = font;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -997,7 +543,7 @@
      * @return The sans-serif font family name as a string.
      */
     public synchronized String getSansSerifFontFamily() {
-        return mSansSerifFontFamily;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1005,10 +551,7 @@
      * @param font A font family name.
      */
     public synchronized void setSerifFontFamily(String font) {
-        if (font != null && !font.equals(mSerifFontFamily)) {
-            mSerifFontFamily = font;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1016,7 +559,7 @@
      * @return The serif font family name as a string.
      */
     public synchronized String getSerifFontFamily() {
-        return mSerifFontFamily;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1024,10 +567,7 @@
      * @param font A font family name.
      */
     public synchronized void setCursiveFontFamily(String font) {
-        if (font != null && !font.equals(mCursiveFontFamily)) {
-            mCursiveFontFamily = font;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1035,7 +575,7 @@
      * @return The cursive font family name as a string.
      */
     public synchronized String getCursiveFontFamily() {
-        return mCursiveFontFamily;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1043,10 +583,7 @@
      * @param font A font family name.
      */
     public synchronized void setFantasyFontFamily(String font) {
-        if (font != null && !font.equals(mFantasyFontFamily)) {
-            mFantasyFontFamily = font;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1054,7 +591,7 @@
      * @return The fantasy font family name as a string.
      */
     public synchronized String getFantasyFontFamily() {
-        return mFantasyFontFamily;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1063,11 +600,7 @@
      * Any number outside the specified range will be pinned.
      */
     public synchronized void setMinimumFontSize(int size) {
-        size = pin(size);
-        if (mMinimumFontSize != size) {
-            mMinimumFontSize = size;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1075,7 +608,7 @@
      * @return A non-negative integer between 1 and 72.
      */
     public synchronized int getMinimumFontSize() {
-        return mMinimumFontSize;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1084,11 +617,7 @@
      * Any number outside the specified range will be pinned.
      */
     public synchronized void setMinimumLogicalFontSize(int size) {
-        size = pin(size);
-        if (mMinimumLogicalFontSize != size) {
-            mMinimumLogicalFontSize = size;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1096,7 +625,7 @@
      * @return A non-negative integer between 1 and 72.
      */
     public synchronized int getMinimumLogicalFontSize() {
-        return mMinimumLogicalFontSize;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1105,11 +634,7 @@
      * Any number outside the specified range will be pinned.
      */
     public synchronized void setDefaultFontSize(int size) {
-        size = pin(size);
-        if (mDefaultFontSize != size) {
-            mDefaultFontSize = size;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1117,7 +642,7 @@
      * @return A non-negative integer between 1 and 72.
      */
     public synchronized int getDefaultFontSize() {
-        return mDefaultFontSize;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1126,11 +651,7 @@
      * Any number outside the specified range will be pinned.
      */
     public synchronized void setDefaultFixedFontSize(int size) {
-        size = pin(size);
-        if (mDefaultFixedFontSize != size) {
-            mDefaultFixedFontSize = size;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1138,21 +659,7 @@
      * @return A non-negative integer between 1 and 72.
      */
     public synchronized int getDefaultFixedFontSize() {
-        return mDefaultFixedFontSize;
-    }
-
-    /**
-     * Set the number of pages cached by the WebKit for the history navigation.
-     * @param size A non-negative integer between 0 (no cache) and 20 (max).
-     * @hide
-     */
-    public synchronized void setPageCacheCapacity(int size) {
-        if (size < 0) size = 0;
-        if (size > 20) size = 20;
-        if (mPageCacheCapacity != size) {
-            mPageCacheCapacity = size;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1165,10 +672,7 @@
      * @param flag Whether the WebView should load image resources.
      */
     public synchronized void setLoadsImagesAutomatically(boolean flag) {
-        if (mLoadsImagesAutomatically != flag) {
-            mLoadsImagesAutomatically = flag;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1177,7 +681,7 @@
      * @return True if the WebView loads image resources.
      */
     public synchronized boolean getLoadsImagesAutomatically() {
-        return mLoadsImagesAutomatically;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1195,10 +699,7 @@
      * @see #setBlockNetworkLoads
      */
     public synchronized void setBlockNetworkImage(boolean flag) {
-        if (mBlockNetworkImage != flag) {
-            mBlockNetworkImage = flag;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1207,7 +708,7 @@
      * @return True if the WebView does not load image resources from the network.
      */
     public synchronized boolean getBlockNetworkImage() {
-        return mBlockNetworkImage;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1226,11 +727,7 @@
      * @see android.webkit.WebView#reload
      */
     public synchronized void setBlockNetworkLoads(boolean flag) {
-        if (mBlockNetworkLoads != flag) {
-            mBlockNetworkLoads = flag;
-            verifyNetworkAccess();
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1241,20 +738,7 @@
      * @return True if the WebView does not load any resources from the network.
      */
     public synchronized boolean getBlockNetworkLoads() {
-        return mBlockNetworkLoads;
-    }
-
-
-    private void verifyNetworkAccess() {
-        if (!mBlockNetworkLoads) {
-            if (mContext.checkPermission("android.permission.INTERNET",
-                    android.os.Process.myPid(), android.os.Process.myUid()) !=
-                        PackageManager.PERMISSION_GRANTED) {
-                throw new SecurityException
-                        ("Permission denied - " +
-                                "application missing INTERNET permission");
-            }
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1262,50 +746,7 @@
      * @param flag True if the WebView should execute javascript.
      */
     public synchronized void setJavaScriptEnabled(boolean flag) {
-        if (mJavaScriptEnabled != flag) {
-            mJavaScriptEnabled = flag;
-            postSync();
-        }
-    }
-
-    /**
-     * Tell the WebView to use Skia's hardware accelerated rendering path
-     * @param flag True if the WebView should use Skia's hw-accel path
-     * @hide
-     */
-    public synchronized void setHardwareAccelSkiaEnabled(boolean flag) {
-        if (mHardwareAccelSkia != flag) {
-            mHardwareAccelSkia = flag;
-            postSync();
-        }
-    }
-
-    /**
-     * @return True if the WebView is using hardware accelerated skia
-     * @hide
-     */
-    public synchronized boolean getHardwareAccelSkiaEnabled() {
-        return mHardwareAccelSkia;
-    }
-
-    /**
-     * Tell the WebView to show the visual indicator
-     * @param flag True if the WebView should show the visual indicator
-     * @hide
-     */
-    public synchronized void setShowVisualIndicator(boolean flag) {
-        if (mShowVisualIndicator != flag) {
-            mShowVisualIndicator = flag;
-            postSync();
-        }
-    }
-
-    /**
-     * @return True if the WebView is showing the visual indicator
-     * @hide
-     */
-    public synchronized boolean getShowVisualIndicator() {
-        return mShowVisualIndicator;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1316,7 +757,7 @@
      */
     @Deprecated
     public synchronized void setPluginsEnabled(boolean flag) {
-        setPluginState(flag ? PluginState.ON : PluginState.OFF);
+        throw new MustOverrideException();
     }
 
     /**
@@ -1327,10 +768,7 @@
      * @param state One of the PluginState values.
      */
     public synchronized void setPluginState(PluginState state) {
-        if (mPluginState != state) {
-            mPluginState = state;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1342,6 +780,7 @@
      */
     @Deprecated
     public synchronized void setPluginsPath(String pluginsPath) {
+        // Specified to do nothing, so no need for derived classes to override.
     }
 
     /**
@@ -1352,11 +791,7 @@
      *     be saved. May be the empty string but should never be null.
      */
     public synchronized void setDatabasePath(String databasePath) {
-        if (databasePath != null && !mDatabasePathHasBeenSet) {
-            mDatabasePath = databasePath;
-            mDatabasePathHasBeenSet = true;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1367,40 +802,26 @@
      *     should never be null.
      */
     public synchronized void setGeolocationDatabasePath(String databasePath) {
-        if (databasePath != null
-                && !databasePath.equals(mGeolocationDatabasePath)) {
-            mGeolocationDatabasePath = databasePath;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
-     * Enable or disable the Application Cache API.
-     * @param flag Whether to enable the Application Cache API.
+     * Tell the WebView to enable Application Caches API.
+     * @param flag True if the WebView should enable Application Caches.
      */
     public synchronized void setAppCacheEnabled(boolean flag) {
-        if (mAppCacheEnabled != flag) {
-            mAppCacheEnabled = flag;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
-     * Set the path used by the Application Cache API to store files. This
-     * setting is applied to all WebViews in the application. In order for the
-     * Application Cache API to function, this method must be called with a
-     * path which exists and is writable by the application. This method may
-     * only be called once: repeated calls are ignored.
-     * @param path Path to the directory that should be used to store Application
-     * Cache files.
+     * Set a custom path to the Application Caches files. The client
+     * must ensure it exists before this call.
+     * @param appCachePath String path to the directory containing Application
+     * Caches files. The appCache path can be the empty string but should not
+     * be null. Passing null for this parameter will result in a no-op.
      */
-    public synchronized void setAppCachePath(String path) {
-        // We test for a valid path and for repeated setting on the native
-        // side, but we can avoid syncing in some simple cases. 
-        if (mAppCachePath == null && path != null && !path.isEmpty()) {
-            mAppCachePath = path;
-            postSync();
-        }
+    public synchronized void setAppCachePath(String appCachePath) {
+        throw new MustOverrideException();
     }
 
     /**
@@ -1408,10 +829,7 @@
      * @param appCacheMaxSize the maximum size in bytes.
      */
     public synchronized void setAppCacheMaxSize(long appCacheMaxSize) {
-        if (appCacheMaxSize != mAppCacheMaxSize) {
-            mAppCacheMaxSize = appCacheMaxSize;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1420,10 +838,7 @@
      *     API.
      */
     public synchronized void setDatabaseEnabled(boolean flag) {
-       if (mDatabaseEnabled != flag) {
-           mDatabaseEnabled = flag;
-           postSync();
-       }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1432,10 +847,7 @@
      *     API.
      */
     public synchronized void setDomStorageEnabled(boolean flag) {
-       if (mDomStorageEnabled != flag) {
-           mDomStorageEnabled = flag;
-           postSync();
-       }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1443,16 +855,15 @@
      * @return True if the DOM Storage API's are enabled.
      */
     public synchronized boolean getDomStorageEnabled() {
-       return mDomStorageEnabled;
+        throw new MustOverrideException();
     }
-
     /**
      * Return the path to where database storage API databases are saved for
      * the current WebView.
      * @return the String path to the database storage API databases.
      */
     public synchronized String getDatabasePath() {
-        return mDatabasePath;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1460,21 +871,7 @@
      * @return True if the database storage API is enabled.
      */
     public synchronized boolean getDatabaseEnabled() {
-        return mDatabaseEnabled;
-    }
-
-    /**
-     * Tell the WebView to enable WebWorkers API.
-     * @param flag True if the WebView should enable WebWorkers.
-     * Note that this flag only affects V8. JSC does not have
-     * an equivalent setting.
-     * @hide
-     */
-    public synchronized void setWorkersEnabled(boolean flag) {
-        if (mWorkersEnabled != flag) {
-            mWorkersEnabled = flag;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1482,22 +879,7 @@
      * @param flag Whether Geolocation should be enabled.
      */
     public synchronized void setGeolocationEnabled(boolean flag) {
-        if (mGeolocationEnabled != flag) {
-            mGeolocationEnabled = flag;
-            postSync();
-        }
-    }
-
-    /**
-     * Sets whether XSS Auditor is enabled.
-     * @param flag Whether XSS Auditor should be enabled.
-     * @hide Only used by LayoutTestController.
-     */
-    public synchronized void setXSSAuditorEnabled(boolean flag) {
-        if (mXSSAuditorEnabled != flag) {
-            mXSSAuditorEnabled = flag;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1505,7 +887,7 @@
      * @return True if javascript is enabled.
      */
     public synchronized boolean getJavaScriptEnabled() {
-        return mJavaScriptEnabled;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1515,7 +897,7 @@
      */
     @Deprecated
     public synchronized boolean getPluginsEnabled() {
-        return mPluginState == PluginState.ON;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1523,7 +905,7 @@
      * @return A value corresponding to the enum PluginState.
      */
     public synchronized PluginState getPluginState() {
-        return mPluginState;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1535,6 +917,7 @@
      */
     @Deprecated
     public synchronized String getPluginsPath() {
+        // Unconditionally returns empty string, so no need for derived classes to override.
         return "";
     }
 
@@ -1543,12 +926,8 @@
      * javascript function window.open().
      * @param flag True if javascript can open windows automatically.
      */
-    public synchronized void setJavaScriptCanOpenWindowsAutomatically(
-            boolean flag) {
-        if (mJavaScriptCanOpenWindowsAutomatically != flag) {
-            mJavaScriptCanOpenWindowsAutomatically = flag;
-            postSync();
-        }
+    public synchronized void setJavaScriptCanOpenWindowsAutomatically(boolean flag) {
+        throw new MustOverrideException();
     }
 
     /**
@@ -1558,18 +937,14 @@
      *         window.open().
      */
     public synchronized boolean getJavaScriptCanOpenWindowsAutomatically() {
-        return mJavaScriptCanOpenWindowsAutomatically;
+        throw new MustOverrideException();
     }
-
     /**
      * Set the default text encoding name to use when decoding html pages.
      * @param encoding The text encoding name.
      */
     public synchronized void setDefaultTextEncodingName(String encoding) {
-        if (encoding != null && !encoding.equals(mDefaultTextEncoding)) {
-            mDefaultTextEncoding = encoding;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1577,7 +952,7 @@
      * @return The default text encoding name as a string.
      */
     public synchronized String getDefaultTextEncodingName() {
-        return mDefaultTextEncoding;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1585,66 +960,14 @@
      * it will use the system default user-agent string.
      */
     public synchronized void setUserAgentString(String ua) {
-        if (ua == null || ua.length() == 0) {
-            synchronized(sLockForLocaleSettings) {
-                Locale currentLocale = Locale.getDefault();
-                if (!sLocale.equals(currentLocale)) {
-                    sLocale = currentLocale;
-                    mAcceptLanguage = getCurrentAcceptLanguage();
-                }
-            }
-            ua = getCurrentUserAgent();
-            mUseDefaultUserAgent = true;
-        } else  {
-            mUseDefaultUserAgent = false;
-        }
-
-        if (!ua.equals(mUserAgent)) {
-            mUserAgent = ua;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
      * Return the WebView's user-agent string.
      */
     public synchronized String getUserAgentString() {
-        if (DESKTOP_USERAGENT.equals(mUserAgent) ||
-                IPHONE_USERAGENT.equals(mUserAgent) ||
-                !mUseDefaultUserAgent) {
-            return mUserAgent;
-        }
-
-        boolean doPostSync = false;
-        synchronized(sLockForLocaleSettings) {
-            Locale currentLocale = Locale.getDefault();
-            if (!sLocale.equals(currentLocale)) {
-                sLocale = currentLocale;
-                mUserAgent = getCurrentUserAgent();
-                mAcceptLanguage = getCurrentAcceptLanguage();
-                doPostSync = true;
-            }
-        }
-        if (doPostSync) {
-            postSync();
-        }
-        return mUserAgent;
-    }
-
-    /* package api to grab the Accept Language string. */
-    /*package*/ synchronized String getAcceptLanguage() {
-        synchronized(sLockForLocaleSettings) {
-            Locale currentLocale = Locale.getDefault();
-            if (!sLocale.equals(currentLocale)) {
-                sLocale = currentLocale;
-                mAcceptLanguage = getCurrentAcceptLanguage();
-            }
-        }
-        return mAcceptLanguage;
-    }
-
-    /* package */ boolean isNarrowColumnLayout() {
-        return getLayoutAlgorithm() == LayoutAlgorithm.NARROW_COLUMNS;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1654,14 +977,7 @@
      * @param flag
      */
     public void setNeedInitialFocus(boolean flag) {
-        if (mNeedInitialFocus != flag) {
-            mNeedInitialFocus = flag;
-        }
-    }
-
-    /* Package api to get the choice whether it needs to set initial focus. */
-    /* package */ boolean getNeedInitialFocus() {
-        return mNeedInitialFocus;
+        throw new MustOverrideException();
     }
 
     /**
@@ -1671,11 +987,7 @@
      * @param priority RenderPriority, can be normal, high or low.
      */
     public synchronized void setRenderPriority(RenderPriority priority) {
-        if (mRenderPriority != priority) {
-            mRenderPriority = priority;
-            mEventHandler.sendMessage(Message.obtain(null,
-                    EventHandler.PRIORITY));
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1687,10 +999,7 @@
      * @param mode One of the LOAD_ values.
      */
     public void setCacheMode(int mode) {
-        if (mode != mOverrideCacheMode) {
-            mOverrideCacheMode = mode;
-            postSync();
-        }
+        throw new MustOverrideException();
     }
 
     /**
@@ -1698,204 +1007,6 @@
      * description, see the {@link #setCacheMode(int)} function.
      */
     public int getCacheMode() {
-        return mOverrideCacheMode;
+        throw new MustOverrideException();
     }
-
-    /**
-     * If set, webkit alternately shrinks and expands images viewed outside
-     * of an HTML page to fit the screen. This conflicts with attempts by
-     * the UI to zoom in and out of an image, so it is set false by default.
-     * @param shrink Set true to let webkit shrink the standalone image to fit.
-     * {@hide}
-     */
-    public void setShrinksStandaloneImagesToFit(boolean shrink) {
-        if (mShrinksStandaloneImagesToFit != shrink) {
-            mShrinksStandaloneImagesToFit = shrink;
-            postSync();
-        }
-     }
-
-    /**
-     * Specify the maximum decoded image size. The default is
-     * 2 megs for small memory devices and 8 megs for large memory devices.
-     * @param size The maximum decoded size, or zero to set to the default.
-     * @hide
-     */
-    public void setMaximumDecodedImageSize(long size) {
-        if (mMaximumDecodedImageSize != size) {
-            mMaximumDecodedImageSize = size;
-            postSync();
-        }
-    }
-
-    /**
-     * Returns whether to use fixed viewport.  Use fixed viewport
-     * whenever wide viewport is on.
-     */
-    /* package */ boolean getUseFixedViewport() {
-        return getUseWideViewPort();
-    }
-
-    /**
-     * Returns whether private browsing is enabled.
-     */
-    /* package */ boolean isPrivateBrowsingEnabled() {
-        return mPrivateBrowsingEnabled;
-    }
-
-    /**
-     * Sets whether private browsing is enabled.
-     * @param flag Whether private browsing should be enabled.
-     */
-    /* package */ synchronized void setPrivateBrowsingEnabled(boolean flag) {
-        if (mPrivateBrowsingEnabled != flag) {
-            mPrivateBrowsingEnabled = flag;
-
-            // AutoFill is dependant on private browsing being enabled so
-            // reset it to take account of the new value of mPrivateBrowsingEnabled.
-            setAutoFillEnabled(mAutoFillEnabled);
-
-            postSync();
-        }
-    }
-
-    /**
-     * Returns whether the viewport metatag can disable zooming
-     * @hide
-     */
-    public boolean forceUserScalable() {
-        return mForceUserScalable;
-    }
-
-    /**
-     * Sets whether viewport metatag can disable zooming.
-     * @param flag Whether or not to forceably enable user scalable.
-     * @hide
-     */
-    public synchronized void setForceUserScalable(boolean flag) {
-        mForceUserScalable = flag;
-    }
-
-    synchronized void setSyntheticLinksEnabled(boolean flag) {
-        if (mSyntheticLinksEnabled != flag) {
-            mSyntheticLinksEnabled = flag;
-            postSync();
-        }
-    }
-
-    /**
-     * @hide
-     */
-    public synchronized void setAutoFillEnabled(boolean enabled) {
-        // AutoFill is always disabled in private browsing mode.
-        boolean autoFillEnabled = enabled && !mPrivateBrowsingEnabled;
-        if (mAutoFillEnabled != autoFillEnabled) {
-            mAutoFillEnabled = autoFillEnabled;
-            postSync();
-        }
-    }
-
-    /**
-     * @hide
-     */
-    public synchronized boolean getAutoFillEnabled() {
-        return mAutoFillEnabled;
-    }
-
-    /**
-     * @hide
-     */
-    public synchronized void setAutoFillProfile(AutoFillProfile profile) {
-        if (mAutoFillProfile != profile) {
-            mAutoFillProfile = profile;
-            postSync();
-        }
-    }
-
-    /**
-     * @hide
-     */
-    public synchronized AutoFillProfile getAutoFillProfile() {
-        return mAutoFillProfile;
-    }
-
-    int getDoubleTapToastCount() {
-        return mDoubleTapToastCount;
-    }
-
-    void setDoubleTapToastCount(int count) {
-        if (mDoubleTapToastCount != count) {
-            mDoubleTapToastCount = count;
-            // write the settings in the non-UI thread
-            mEventHandler.sendMessage(Message.obtain(null,
-                    EventHandler.SET_DOUBLE_TAP_TOAST_COUNT));
-        }
-    }
-
-    /**
-     * @hide
-     */
-    public void setProperty(String key, String value) {
-        if (mWebView.nativeSetProperty(key, value)) {
-            mWebView.contentInvalidateAll();
-        }
-    }
-
-    /**
-     * @hide
-     */
-    public String getProperty(String key) {
-        return mWebView.nativeGetProperty(key);
-    }
-
-    /**
-     * Transfer messages from the queue to the new WebCoreThread. Called from
-     * WebCore thread.
-     */
-    /*package*/
-    synchronized void syncSettingsAndCreateHandler(BrowserFrame frame) {
-        mBrowserFrame = frame;
-        if (DebugFlags.WEB_SETTINGS) {
-            junit.framework.Assert.assertTrue(frame.mNativeFrame != 0);
-        }
-
-        SharedPreferences sp = mContext.getSharedPreferences(PREF_FILE,
-                Context.MODE_PRIVATE);
-        if (mDoubleTapToastCount > 0) {
-            mDoubleTapToastCount = sp.getInt(DOUBLE_TAP_TOAST_COUNT,
-                    mDoubleTapToastCount);
-        }
-        nativeSync(frame.mNativeFrame);
-        mSyncPending = false;
-        mEventHandler.createHandler();
-    }
-
-    /**
-     * Let the Settings object know that our owner is being destroyed.
-     */
-    /*package*/
-    synchronized void onDestroyed() {
-    }
-
-    private int pin(int size) {
-        // FIXME: 72 is just an arbitrary max text size value.
-        if (size < 1) {
-            return 1;
-        } else if (size > 72) {
-            return 72;
-        }
-        return size;
-    }
-
-    /* Post a SYNC message to handle syncing the native settings. */
-    private synchronized void postSync() {
-        // Only post if a sync is not pending
-        if (!mSyncPending) {
-            mSyncPending = mEventHandler.sendMessage(
-                    Message.obtain(null, EventHandler.SYNC));
-        }
-    }
-
-    // Synchronize the native and java settings.
-    private native void nativeSync(int nativeFrame);
 }
diff --git a/core/java/android/webkit/WebSettingsClassic.java b/core/java/android/webkit/WebSettingsClassic.java
new file mode 100644
index 0000000..6850eea
--- /dev/null
+++ b/core/java/android/webkit/WebSettingsClassic.java
@@ -0,0 +1,1702 @@
+/*
+ * Copyright (C) 2012 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 android.webkit;
+
+import android.content.Context;
+import android.content.SharedPreferences;
+import android.content.pm.PackageManager;
+import android.os.Build;
+import android.os.Handler;
+import android.os.Message;
+import android.util.DisplayMetrics;
+import android.util.EventLog;
+
+import java.util.Locale;
+
+/**
+ * WebSettings implementation for the WebViewClassic implementation of WebView.
+ * @hide
+ */
+public class WebSettingsClassic extends WebSettings {
+    // TODO: Keep this up to date
+    private static final String PREVIOUS_VERSION = "4.0.3";
+
+    // WebView associated with this WebSettings.
+    private WebViewClassic mWebView;
+    // BrowserFrame used to access the native frame pointer.
+    private BrowserFrame mBrowserFrame;
+    // Flag to prevent multiple SYNC messages at one time.
+    private boolean mSyncPending = false;
+    // Custom handler that queues messages until the WebCore thread is active.
+    private final EventHandler mEventHandler;
+
+    // Private settings so we don't have to go into native code to
+    // retrieve the values. After setXXX, postSync() needs to be called.
+    //
+    // The default values need to match those in WebSettings.cpp
+    // If the defaults change, please also update the JavaDocs so developers
+    // know what they are.
+    private LayoutAlgorithm mLayoutAlgorithm = LayoutAlgorithm.NARROW_COLUMNS;
+    private Context         mContext;
+    private int             mTextSize = 100;
+    private String          mStandardFontFamily = "sans-serif";
+    private String          mFixedFontFamily = "monospace";
+    private String          mSansSerifFontFamily = "sans-serif";
+    private String          mSerifFontFamily = "serif";
+    private String          mCursiveFontFamily = "cursive";
+    private String          mFantasyFontFamily = "fantasy";
+    private String          mDefaultTextEncoding;
+    private String          mUserAgent;
+    private boolean         mUseDefaultUserAgent;
+    private String          mAcceptLanguage;
+    private int             mMinimumFontSize = 8;
+    private int             mMinimumLogicalFontSize = 8;
+    private int             mDefaultFontSize = 16;
+    private int             mDefaultFixedFontSize = 13;
+    private int             mPageCacheCapacity = 0;
+    private boolean         mLoadsImagesAutomatically = true;
+    private boolean         mBlockNetworkImage = false;
+    private boolean         mBlockNetworkLoads;
+    private boolean         mJavaScriptEnabled = false;
+    private boolean         mHardwareAccelSkia = false;
+    private boolean         mShowVisualIndicator = false;
+    private PluginState     mPluginState = PluginState.OFF;
+    private boolean         mJavaScriptCanOpenWindowsAutomatically = false;
+    private boolean         mUseDoubleTree = false;
+    private boolean         mUseWideViewport = false;
+    private boolean         mSupportMultipleWindows = false;
+    private boolean         mShrinksStandaloneImagesToFit = false;
+    private long            mMaximumDecodedImageSize = 0; // 0 means default
+    private boolean         mPrivateBrowsingEnabled = false;
+    private boolean         mSyntheticLinksEnabled = true;
+    // HTML5 API flags
+    private boolean         mAppCacheEnabled = false;
+    private boolean         mDatabaseEnabled = false;
+    private boolean         mDomStorageEnabled = false;
+    private boolean         mWorkersEnabled = false;  // only affects V8.
+    private boolean         mGeolocationEnabled = true;
+    private boolean         mXSSAuditorEnabled = false;
+    // HTML5 configuration parameters
+    private long            mAppCacheMaxSize = Long.MAX_VALUE;
+    private String          mAppCachePath = null;
+    private String          mDatabasePath = "";
+    // The WebCore DatabaseTracker only allows the database path to be set
+    // once. Keep track of when the path has been set.
+    private boolean         mDatabasePathHasBeenSet = false;
+    private String          mGeolocationDatabasePath = "";
+    // Don't need to synchronize the get/set methods as they
+    // are basic types, also none of these values are used in
+    // native WebCore code.
+    private ZoomDensity     mDefaultZoom = ZoomDensity.MEDIUM;
+    private RenderPriority  mRenderPriority = RenderPriority.NORMAL;
+    private int             mOverrideCacheMode = LOAD_DEFAULT;
+    private int             mDoubleTapZoom = 100;
+    private boolean         mSaveFormData = true;
+    private boolean         mAutoFillEnabled = false;
+    private boolean         mSavePassword = true;
+    private boolean         mLightTouchEnabled = false;
+    private boolean         mNeedInitialFocus = true;
+    private boolean         mNavDump = false;
+    private boolean         mSupportZoom = true;
+    private boolean         mBuiltInZoomControls = false;
+    private boolean         mDisplayZoomControls = true;
+    private boolean         mAllowFileAccess = true;
+    private boolean         mAllowContentAccess = true;
+    private boolean         mLoadWithOverviewMode = false;
+    private boolean         mEnableSmoothTransition = false;
+    private boolean         mForceUserScalable = false;
+
+    // AutoFill Profile data
+    /**
+     * @hide for now, pending API council approval.
+     */
+    public static class AutoFillProfile {
+        private int mUniqueId;
+        private String mFullName;
+        private String mEmailAddress;
+        private String mCompanyName;
+        private String mAddressLine1;
+        private String mAddressLine2;
+        private String mCity;
+        private String mState;
+        private String mZipCode;
+        private String mCountry;
+        private String mPhoneNumber;
+
+        public AutoFillProfile(int uniqueId, String fullName, String email,
+                String companyName, String addressLine1, String addressLine2,
+                String city, String state, String zipCode, String country,
+                String phoneNumber) {
+            mUniqueId = uniqueId;
+            mFullName = fullName;
+            mEmailAddress = email;
+            mCompanyName = companyName;
+            mAddressLine1 = addressLine1;
+            mAddressLine2 = addressLine2;
+            mCity = city;
+            mState = state;
+            mZipCode = zipCode;
+            mCountry = country;
+            mPhoneNumber = phoneNumber;
+        }
+
+        public int getUniqueId() { return mUniqueId; }
+        public String getFullName() { return mFullName; }
+        public String getEmailAddress() { return mEmailAddress; }
+        public String getCompanyName() { return mCompanyName; }
+        public String getAddressLine1() { return mAddressLine1; }
+        public String getAddressLine2() { return mAddressLine2; }
+        public String getCity() { return mCity; }
+        public String getState() { return mState; }
+        public String getZipCode() { return mZipCode; }
+        public String getCountry() { return mCountry; }
+        public String getPhoneNumber() { return mPhoneNumber; }
+    }
+
+
+    private AutoFillProfile mAutoFillProfile;
+
+    private boolean         mUseWebViewBackgroundForOverscroll = true;
+
+    // private WebSettings, not accessible by the host activity
+    static private int      mDoubleTapToastCount = 3;
+
+    private static final String PREF_FILE = "WebViewSettings";
+    private static final String DOUBLE_TAP_TOAST_COUNT = "double_tap_toast_count";
+
+    // Class to handle messages before WebCore is ready.
+    private class EventHandler {
+        // Message id for syncing
+        static final int SYNC = 0;
+        // Message id for setting priority
+        static final int PRIORITY = 1;
+        // Message id for writing double-tap toast count
+        static final int SET_DOUBLE_TAP_TOAST_COUNT = 2;
+        // Actual WebCore thread handler
+        private Handler mHandler;
+
+        private synchronized void createHandler() {
+            // as mRenderPriority can be set before thread is running, sync up
+            setRenderPriority();
+
+            // create a new handler
+            mHandler = new Handler() {
+                @Override
+                public void handleMessage(Message msg) {
+                    switch (msg.what) {
+                        case SYNC:
+                            synchronized (WebSettingsClassic.this) {
+                                if (mBrowserFrame.mNativeFrame != 0) {
+                                    nativeSync(mBrowserFrame.mNativeFrame);
+                                }
+                                mSyncPending = false;
+                            }
+                            break;
+
+                        case PRIORITY: {
+                            setRenderPriority();
+                            break;
+                        }
+
+                        case SET_DOUBLE_TAP_TOAST_COUNT: {
+                            SharedPreferences.Editor editor = mContext
+                                    .getSharedPreferences(PREF_FILE,
+                                            Context.MODE_PRIVATE).edit();
+                            editor.putInt(DOUBLE_TAP_TOAST_COUNT,
+                                    mDoubleTapToastCount);
+                            editor.commit();
+                            break;
+                        }
+                    }
+                }
+            };
+        }
+
+        private void setRenderPriority() {
+            synchronized (WebSettingsClassic.this) {
+                if (mRenderPriority == RenderPriority.NORMAL) {
+                    android.os.Process.setThreadPriority(
+                            android.os.Process.THREAD_PRIORITY_DEFAULT);
+                } else if (mRenderPriority == RenderPriority.HIGH) {
+                    android.os.Process.setThreadPriority(
+                            android.os.Process.THREAD_PRIORITY_FOREGROUND +
+                            android.os.Process.THREAD_PRIORITY_LESS_FAVORABLE);
+                } else if (mRenderPriority == RenderPriority.LOW) {
+                    android.os.Process.setThreadPriority(
+                            android.os.Process.THREAD_PRIORITY_BACKGROUND);
+                }
+            }
+        }
+
+        /**
+         * Send a message to the private queue or handler.
+         */
+        private synchronized boolean sendMessage(Message msg) {
+            if (mHandler != null) {
+                mHandler.sendMessage(msg);
+                return true;
+            } else {
+                return false;
+            }
+        }
+    }
+
+    // User agent strings.
+    private static final String DESKTOP_USERAGENT = "Mozilla/5.0 (X11; " +
+        "Linux x86_64) AppleWebKit/534.24 (KHTML, like Gecko) " +
+        "Chrome/11.0.696.34 Safari/534.24";
+    private static final String IPHONE_USERAGENT =
+            "Mozilla/5.0 (iPhone; U; CPU iPhone OS 3_0 like Mac OS X; en-us)"
+            + " AppleWebKit/528.18 (KHTML, like Gecko) Version/4.0"
+            + " Mobile/7A341 Safari/528.16";
+    private static Locale sLocale;
+    private static Object sLockForLocaleSettings;
+
+    /**
+     * Package constructor to prevent clients from creating a new settings
+     * instance.
+     */
+    WebSettingsClassic(Context context, WebViewClassic webview) {
+        mEventHandler = new EventHandler();
+        mContext = context;
+        mWebView = webview;
+        mDefaultTextEncoding = context.getString(com.android.internal.
+                                                 R.string.default_text_encoding);
+
+        if (sLockForLocaleSettings == null) {
+            sLockForLocaleSettings = new Object();
+            sLocale = Locale.getDefault();
+        }
+        mAcceptLanguage = getCurrentAcceptLanguage();
+        mUserAgent = getCurrentUserAgent();
+        mUseDefaultUserAgent = true;
+
+        mBlockNetworkLoads = mContext.checkPermission(
+                "android.permission.INTERNET", android.os.Process.myPid(),
+                android.os.Process.myUid()) != PackageManager.PERMISSION_GRANTED;
+    }
+
+    private static final String ACCEPT_LANG_FOR_US_LOCALE = "en-US";
+
+    /**
+     * Looks at sLocale and returns current AcceptLanguage String.
+     * @return Current AcceptLanguage String.
+     */
+    private String getCurrentAcceptLanguage() {
+        Locale locale;
+        synchronized(sLockForLocaleSettings) {
+            locale = sLocale;
+        }
+        StringBuilder buffer = new StringBuilder();
+        addLocaleToHttpAcceptLanguage(buffer, locale);
+
+        if (!Locale.US.equals(locale)) {
+            if (buffer.length() > 0) {
+                buffer.append(", ");
+            }
+            buffer.append(ACCEPT_LANG_FOR_US_LOCALE);
+        }
+
+        return buffer.toString();
+    }
+
+    /**
+     * Convert obsolete language codes, including Hebrew/Indonesian/Yiddish,
+     * to new standard.
+     */
+    private static String convertObsoleteLanguageCodeToNew(String langCode) {
+        if (langCode == null) {
+            return null;
+        }
+        if ("iw".equals(langCode)) {
+            // Hebrew
+            return "he";
+        } else if ("in".equals(langCode)) {
+            // Indonesian
+            return "id";
+        } else if ("ji".equals(langCode)) {
+            // Yiddish
+            return "yi";
+        }
+        return langCode;
+    }
+
+    private static void addLocaleToHttpAcceptLanguage(StringBuilder builder,
+                                                      Locale locale) {
+        String language = convertObsoleteLanguageCodeToNew(locale.getLanguage());
+        if (language != null) {
+            builder.append(language);
+            String country = locale.getCountry();
+            if (country != null) {
+                builder.append("-");
+                builder.append(country);
+            }
+        }
+    }
+
+    /**
+     * Looks at sLocale and mContext and returns current UserAgent String.
+     * @return Current UserAgent String.
+     */
+    private synchronized String getCurrentUserAgent() {
+        Locale locale;
+        synchronized(sLockForLocaleSettings) {
+            locale = sLocale;
+        }
+        StringBuffer buffer = new StringBuffer();
+        // Add version
+        final String version = Build.VERSION.RELEASE;
+        if (version.length() > 0) {
+            if (Character.isDigit(version.charAt(0))) {
+                // Release is a version, eg "3.1"
+                buffer.append(version);
+            } else {
+                // Release is a codename, eg "Honeycomb"
+                // In this case, use the previous release's version
+                buffer.append(PREVIOUS_VERSION);
+            }
+        } else {
+            // default to "1.0"
+            buffer.append("1.0");
+        }
+        buffer.append("; ");
+        final String language = locale.getLanguage();
+        if (language != null) {
+            buffer.append(convertObsoleteLanguageCodeToNew(language));
+            final String country = locale.getCountry();
+            if (country != null) {
+                buffer.append("-");
+                buffer.append(country.toLowerCase());
+            }
+        } else {
+            // default to "en"
+            buffer.append("en");
+        }
+        buffer.append(";");
+        // add the model for the release build
+        if ("REL".equals(Build.VERSION.CODENAME)) {
+            final String model = Build.MODEL;
+            if (model.length() > 0) {
+                buffer.append(" ");
+                buffer.append(model);
+            }
+        }
+        final String id = Build.ID;
+        if (id.length() > 0) {
+            buffer.append(" Build/");
+            buffer.append(id);
+        }
+        String mobile = mContext.getResources().getText(
+            com.android.internal.R.string.web_user_agent_target_content).toString();
+        final String base = mContext.getResources().getText(
+                com.android.internal.R.string.web_user_agent).toString();
+        return String.format(base, buffer, mobile);
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setNavDump(boolean)
+     */
+    @Override
+    @Deprecated
+    public void setNavDump(boolean enabled) {
+        mNavDump = enabled;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getNavDump()
+     */
+    @Override
+    @Deprecated
+    public boolean getNavDump() {
+        return mNavDump;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setSupportZoom(boolean)
+     */
+    @Override
+    public void setSupportZoom(boolean support) {
+        mSupportZoom = support;
+        mWebView.updateMultiTouchSupport(mContext);
+    }
+
+    /**
+     * @see android.webkit.WebSettings#supportZoom()
+     */
+    @Override
+    public boolean supportZoom() {
+        return mSupportZoom;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setBuiltInZoomControls(boolean)
+     */
+    @Override
+    public void setBuiltInZoomControls(boolean enabled) {
+        mBuiltInZoomControls = enabled;
+        mWebView.updateMultiTouchSupport(mContext);
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getBuiltInZoomControls()
+     */
+    @Override
+    public boolean getBuiltInZoomControls() {
+        return mBuiltInZoomControls;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setDisplayZoomControls(boolean)
+     */
+    @Override
+    public void setDisplayZoomControls(boolean enabled) {
+        mDisplayZoomControls = enabled;
+        mWebView.updateMultiTouchSupport(mContext);
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getDisplayZoomControls()
+     */
+    @Override
+    public boolean getDisplayZoomControls() {
+        return mDisplayZoomControls;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setAllowFileAccess(boolean)
+     */
+    @Override
+    public void setAllowFileAccess(boolean allow) {
+        mAllowFileAccess = allow;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getAllowFileAccess()
+     */
+    @Override
+    public boolean getAllowFileAccess() {
+        return mAllowFileAccess;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setAllowContentAccess(boolean)
+     */
+    @Override
+    public void setAllowContentAccess(boolean allow) {
+        mAllowContentAccess = allow;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getAllowContentAccess()
+     */
+    @Override
+    public boolean getAllowContentAccess() {
+        return mAllowContentAccess;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setLoadWithOverviewMode(boolean)
+     */
+    @Override
+    public void setLoadWithOverviewMode(boolean overview) {
+        mLoadWithOverviewMode = overview;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getLoadWithOverviewMode()
+     */
+    @Override
+    public boolean getLoadWithOverviewMode() {
+        return mLoadWithOverviewMode;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setEnableSmoothTransition(boolean)
+     */
+    @Override
+    public void setEnableSmoothTransition(boolean enable) {
+        mEnableSmoothTransition = enable;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#enableSmoothTransition()
+     */
+    @Override
+    public boolean enableSmoothTransition() {
+        return mEnableSmoothTransition;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setUseWebViewBackgroundForOverscrollBackground(boolean)
+     */
+    @Override
+    @Deprecated
+    public void setUseWebViewBackgroundForOverscrollBackground(boolean view) {
+        mUseWebViewBackgroundForOverscroll = view;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getUseWebViewBackgroundForOverscrollBackground()
+     */
+    @Override
+    @Deprecated
+    public boolean getUseWebViewBackgroundForOverscrollBackground() {
+        return mUseWebViewBackgroundForOverscroll;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setSaveFormData(boolean)
+     */
+    @Override
+    public void setSaveFormData(boolean save) {
+        mSaveFormData = save;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getSaveFormData()
+     */
+    @Override
+    public boolean getSaveFormData() {
+        return mSaveFormData && !mPrivateBrowsingEnabled;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setSavePassword(boolean)
+     */
+    @Override
+    public void setSavePassword(boolean save) {
+        mSavePassword = save;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getSavePassword()
+     */
+    @Override
+    public boolean getSavePassword() {
+        return mSavePassword;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setTextZoom(int)
+     */
+    @Override
+    public synchronized void setTextZoom(int textZoom) {
+        if (mTextSize != textZoom) {
+            if (WebViewClassic.mLogEvent) {
+                EventLog.writeEvent(EventLogTags.BROWSER_TEXT_SIZE_CHANGE,
+                        mTextSize, textZoom);
+            }
+            mTextSize = textZoom;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getTextZoom()
+     */
+    @Override
+    public synchronized int getTextZoom() {
+        return mTextSize;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setTextSize(android.webkit.WebSettingsClassic.TextSize)
+     */
+    @Override
+    public synchronized void setTextSize(TextSize t) {
+        setTextZoom(t.value);
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getTextSize()
+     */
+    @Override
+    public synchronized TextSize getTextSize() {
+        TextSize closestSize = null;
+        int smallestDelta = Integer.MAX_VALUE;
+        for (TextSize size : TextSize.values()) {
+            int delta = Math.abs(mTextSize - size.value);
+            if (delta == 0) {
+                return size;
+            }
+            if (delta < smallestDelta) {
+                smallestDelta = delta;
+                closestSize = size;
+            }
+        }
+        return closestSize != null ? closestSize : TextSize.NORMAL;
+    }
+
+    /**
+     * Set the double-tap zoom of the page in percent. Default is 100.
+     * @param doubleTapZoom A percent value for increasing or decreasing the double-tap zoom.
+     * @hide
+     */
+    public void setDoubleTapZoom(int doubleTapZoom) {
+        if (mDoubleTapZoom != doubleTapZoom) {
+            mDoubleTapZoom = doubleTapZoom;
+            mWebView.updateDoubleTapZoom(doubleTapZoom);
+        }
+    }
+
+    /**
+     * Get the double-tap zoom of the page in percent.
+     * @return A percent value describing the double-tap zoom.
+     * @hide
+     */
+    public int getDoubleTapZoom() {
+        return mDoubleTapZoom;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setDefaultZoom(android.webkit.WebSettingsClassic.ZoomDensity)
+     */
+    @Override
+    public void setDefaultZoom(ZoomDensity zoom) {
+        if (mDefaultZoom != zoom) {
+            mDefaultZoom = zoom;
+            mWebView.adjustDefaultZoomDensity(zoom.value);
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getDefaultZoom()
+     */
+    @Override
+    public ZoomDensity getDefaultZoom() {
+        return mDefaultZoom;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setLightTouchEnabled(boolean)
+     */
+    @Override
+    public void setLightTouchEnabled(boolean enabled) {
+        mLightTouchEnabled = enabled;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getLightTouchEnabled()
+     */
+    @Override
+    public boolean getLightTouchEnabled() {
+        return mLightTouchEnabled;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setUseDoubleTree(boolean)
+     */
+    @Override
+    @Deprecated
+    public synchronized void setUseDoubleTree(boolean use) {
+        return;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getUseDoubleTree()
+     */
+    @Override
+    @Deprecated
+    public synchronized boolean getUseDoubleTree() {
+        return false;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setUserAgent(int)
+     */
+    @Override
+    @Deprecated
+    public synchronized void setUserAgent(int ua) {
+        String uaString = null;
+        if (ua == 1) {
+            if (DESKTOP_USERAGENT.equals(mUserAgent)) {
+                return; // do nothing
+            } else {
+                uaString = DESKTOP_USERAGENT;
+            }
+        } else if (ua == 2) {
+            if (IPHONE_USERAGENT.equals(mUserAgent)) {
+                return; // do nothing
+            } else {
+                uaString = IPHONE_USERAGENT;
+            }
+        } else if (ua != 0) {
+            return; // do nothing
+        }
+        setUserAgentString(uaString);
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getUserAgent()
+     */
+    @Override
+    @Deprecated
+    public synchronized int getUserAgent() {
+        if (DESKTOP_USERAGENT.equals(mUserAgent)) {
+            return 1;
+        } else if (IPHONE_USERAGENT.equals(mUserAgent)) {
+            return 2;
+        } else if (mUseDefaultUserAgent) {
+            return 0;
+        }
+        return -1;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setUseWideViewPort(boolean)
+     */
+    @Override
+    public synchronized void setUseWideViewPort(boolean use) {
+        if (mUseWideViewport != use) {
+            mUseWideViewport = use;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getUseWideViewPort()
+     */
+    @Override
+    public synchronized boolean getUseWideViewPort() {
+        return mUseWideViewport;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setSupportMultipleWindows(boolean)
+     */
+    @Override
+    public synchronized void setSupportMultipleWindows(boolean support) {
+        if (mSupportMultipleWindows != support) {
+            mSupportMultipleWindows = support;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#supportMultipleWindows()
+     */
+    @Override
+    public synchronized boolean supportMultipleWindows() {
+        return mSupportMultipleWindows;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setLayoutAlgorithm(android.webkit.WebSettingsClassic.LayoutAlgorithm)
+     */
+    @Override
+    public synchronized void setLayoutAlgorithm(LayoutAlgorithm l) {
+        // XXX: This will only be affective if libwebcore was built with
+        // ANDROID_LAYOUT defined.
+        if (mLayoutAlgorithm != l) {
+            mLayoutAlgorithm = l;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getLayoutAlgorithm()
+     */
+    @Override
+    public synchronized LayoutAlgorithm getLayoutAlgorithm() {
+        return mLayoutAlgorithm;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setStandardFontFamily(java.lang.String)
+     */
+    @Override
+    public synchronized void setStandardFontFamily(String font) {
+        if (font != null && !font.equals(mStandardFontFamily)) {
+            mStandardFontFamily = font;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getStandardFontFamily()
+     */
+    @Override
+    public synchronized String getStandardFontFamily() {
+        return mStandardFontFamily;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setFixedFontFamily(java.lang.String)
+     */
+    @Override
+    public synchronized void setFixedFontFamily(String font) {
+        if (font != null && !font.equals(mFixedFontFamily)) {
+            mFixedFontFamily = font;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getFixedFontFamily()
+     */
+    @Override
+    public synchronized String getFixedFontFamily() {
+        return mFixedFontFamily;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setSansSerifFontFamily(java.lang.String)
+     */
+    @Override
+    public synchronized void setSansSerifFontFamily(String font) {
+        if (font != null && !font.equals(mSansSerifFontFamily)) {
+            mSansSerifFontFamily = font;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getSansSerifFontFamily()
+     */
+    @Override
+    public synchronized String getSansSerifFontFamily() {
+        return mSansSerifFontFamily;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setSerifFontFamily(java.lang.String)
+     */
+    @Override
+    public synchronized void setSerifFontFamily(String font) {
+        if (font != null && !font.equals(mSerifFontFamily)) {
+            mSerifFontFamily = font;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getSerifFontFamily()
+     */
+    @Override
+    public synchronized String getSerifFontFamily() {
+        return mSerifFontFamily;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setCursiveFontFamily(java.lang.String)
+     */
+    @Override
+    public synchronized void setCursiveFontFamily(String font) {
+        if (font != null && !font.equals(mCursiveFontFamily)) {
+            mCursiveFontFamily = font;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getCursiveFontFamily()
+     */
+    @Override
+    public synchronized String getCursiveFontFamily() {
+        return mCursiveFontFamily;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setFantasyFontFamily(java.lang.String)
+     */
+    @Override
+    public synchronized void setFantasyFontFamily(String font) {
+        if (font != null && !font.equals(mFantasyFontFamily)) {
+            mFantasyFontFamily = font;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getFantasyFontFamily()
+     */
+    @Override
+    public synchronized String getFantasyFontFamily() {
+        return mFantasyFontFamily;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setMinimumFontSize(int)
+     */
+    @Override
+    public synchronized void setMinimumFontSize(int size) {
+        size = pin(size);
+        if (mMinimumFontSize != size) {
+            mMinimumFontSize = size;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getMinimumFontSize()
+     */
+    @Override
+    public synchronized int getMinimumFontSize() {
+        return mMinimumFontSize;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setMinimumLogicalFontSize(int)
+     */
+    @Override
+    public synchronized void setMinimumLogicalFontSize(int size) {
+        size = pin(size);
+        if (mMinimumLogicalFontSize != size) {
+            mMinimumLogicalFontSize = size;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getMinimumLogicalFontSize()
+     */
+    @Override
+    public synchronized int getMinimumLogicalFontSize() {
+        return mMinimumLogicalFontSize;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setDefaultFontSize(int)
+     */
+    @Override
+    public synchronized void setDefaultFontSize(int size) {
+        size = pin(size);
+        if (mDefaultFontSize != size) {
+            mDefaultFontSize = size;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getDefaultFontSize()
+     */
+    @Override
+    public synchronized int getDefaultFontSize() {
+        return mDefaultFontSize;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setDefaultFixedFontSize(int)
+     */
+    @Override
+    public synchronized void setDefaultFixedFontSize(int size) {
+        size = pin(size);
+        if (mDefaultFixedFontSize != size) {
+            mDefaultFixedFontSize = size;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getDefaultFixedFontSize()
+     */
+    @Override
+    public synchronized int getDefaultFixedFontSize() {
+        return mDefaultFixedFontSize;
+    }
+
+    /**
+     * Set the number of pages cached by the WebKit for the history navigation.
+     * @param size A non-negative integer between 0 (no cache) and 20 (max).
+     * @hide
+     */
+    public synchronized void setPageCacheCapacity(int size) {
+        if (size < 0) size = 0;
+        if (size > 20) size = 20;
+        if (mPageCacheCapacity != size) {
+            mPageCacheCapacity = size;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setLoadsImagesAutomatically(boolean)
+     */
+    @Override
+    public synchronized void setLoadsImagesAutomatically(boolean flag) {
+        if (mLoadsImagesAutomatically != flag) {
+            mLoadsImagesAutomatically = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getLoadsImagesAutomatically()
+     */
+    @Override
+    public synchronized boolean getLoadsImagesAutomatically() {
+        return mLoadsImagesAutomatically;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setBlockNetworkImage(boolean)
+     */
+    @Override
+    public synchronized void setBlockNetworkImage(boolean flag) {
+        if (mBlockNetworkImage != flag) {
+            mBlockNetworkImage = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getBlockNetworkImage()
+     */
+    @Override
+    public synchronized boolean getBlockNetworkImage() {
+        return mBlockNetworkImage;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setBlockNetworkLoads(boolean)
+     */
+    @Override
+    public synchronized void setBlockNetworkLoads(boolean flag) {
+        if (mBlockNetworkLoads != flag) {
+            mBlockNetworkLoads = flag;
+            verifyNetworkAccess();
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getBlockNetworkLoads()
+     */
+    @Override
+    public synchronized boolean getBlockNetworkLoads() {
+        return mBlockNetworkLoads;
+    }
+
+
+    private void verifyNetworkAccess() {
+        if (!mBlockNetworkLoads) {
+            if (mContext.checkPermission("android.permission.INTERNET",
+                    android.os.Process.myPid(), android.os.Process.myUid()) !=
+                        PackageManager.PERMISSION_GRANTED) {
+                throw new SecurityException
+                        ("Permission denied - " +
+                                "application missing INTERNET permission");
+            }
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setJavaScriptEnabled(boolean)
+     */
+    @Override
+    public synchronized void setJavaScriptEnabled(boolean flag) {
+        if (mJavaScriptEnabled != flag) {
+            mJavaScriptEnabled = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * Tell the WebView to use Skia's hardware accelerated rendering path
+     * @param flag True if the WebView should use Skia's hw-accel path
+     * @hide
+     */
+    public synchronized void setHardwareAccelSkiaEnabled(boolean flag) {
+        if (mHardwareAccelSkia != flag) {
+            mHardwareAccelSkia = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @return True if the WebView is using hardware accelerated skia
+     * @hide
+     */
+    public synchronized boolean getHardwareAccelSkiaEnabled() {
+        return mHardwareAccelSkia;
+    }
+
+    /**
+     * Tell the WebView to show the visual indicator
+     * @param flag True if the WebView should show the visual indicator
+     * @hide
+     */
+    public synchronized void setShowVisualIndicator(boolean flag) {
+        if (mShowVisualIndicator != flag) {
+            mShowVisualIndicator = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @return True if the WebView is showing the visual indicator
+     * @hide
+     */
+    public synchronized boolean getShowVisualIndicator() {
+        return mShowVisualIndicator;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setPluginsEnabled(boolean)
+     */
+    @Override
+    @Deprecated
+    public synchronized void setPluginsEnabled(boolean flag) {
+        setPluginState(flag ? PluginState.ON : PluginState.OFF);
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setPluginState(android.webkit.WebSettingsClassic.PluginState)
+     */
+    @Override
+    public synchronized void setPluginState(PluginState state) {
+        if (mPluginState != state) {
+            mPluginState = state;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setPluginsPath(java.lang.String)
+     */
+    @Override
+    @Deprecated
+    public synchronized void setPluginsPath(String pluginsPath) {
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setDatabasePath(java.lang.String)
+     */
+    @Override
+    public synchronized void setDatabasePath(String databasePath) {
+        if (databasePath != null && !mDatabasePathHasBeenSet) {
+            mDatabasePath = databasePath;
+            mDatabasePathHasBeenSet = true;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setGeolocationDatabasePath(java.lang.String)
+     */
+    @Override
+    public synchronized void setGeolocationDatabasePath(String databasePath) {
+        if (databasePath != null
+                && !databasePath.equals(mGeolocationDatabasePath)) {
+            mGeolocationDatabasePath = databasePath;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setAppCacheEnabled(boolean)
+     */
+    @Override
+    public synchronized void setAppCacheEnabled(boolean flag) {
+        if (mAppCacheEnabled != flag) {
+            mAppCacheEnabled = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setAppCachePath(java.lang.String)
+     */
+    @Override
+    public synchronized void setAppCachePath(String path) {
+        // We test for a valid path and for repeated setting on the native
+        // side, but we can avoid syncing in some simple cases. 
+        if (mAppCachePath == null && path != null && !path.isEmpty()) {
+            mAppCachePath = path;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setAppCacheMaxSize(long)
+     */
+    @Override
+    public synchronized void setAppCacheMaxSize(long appCacheMaxSize) {
+        if (appCacheMaxSize != mAppCacheMaxSize) {
+            mAppCacheMaxSize = appCacheMaxSize;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setDatabaseEnabled(boolean)
+     */
+    @Override
+    public synchronized void setDatabaseEnabled(boolean flag) {
+       if (mDatabaseEnabled != flag) {
+           mDatabaseEnabled = flag;
+           postSync();
+       }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setDomStorageEnabled(boolean)
+     */
+    @Override
+    public synchronized void setDomStorageEnabled(boolean flag) {
+       if (mDomStorageEnabled != flag) {
+           mDomStorageEnabled = flag;
+           postSync();
+       }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getDomStorageEnabled()
+     */
+    @Override
+    public synchronized boolean getDomStorageEnabled() {
+       return mDomStorageEnabled;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getDatabasePath()
+     */
+    @Override
+    public synchronized String getDatabasePath() {
+        return mDatabasePath;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getDatabaseEnabled()
+     */
+    @Override
+    public synchronized boolean getDatabaseEnabled() {
+        return mDatabaseEnabled;
+    }
+
+    /**
+     * Tell the WebView to enable WebWorkers API.
+     * @param flag True if the WebView should enable WebWorkers.
+     * Note that this flag only affects V8. JSC does not have
+     * an equivalent setting.
+     * @hide
+     */
+    public synchronized void setWorkersEnabled(boolean flag) {
+        if (mWorkersEnabled != flag) {
+            mWorkersEnabled = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setGeolocationEnabled(boolean)
+     */
+    @Override
+    public synchronized void setGeolocationEnabled(boolean flag) {
+        if (mGeolocationEnabled != flag) {
+            mGeolocationEnabled = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * Sets whether XSS Auditor is enabled.
+     * @param flag Whether XSS Auditor should be enabled.
+     * @hide Only used by LayoutTestController.
+     */
+    public synchronized void setXSSAuditorEnabled(boolean flag) {
+        if (mXSSAuditorEnabled != flag) {
+            mXSSAuditorEnabled = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getJavaScriptEnabled()
+     */
+    @Override
+    public synchronized boolean getJavaScriptEnabled() {
+        return mJavaScriptEnabled;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getPluginsEnabled()
+     */
+    @Override
+    @Deprecated
+    public synchronized boolean getPluginsEnabled() {
+        return mPluginState == PluginState.ON;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getPluginState()
+     */
+    @Override
+    public synchronized PluginState getPluginState() {
+        return mPluginState;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getPluginsPath()
+     */
+    @Override
+    @Deprecated
+    public synchronized String getPluginsPath() {
+        return "";
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setJavaScriptCanOpenWindowsAutomatically(boolean)
+     */
+    @Override
+    public synchronized void setJavaScriptCanOpenWindowsAutomatically(
+            boolean flag) {
+        if (mJavaScriptCanOpenWindowsAutomatically != flag) {
+            mJavaScriptCanOpenWindowsAutomatically = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getJavaScriptCanOpenWindowsAutomatically()
+     */
+    @Override
+    public synchronized boolean getJavaScriptCanOpenWindowsAutomatically() {
+        return mJavaScriptCanOpenWindowsAutomatically;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setDefaultTextEncodingName(java.lang.String)
+     */
+    @Override
+    public synchronized void setDefaultTextEncodingName(String encoding) {
+        if (encoding != null && !encoding.equals(mDefaultTextEncoding)) {
+            mDefaultTextEncoding = encoding;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getDefaultTextEncodingName()
+     */
+    @Override
+    public synchronized String getDefaultTextEncodingName() {
+        return mDefaultTextEncoding;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setUserAgentString(java.lang.String)
+     */
+    @Override
+    public synchronized void setUserAgentString(String ua) {
+        if (ua == null || ua.length() == 0) {
+            synchronized(sLockForLocaleSettings) {
+                Locale currentLocale = Locale.getDefault();
+                if (!sLocale.equals(currentLocale)) {
+                    sLocale = currentLocale;
+                    mAcceptLanguage = getCurrentAcceptLanguage();
+                }
+            }
+            ua = getCurrentUserAgent();
+            mUseDefaultUserAgent = true;
+        } else  {
+            mUseDefaultUserAgent = false;
+        }
+
+        if (!ua.equals(mUserAgent)) {
+            mUserAgent = ua;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getUserAgentString()
+     */
+    @Override
+    public synchronized String getUserAgentString() {
+        if (DESKTOP_USERAGENT.equals(mUserAgent) ||
+                IPHONE_USERAGENT.equals(mUserAgent) ||
+                !mUseDefaultUserAgent) {
+            return mUserAgent;
+        }
+
+        boolean doPostSync = false;
+        synchronized(sLockForLocaleSettings) {
+            Locale currentLocale = Locale.getDefault();
+            if (!sLocale.equals(currentLocale)) {
+                sLocale = currentLocale;
+                mUserAgent = getCurrentUserAgent();
+                mAcceptLanguage = getCurrentAcceptLanguage();
+                doPostSync = true;
+            }
+        }
+        if (doPostSync) {
+            postSync();
+        }
+        return mUserAgent;
+    }
+
+    /* package api to grab the Accept Language string. */
+    /*package*/ synchronized String getAcceptLanguage() {
+        synchronized(sLockForLocaleSettings) {
+            Locale currentLocale = Locale.getDefault();
+            if (!sLocale.equals(currentLocale)) {
+                sLocale = currentLocale;
+                mAcceptLanguage = getCurrentAcceptLanguage();
+            }
+        }
+        return mAcceptLanguage;
+    }
+
+    /* package */ boolean isNarrowColumnLayout() {
+        return getLayoutAlgorithm() == LayoutAlgorithm.NARROW_COLUMNS;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setNeedInitialFocus(boolean)
+     */
+    @Override
+    public void setNeedInitialFocus(boolean flag) {
+        if (mNeedInitialFocus != flag) {
+            mNeedInitialFocus = flag;
+        }
+    }
+
+    /* Package api to get the choice whether it needs to set initial focus. */
+    /* package */ boolean getNeedInitialFocus() {
+        return mNeedInitialFocus;
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setRenderPriority(android.webkit.WebSettingsClassic.RenderPriority)
+     */
+    @Override
+    public synchronized void setRenderPriority(RenderPriority priority) {
+        if (mRenderPriority != priority) {
+            mRenderPriority = priority;
+            mEventHandler.sendMessage(Message.obtain(null,
+                    EventHandler.PRIORITY));
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#setCacheMode(int)
+     */
+    @Override
+    public void setCacheMode(int mode) {
+        if (mode != mOverrideCacheMode) {
+            mOverrideCacheMode = mode;
+            postSync();
+        }
+    }
+
+    /**
+     * @see android.webkit.WebSettings#getCacheMode()
+     */
+    @Override
+    public int getCacheMode() {
+        return mOverrideCacheMode;
+    }
+
+    /**
+     * If set, webkit alternately shrinks and expands images viewed outside
+     * of an HTML page to fit the screen. This conflicts with attempts by
+     * the UI to zoom in and out of an image, so it is set false by default.
+     * @param shrink Set true to let webkit shrink the standalone image to fit.
+     * {@hide}
+     */
+    public void setShrinksStandaloneImagesToFit(boolean shrink) {
+        if (mShrinksStandaloneImagesToFit != shrink) {
+            mShrinksStandaloneImagesToFit = shrink;
+            postSync();
+        }
+     }
+
+    /**
+     * Specify the maximum decoded image size. The default is
+     * 2 megs for small memory devices and 8 megs for large memory devices.
+     * @param size The maximum decoded size, or zero to set to the default.
+     * @hide
+     */
+    public void setMaximumDecodedImageSize(long size) {
+        if (mMaximumDecodedImageSize != size) {
+            mMaximumDecodedImageSize = size;
+            postSync();
+        }
+    }
+
+    /**
+     * Returns whether to use fixed viewport.  Use fixed viewport
+     * whenever wide viewport is on.
+     */
+    /* package */ boolean getUseFixedViewport() {
+        return getUseWideViewPort();
+    }
+
+    /**
+     * Returns whether private browsing is enabled.
+     */
+    /* package */ boolean isPrivateBrowsingEnabled() {
+        return mPrivateBrowsingEnabled;
+    }
+
+    /**
+     * Sets whether private browsing is enabled.
+     * @param flag Whether private browsing should be enabled.
+     */
+    /* package */ synchronized void setPrivateBrowsingEnabled(boolean flag) {
+        if (mPrivateBrowsingEnabled != flag) {
+            mPrivateBrowsingEnabled = flag;
+
+            // AutoFill is dependant on private browsing being enabled so
+            // reset it to take account of the new value of mPrivateBrowsingEnabled.
+            setAutoFillEnabled(mAutoFillEnabled);
+
+            postSync();
+        }
+    }
+
+    /**
+     * Returns whether the viewport metatag can disable zooming
+     * @hide
+     */
+    public boolean forceUserScalable() {
+        return mForceUserScalable;
+    }
+
+    /**
+     * Sets whether viewport metatag can disable zooming.
+     * @param flag Whether or not to forceably enable user scalable.
+     * @hide
+     */
+    public synchronized void setForceUserScalable(boolean flag) {
+        mForceUserScalable = flag;
+    }
+
+    synchronized void setSyntheticLinksEnabled(boolean flag) {
+        if (mSyntheticLinksEnabled != flag) {
+            mSyntheticLinksEnabled = flag;
+            postSync();
+        }
+    }
+
+    /**
+     * @hide
+     */
+    public synchronized void setAutoFillEnabled(boolean enabled) {
+        // AutoFill is always disabled in private browsing mode.
+        boolean autoFillEnabled = enabled && !mPrivateBrowsingEnabled;
+        if (mAutoFillEnabled != autoFillEnabled) {
+            mAutoFillEnabled = autoFillEnabled;
+            postSync();
+        }
+    }
+
+    /**
+     * @hide
+     */
+    public synchronized boolean getAutoFillEnabled() {
+        return mAutoFillEnabled;
+    }
+
+    /**
+     * @hide
+     */
+    public synchronized void setAutoFillProfile(AutoFillProfile profile) {
+        if (mAutoFillProfile != profile) {
+            mAutoFillProfile = profile;
+            postSync();
+        }
+    }
+
+    /**
+     * @hide
+     */
+    public synchronized AutoFillProfile getAutoFillProfile() {
+        return mAutoFillProfile;
+    }
+
+    int getDoubleTapToastCount() {
+        return mDoubleTapToastCount;
+    }
+
+    void setDoubleTapToastCount(int count) {
+        if (mDoubleTapToastCount != count) {
+            mDoubleTapToastCount = count;
+            // write the settings in the non-UI thread
+            mEventHandler.sendMessage(Message.obtain(null,
+                    EventHandler.SET_DOUBLE_TAP_TOAST_COUNT));
+        }
+    }
+
+    /**
+     * @hide
+     */
+    public void setProperty(String key, String value) {
+        if (mWebView.nativeSetProperty(key, value)) {
+            mWebView.contentInvalidateAll();
+        }
+    }
+
+    /**
+     * @hide
+     */
+    public String getProperty(String key) {
+        return mWebView.nativeGetProperty(key);
+    }
+
+    /**
+     * Transfer messages from the queue to the new WebCoreThread. Called from
+     * WebCore thread.
+     */
+    /*package*/
+    synchronized void syncSettingsAndCreateHandler(BrowserFrame frame) {
+        mBrowserFrame = frame;
+        if (DebugFlags.WEB_SETTINGS) {
+            junit.framework.Assert.assertTrue(frame.mNativeFrame != 0);
+        }
+
+        SharedPreferences sp = mContext.getSharedPreferences(PREF_FILE,
+                Context.MODE_PRIVATE);
+        if (mDoubleTapToastCount > 0) {
+            mDoubleTapToastCount = sp.getInt(DOUBLE_TAP_TOAST_COUNT,
+                    mDoubleTapToastCount);
+        }
+        nativeSync(frame.mNativeFrame);
+        mSyncPending = false;
+        mEventHandler.createHandler();
+    }
+
+    /**
+     * Let the Settings object know that our owner is being destroyed.
+     */
+    /*package*/
+    synchronized void onDestroyed() {
+    }
+
+    private int pin(int size) {
+        // FIXME: 72 is just an arbitrary max text size value.
+        if (size < 1) {
+            return 1;
+        } else if (size > 72) {
+            return 72;
+        }
+        return size;
+    }
+
+    /* Post a SYNC message to handle syncing the native settings. */
+    private synchronized void postSync() {
+        // Only post if a sync is not pending
+        if (!mSyncPending) {
+            mSyncPending = mEventHandler.sendMessage(
+                    Message.obtain(null, EventHandler.SYNC));
+        }
+    }
+
+    // Synchronize the native and java settings.
+    private native void nativeSync(int nativeFrame);
+}
diff --git a/core/java/android/webkit/WebTextView.java b/core/java/android/webkit/WebTextView.java
index 510c168..911073d 100644
--- a/core/java/android/webkit/WebTextView.java
+++ b/core/java/android/webkit/WebTextView.java
@@ -16,148 +16,15 @@
 
 package android.webkit;
 
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.ColorFilter;
-import android.graphics.Paint;
-import android.graphics.Paint.Style;
-import android.graphics.PixelFormat;
-import android.graphics.Rect;
-import android.graphics.drawable.ColorDrawable;
-import android.graphics.drawable.Drawable;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
-import android.os.ResultReceiver;
-import android.text.BoringLayout.Metrics;
-import android.text.DynamicLayout;
-import android.text.Editable;
-import android.text.InputFilter;
-import android.text.InputType;
-import android.text.Layout;
-import android.text.Selection;
-import android.text.Spannable;
-import android.text.TextPaint;
-import android.text.TextUtils;
-import android.text.method.MovementMethod;
-import android.text.method.Touch;
 import android.util.Log;
-import android.util.TypedValue;
-import android.view.Gravity;
-import android.view.KeyCharacterMap;
-import android.view.KeyEvent;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewConfiguration;
-import android.view.ViewGroup;
-import android.view.inputmethod.EditorInfo;
-import android.view.inputmethod.InputConnection;
-import android.view.inputmethod.InputMethodManager;
-import android.widget.AbsoluteLayout.LayoutParams;
-import android.widget.AdapterView;
-import android.widget.ArrayAdapter;
-import android.widget.AutoCompleteTextView;
-import android.widget.TextView;
-
-import junit.framework.Assert;
 
 import java.net.MalformedURLException;
 import java.net.URL;
-import java.util.ArrayList;
 
-/**
- * WebTextView is a specialized version of EditText used by WebView
- * to overlay html textfields (and textareas) to use our standard
- * text editing.
- */
-/* package */ class WebTextView extends AutoCompleteTextView
-        implements AdapterView.OnItemClickListener {
+// TODO: Move these to a better place.
+/* package */ abstract class WebTextView {
 
-    static final String LOGTAG = "webtextview";
-
-    private int mRingInset;
-
-    private WebView         mWebView;
-    private boolean         mSingle;
-    private int             mWidthSpec;
-    private int             mHeightSpec;
-    private int             mNodePointer;
-    // FIXME: This is a hack for blocking unmatched key ups, in particular
-    // on the enter key.  The method for blocking unmatched key ups prevents
-    // the shift key from working properly.
-    private boolean         mGotEnterDown;
-    private int             mMaxLength;
-    // Keep track of the text before the change so we know whether we actually
-    // need to send down the DOM events.
-    private String          mPreChange;
-    // Variables for keeping track of the touch down, to send to the WebView
-    // when a drag starts
-    private float           mDragStartX;
-    private float           mDragStartY;
-    private long            mDragStartTime;
-    private boolean         mDragSent;
-    // True if the most recent drag event has caused either the TextView to
-    // scroll or the web page to scroll.  Gets reset after a touch down.
-    private boolean         mScrolled;
-    // Whether or not a selection change was generated from webkit.  If it was,
-    // we do not need to pass the selection back to webkit.
-    private boolean         mFromWebKit;
-    // Whether or not a selection change was generated from the WebTextView
-    // gaining focus.  If it is, we do not want to pass it to webkit.  This
-    // selection comes from the MovementMethod, but we behave differently.  If
-    // WebTextView gained focus from a touch, webkit will determine the
-    // selection.
-    private boolean         mFromFocusChange;
-    // Whether or not a selection change was generated from setInputType.  We
-    // do not want to pass this change to webkit.
-    private boolean         mFromSetInputType;
-    private boolean         mGotTouchDown;
-    // Keep track of whether a long press has happened.  Only meaningful after
-    // an ACTION_DOWN MotionEvent
-    private boolean         mHasPerformedLongClick;
-    private boolean         mInSetTextAndKeepSelection;
-    // Array to store the final character added in onTextChanged, so that its
-    // KeyEvents may be determined.
-    private char[]          mCharacter = new char[1];
-    // This is used to reset the length filter when on a textfield
-    // with no max length.
-    // FIXME: This can be replaced with TextView.NO_FILTERS if that
-    // is made public/protected.
-    private static final InputFilter[] NO_FILTERS = new InputFilter[0];
-    // For keeping track of the fact that the delete key was pressed, so
-    // we can simply pass a delete key instead of calling deleteSelection.
-    private boolean mGotDelete;
-    private int mDelSelStart;
-    private int mDelSelEnd;
-
-    // Keep in sync with native constant in
-    // external/webkit/WebKit/android/WebCoreSupport/autofill/WebAutoFill.cpp
-    /* package */ static final int FORM_NOT_AUTOFILLABLE = -1;
-
-    private boolean mAutoFillable; // Is this textview part of an autofillable form?
-    private int mQueryId;
-    private boolean mAutoFillProfileIsSet;
-    // Used to determine whether onFocusChanged was called as a result of
-    // calling remove().
-    private boolean mInsideRemove;
-    private class MyResultReceiver extends ResultReceiver {
-        @Override
-        protected void onReceiveResult(int resultCode, Bundle resultData) {
-            if (resultCode == InputMethodManager.RESULT_SHOWN
-                    && mWebView != null) {
-                mWebView.revealSelection();
-            }
-        }
-
-        /**
-         * @param handler
-         */
-        public MyResultReceiver(Handler handler) {
-            super(handler);
-        }
-    }
-    private MyResultReceiver mReceiver;
+    private static final String LOGTAG = "WebTextView";
 
     // Types used with setType.  Keep in sync with CachedInput.h
     static final int NORMAL_TEXT_FIELD = 0;
@@ -169,1006 +36,7 @@
     static final int TELEPHONE = 6;
     static final int URL = 7;
 
-    private static final int AUTOFILL_FORM = 100;
-    private Handler mHandler;
-
-    /**
-     * Create a new WebTextView.
-     * @param   context The Context for this WebTextView.
-     * @param   webView The WebView that created this.
-     */
-    /* package */ WebTextView(Context context, WebView webView, int autoFillQueryId) {
-        super(context, null, com.android.internal.R.attr.webTextViewStyle);
-        mWebView = webView;
-        mMaxLength = -1;
-        setAutoFillable(autoFillQueryId);
-        // Turn on subpixel text, and turn off kerning, so it better matches
-        // the text in webkit.
-        TextPaint paint = getPaint();
-        int flags = paint.getFlags() & ~Paint.DEV_KERN_TEXT_FLAG
-                | Paint.SUBPIXEL_TEXT_FLAG | Paint.DITHER_FLAG;
-        paint.setFlags(flags);
-
-        // Set the text color to black, regardless of the theme.  This ensures
-        // that other applications that use embedded WebViews will properly
-        // display the text in password textfields.
-        setTextColor(DebugFlags.DRAW_WEBTEXTVIEW ? Color.RED : Color.BLACK);
-        setBackgroundDrawable(DebugFlags.DRAW_WEBTEXTVIEW ? null : new ColorDrawable(Color.WHITE));
-
-        // This helps to align the text better with the text in the web page.
-        setIncludeFontPadding(false);
-
-        mHandler = new Handler() {
-            @Override
-            public void handleMessage(Message msg) {
-                switch (msg.what) {
-                case AUTOFILL_FORM:
-                    mWebView.autoFillForm(mQueryId);
-                    break;
-                }
-            }
-        };
-        mReceiver = new MyResultReceiver(mHandler);
-        float ringWidth = 2f * context.getResources().getDisplayMetrics().density;
-        mRingInset = (int) ringWidth;
-        setBackgroundDrawable(new BackgroundDrawable(mRingInset));
-        setPadding(getPaddingLeft(), getPaddingTop(), getPaddingRight(),
-                getPaddingBottom());
-    }
-
-    private static class BackgroundDrawable extends Drawable {
-
-        private Paint mPaint = new Paint();
-        private int mBorderWidth;
-        private Rect mInsetRect = new Rect();
-
-        public BackgroundDrawable(int width) {
-            mPaint = new Paint();
-            mPaint.setStrokeWidth(width);
-            mBorderWidth = width;
-        }
-
-        @Override
-        public void draw(Canvas canvas) {
-            mPaint.setColor(0x6633b5e5);
-            canvas.drawRect(getBounds(), mPaint);
-            mInsetRect.left = getBounds().left + mBorderWidth;
-            mInsetRect.top = getBounds().top + mBorderWidth;
-            mInsetRect.right = getBounds().right - mBorderWidth;
-            mInsetRect.bottom = getBounds().bottom - mBorderWidth;
-            mPaint.setColor(Color.WHITE);
-            canvas.drawRect(mInsetRect, mPaint);
-        }
-
-        @Override
-        public void setAlpha(int alpha) {
-        }
-
-        @Override
-        public void setColorFilter(ColorFilter cf) {
-        }
-
-        @Override
-        public int getOpacity() {
-            return PixelFormat.TRANSLUCENT;
-        }
-
-    }
-
-    public void setAutoFillable(int queryId) {
-        mAutoFillable = mWebView.getSettings().getAutoFillEnabled()
-                && (queryId != FORM_NOT_AUTOFILLABLE);
-        mQueryId = queryId;
-    }
-
-    @Override
-    public void setPadding(int left, int top, int right, int bottom) {
-        super.setPadding(left + mRingInset, top + mRingInset,
-                right + mRingInset, bottom + mRingInset);
-    }
-
-    @Override
-    public boolean dispatchKeyEvent(KeyEvent event) {
-        if (event.isSystem()) {
-            return super.dispatchKeyEvent(event);
-        }
-        // Treat ACTION_DOWN and ACTION MULTIPLE the same
-        boolean down = event.getAction() != KeyEvent.ACTION_UP;
-        int keyCode = event.getKeyCode();
-
-        boolean isArrowKey = false;
-        switch(keyCode) {
-            case KeyEvent.KEYCODE_DPAD_LEFT:
-            case KeyEvent.KEYCODE_DPAD_RIGHT:
-            case KeyEvent.KEYCODE_DPAD_UP:
-            case KeyEvent.KEYCODE_DPAD_DOWN:
-                isArrowKey = true;
-                break;
-        }
-
-        if (KeyEvent.KEYCODE_TAB == keyCode) {
-            if (down) {
-                onEditorAction(EditorInfo.IME_ACTION_NEXT);
-            }
-            return true;
-        }
-        Spannable text = (Spannable) getText();
-        int oldStart = Selection.getSelectionStart(text);
-        int oldEnd = Selection.getSelectionEnd(text);
-        // Normally the delete key's dom events are sent via onTextChanged.
-        // However, if the cursor is at the beginning of the field, which
-        // includes the case where it has zero length, then the text is not
-        // changed, so send the events immediately.
-        if (KeyEvent.KEYCODE_DEL == keyCode) {
-            if (oldStart == 0 && oldEnd == 0) {
-                sendDomEvent(event);
-                return true;
-            }
-            if (down) {
-                mGotDelete = true;
-                mDelSelStart = oldStart;
-                mDelSelEnd = oldEnd;
-            }
-        }
-
-        if (mSingle && (KeyEvent.KEYCODE_ENTER == keyCode
-                    || KeyEvent.KEYCODE_NUMPAD_ENTER == keyCode)) {
-            if (isPopupShowing()) {
-                return super.dispatchKeyEvent(event);
-            }
-            if (!down) {
-                // Hide the keyboard, since the user has just submitted this
-                // form.  The submission happens thanks to the two calls
-                // to sendDomEvent.
-                InputMethodManager.getInstance(mContext)
-                        .hideSoftInputFromWindow(getWindowToken(), 0);
-                sendDomEvent(new KeyEvent(KeyEvent.ACTION_DOWN, keyCode));
-                sendDomEvent(event);
-            }
-            return super.dispatchKeyEvent(event);
-        } else if (KeyEvent.KEYCODE_DPAD_CENTER == keyCode) {
-            // Note that this handles center key and trackball.
-            if (isPopupShowing()) {
-                return super.dispatchKeyEvent(event);
-            }
-            // Center key should be passed to a potential onClick
-            if (!down) {
-                mWebView.centerKeyPressOnTextField();
-            }
-            // Pass to super to handle longpress.
-            return super.dispatchKeyEvent(event);
-        }
-
-        // Ensure there is a layout so arrow keys are handled properly.
-        if (getLayout() == null) {
-            measure(mWidthSpec, mHeightSpec);
-        }
-
-        int oldLength = text.length();
-        boolean maxedOut = mMaxLength != -1 && oldLength == mMaxLength;
-        // If we are at max length, and there is a selection rather than a
-        // cursor, we need to store the text to compare later, since the key
-        // may have changed the string.
-        String oldText;
-        if (maxedOut && oldEnd != oldStart) {
-            oldText = text.toString();
-        } else {
-            oldText = "";
-        }
-        if (super.dispatchKeyEvent(event)) {
-            // If the WebTextView handled the key it was either an alphanumeric
-            // key, a delete, or a movement within the text. All of those are
-            // ok to pass to javascript.
-
-            // UNLESS there is a max length determined by the html.  In that
-            // case, if the string was already at the max length, an
-            // alphanumeric key will be erased by the LengthFilter,
-            // so do not pass down to javascript, and instead
-            // return true.  If it is an arrow key or a delete key, we can go
-            // ahead and pass it down.
-            if (KeyEvent.KEYCODE_ENTER == keyCode
-                        || KeyEvent.KEYCODE_NUMPAD_ENTER == keyCode) {
-                // For multi-line text boxes, newlines will
-                // trigger onTextChanged for key down (which will send both
-                // key up and key down) but not key up.
-                mGotEnterDown = true;
-            }
-            if (maxedOut && !isArrowKey && keyCode != KeyEvent.KEYCODE_DEL) {
-                if (oldEnd == oldStart) {
-                    // Return true so the key gets dropped.
-                    return true;
-                } else if (!oldText.equals(getText().toString())) {
-                    // FIXME: This makes the text work properly, but it
-                    // does not pass down the key event, so it may not
-                    // work for a textfield that has the type of
-                    // behavior of GoogleSuggest.  That said, it is
-                    // unlikely that a site would combine the two in
-                    // one textfield.
-                    Spannable span = (Spannable) getText();
-                    int newStart = Selection.getSelectionStart(span);
-                    int newEnd = Selection.getSelectionEnd(span);
-                    mWebView.replaceTextfieldText(0, oldLength, span.toString(),
-                            newStart, newEnd);
-                    return true;
-                }
-            }
-            /* FIXME:
-             * In theory, we would like to send the events for the arrow keys.
-             * However, the TextView can arbitrarily change the selection (i.e.
-             * long press followed by using the trackball).  Therefore, we keep
-             * in sync with the TextView via onSelectionChanged.  If we also
-             * send the DOM event, we lose the correct selection.
-            if (isArrowKey) {
-                // Arrow key does not change the text, but we still want to send
-                // the DOM events.
-                sendDomEvent(event);
-            }
-             */
-            return true;
-        }
-        // Ignore the key up event for newlines. This prevents
-        // multiple newlines in the native textarea.
-        if (mGotEnterDown && !down) {
-            return true;
-        }
-        // if it is a navigation key, pass it to WebView
-        if (isArrowKey) {
-            // WebView check the trackballtime in onKeyDown to avoid calling
-            // native from both trackball and key handling. As this is called
-            // from WebTextView, we always want WebView to check with native.
-            // Reset trackballtime to ensure it.
-            mWebView.resetTrackballTime();
-            return down ? mWebView.onKeyDown(keyCode, event) : mWebView
-                    .onKeyUp(keyCode, event);
-        }
-        return false;
-    }
-
-    void ensureLayout() {
-        if (getLayout() == null) {
-            // Ensure we have a Layout
-            measure(mWidthSpec, mHeightSpec);
-            LayoutParams params = (LayoutParams) getLayoutParams();
-            if (params != null) {
-                layout(params.x, params.y, params.x + params.width,
-                        params.y + params.height);
-            }
-        }
-    }
-
-    /* package */ ResultReceiver getResultReceiver() { return mReceiver; }
-
-    /**
-     *  Determine whether this WebTextView currently represents the node
-     *  represented by ptr.
-     *  @param  ptr Pointer to a node to compare to.
-     *  @return boolean Whether this WebTextView already represents the node
-     *          pointed to by ptr.
-     */
-    /* package */ boolean isSameTextField(int ptr) {
-        return ptr == mNodePointer;
-    }
-
-    /**
-     * Ensure that the underlying text field/area is lined up with the WebTextView.
-     */
-    private void lineUpScroll() {
-        Layout layout = getLayout();
-        if (mWebView != null && layout != null) {
-            if (mSingle) {
-                // textfields only need to be lined up horizontally.
-                float maxScrollX = layout.getLineRight(0) - getWidth();
-                if (DebugFlags.WEB_TEXT_VIEW) {
-                    Log.v(LOGTAG, "onTouchEvent x=" + mScrollX + " y="
-                            + mScrollY + " maxX=" + maxScrollX);
-                }
-                mWebView.scrollFocusedTextInputX(maxScrollX > 0 ?
-                        mScrollX / maxScrollX : 0);
-            } else {
-                // textareas only need to be lined up vertically.
-                mWebView.scrollFocusedTextInputY(mScrollY);
-            }
-        }
-    }
-
-    @Override
-    protected void makeNewLayout(int w, int hintWidth, Metrics boring,
-            Metrics hintBoring, int ellipsisWidth, boolean bringIntoView) {
-        // Necessary to get a Layout to work with, and to do the other work that
-        // makeNewLayout does.
-        super.makeNewLayout(w, hintWidth, boring, hintBoring, ellipsisWidth,
-                bringIntoView);
-        lineUpScroll();
-    }
-
-    /**
-     * Custom layout which figures out its line spacing.  If -1 is passed in for
-     * the height, it will use the ascent and descent from the paint to
-     * determine the line spacing.  Otherwise it will use the spacing provided.
-     */
-    private static class WebTextViewLayout extends DynamicLayout {
-        private float mLineHeight;
-        private float mDifference;
-        public WebTextViewLayout(CharSequence base, CharSequence display,
-                TextPaint paint,
-                int width, Alignment align,
-                float spacingMult, float spacingAdd,
-                boolean includepad,
-                TextUtils.TruncateAt ellipsize, int ellipsizedWidth,
-                float lineHeight) {
-            super(base, display, paint, width, align, spacingMult, spacingAdd,
-                    includepad, ellipsize, ellipsizedWidth);
-            float paintLineHeight = paint.descent() - paint.ascent();
-            if (lineHeight == -1f) {
-                mLineHeight = paintLineHeight;
-                mDifference = 0f;
-            } else {
-                mLineHeight = lineHeight;
-                // Through trial and error, I found this calculation to improve
-                // the accuracy of line placement.
-                mDifference = (lineHeight - paintLineHeight) / 2;
-            }
-        }
-
-        @Override
-        public int getLineTop(int line) {
-            return Math.round(mLineHeight * line - mDifference);
-        }
-    }
-
-    @Override public InputConnection onCreateInputConnection(
-            EditorInfo outAttrs) {
-        InputConnection connection = super.onCreateInputConnection(outAttrs);
-        if (mWebView != null) {
-            // Use the name of the textfield + the url.  Use backslash as an
-            // arbitrary separator.
-            outAttrs.fieldName = mWebView.nativeFocusCandidateName() + "\\"
-                    + mWebView.getUrl();
-        }
-        return connection;
-    }
-
-    @Override
-    public void onEditorAction(int actionCode) {
-        switch (actionCode) {
-        case EditorInfo.IME_ACTION_NEXT:
-            if (mWebView.nativeMoveCursorToNextTextInput()) {
-                // Preemptively rebuild the WebTextView, so that the action will
-                // be set properly.
-                mWebView.rebuildWebTextView();
-                setDefaultSelection();
-                mWebView.invalidate();
-            }
-            break;
-        case EditorInfo.IME_ACTION_DONE:
-            super.onEditorAction(actionCode);
-            break;
-        case EditorInfo.IME_ACTION_GO:
-        case EditorInfo.IME_ACTION_SEARCH:
-            // Send an enter and hide the soft keyboard
-            InputMethodManager.getInstance(mContext)
-                    .hideSoftInputFromWindow(getWindowToken(), 0);
-            sendDomEvent(new KeyEvent(KeyEvent.ACTION_DOWN,
-                    KeyEvent.KEYCODE_ENTER));
-            sendDomEvent(new KeyEvent(KeyEvent.ACTION_UP,
-                    KeyEvent.KEYCODE_ENTER));
-
-        default:
-            break;
-        }
-    }
-
-    @Override
-    protected void onFocusChanged(boolean focused, int direction,
-            Rect previouslyFocusedRect) {
-        mFromFocusChange = true;
-        super.onFocusChanged(focused, direction, previouslyFocusedRect);
-        if (focused) {
-            mWebView.setActive(true);
-        } else if (!mInsideRemove) {
-            mWebView.setActive(false);
-        }
-        mFromFocusChange = false;
-    }
-
-    // AdapterView.OnItemClickListener implementation
-
-    @Override
-    public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
-        if (id == 0 && position == 0) {
-            // Blank out the text box while we wait for WebCore to fill the form.
-            replaceText("");
-            WebSettings settings = mWebView.getSettings();
-            if (mAutoFillProfileIsSet) {
-                // Call a webview method to tell WebCore to autofill the form.
-                mWebView.autoFillForm(mQueryId);
-            } else {
-                // There is no autofill profile setup yet and the user has
-                // elected to try and set one up. Call through to the
-                // embedder to action that.
-                mWebView.getWebChromeClient().setupAutoFill(
-                        mHandler.obtainMessage(AUTOFILL_FORM));
-            }
-        }
-    }
-
-    @Override
-    protected void onScrollChanged(int l, int t, int oldl, int oldt) {
-        super.onScrollChanged(l, t, oldl, oldt);
-        lineUpScroll();
-    }
-
-    @Override
-    protected void onSelectionChanged(int selStart, int selEnd) {
-        if (!mFromWebKit && !mFromFocusChange && !mFromSetInputType
-                && mWebView != null && !mInSetTextAndKeepSelection) {
-            if (DebugFlags.WEB_TEXT_VIEW) {
-                Log.v(LOGTAG, "onSelectionChanged selStart=" + selStart
-                        + " selEnd=" + selEnd);
-            }
-            mWebView.setSelection(selStart, selEnd);
-            lineUpScroll();
-        }
-    }
-
-    @Override
-    protected void onTextChanged(CharSequence s,int start,int before,int count){
-        super.onTextChanged(s, start, before, count);
-        String postChange = s.toString();
-        // Prevent calls to setText from invoking onTextChanged (since this will
-        // mean we are on a different textfield).  Also prevent the change when
-        // going from a textfield with a string of text to one with a smaller
-        // limit on text length from registering the onTextChanged event.
-        if (mPreChange == null || mPreChange.equals(postChange) ||
-                (mMaxLength > -1 && mPreChange.length() > mMaxLength &&
-                mPreChange.substring(0, mMaxLength).equals(postChange))) {
-            return;
-        }
-        if (0 == count) {
-            if (before > 0) {
-                // For this and all changes to the text, update our cache
-                updateCachedTextfield();
-                if (mGotDelete) {
-                    mGotDelete = false;
-                    int oldEnd = start + before;
-                    if (mDelSelEnd == oldEnd
-                            && (mDelSelStart == start
-                            || (mDelSelStart == oldEnd && before == 1))) {
-                        // If the selection is set up properly before the
-                        // delete, send the DOM events.
-                        sendDomEvent(new KeyEvent(KeyEvent.ACTION_DOWN,
-                                KeyEvent.KEYCODE_DEL));
-                        sendDomEvent(new KeyEvent(KeyEvent.ACTION_UP,
-                                KeyEvent.KEYCODE_DEL));
-                        return;
-                    }
-                }
-                // This was simply a delete or a cut, so just delete the
-                // selection.
-                mWebView.deleteSelection(start, start + before);
-            }
-            mGotDelete = false;
-            // before should never be negative, so whether it was a cut
-            // (handled above), or before is 0, in which case nothing has
-            // changed, we should return.
-            return;
-        }
-        // Ensure that this flag gets cleared, since with autocorrect on, a
-        // delete key press may have a more complex result than deleting one
-        // character or the existing selection, so it will not get cleared
-        // above.
-        mGotDelete = false;
-        // Prefer sending javascript events, so when adding one character,
-        // don't replace the unchanged text.
-        if (count > 1 && before == count - 1) {
-            String replaceButOne =  mPreChange.subSequence(start,
-                    start + before).toString();
-            String replacedString = s.subSequence(start,
-                    start + before).toString();
-            if (replaceButOne.equals(replacedString)) {
-                // we're just adding one character
-                start += before;
-                before = 0;
-                count = 1;
-            }
-        }
-        mPreChange = postChange;
-        // Find the last character being replaced.  If it can be represented by
-        // events, we will pass them to native so we can see javascript events.
-        // Otherwise, replace the text being changed in the textfield.
-        KeyEvent[] events = null;
-        if (count == 1) {
-            TextUtils.getChars(s, start + count - 1, start + count, mCharacter, 0);
-            KeyCharacterMap kmap = KeyCharacterMap.load(KeyCharacterMap.VIRTUAL_KEYBOARD);
-            events = kmap.getEvents(mCharacter);
-        }
-        boolean useKeyEvents = (events != null);
-        if (useKeyEvents) {
-            // This corrects the selection which may have been affected by the
-            // trackball or auto-correct.
-            if (DebugFlags.WEB_TEXT_VIEW) {
-                Log.v(LOGTAG, "onTextChanged start=" + start
-                        + " start + before=" + (start + before));
-            }
-            if (!mInSetTextAndKeepSelection) {
-                mWebView.setSelection(start, start + before);
-            }
-            int length = events.length;
-            for (int i = 0; i < length; i++) {
-                // We never send modifier keys to native code so don't send them
-                // here either.
-                if (!KeyEvent.isModifierKey(events[i].getKeyCode())) {
-                    sendDomEvent(events[i]);
-                }
-            }
-        } else {
-            String replace = s.subSequence(start,
-                    start + count).toString();
-            mWebView.replaceTextfieldText(start, start + before, replace,
-                    start + count,
-                    start + count);
-        }
-        updateCachedTextfield();
-    }
-
-    @Override
-    public boolean onTouchEvent(MotionEvent event) {
-        switch (event.getAction()) {
-        case MotionEvent.ACTION_DOWN:
-            super.onTouchEvent(event);
-            // This event may be the start of a drag, so store it to pass to the
-            // WebView if it is.
-            mDragStartX = event.getX();
-            mDragStartY = event.getY();
-            mDragStartTime = event.getEventTime();
-            mDragSent = false;
-            mScrolled = false;
-            mGotTouchDown = true;
-            mHasPerformedLongClick = false;
-            break;
-        case MotionEvent.ACTION_MOVE:
-            if (mHasPerformedLongClick) {
-                mGotTouchDown = false;
-                return false;
-            }
-            int slop = ViewConfiguration.get(mContext).getScaledTouchSlop();
-            Spannable buffer = getText();
-            int initialScrollX = Touch.getInitialScrollX(this, buffer);
-            int initialScrollY = Touch.getInitialScrollY(this, buffer);
-            super.onTouchEvent(event);
-            int dx = Math.abs(mScrollX - initialScrollX);
-            int dy = Math.abs(mScrollY - initialScrollY);
-            // Use a smaller slop when checking to see if we've moved far enough
-            // to scroll the text, because experimentally, slop has shown to be
-            // to big for the case of a small textfield.
-            int smallerSlop = slop/2;
-            if (dx > smallerSlop || dy > smallerSlop) {
-                // Scrolling is handled in onScrollChanged.
-                mScrolled = true;
-                cancelLongPress();
-                return true;
-            }
-            if (Math.abs((int) event.getX() - mDragStartX) < slop
-                    && Math.abs((int) event.getY() - mDragStartY) < slop) {
-                // If the user has not scrolled further than slop, we should not
-                // send the drag.  Instead, do nothing, and when the user lifts
-                // their finger, we will change the selection.
-                return true;
-            }
-            if (mWebView != null) {
-                // Only want to set the initial state once.
-                if (!mDragSent) {
-                    mWebView.initiateTextFieldDrag(mDragStartX, mDragStartY,
-                            mDragStartTime);
-                    mDragSent = true;
-                }
-                boolean scrolled = mWebView.textFieldDrag(event);
-                if (scrolled) {
-                    mScrolled = true;
-                    cancelLongPress();
-                    return true;
-                }
-            }
-            return false;
-        case MotionEvent.ACTION_UP:
-        case MotionEvent.ACTION_CANCEL:
-            super.onTouchEvent(event);
-            if (mHasPerformedLongClick) {
-                mGotTouchDown = false;
-                return false;
-            }
-            if (!mScrolled) {
-                // If the page scrolled, or the TextView scrolled, we do not
-                // want to change the selection
-                cancelLongPress();
-                if (mGotTouchDown && mWebView != null) {
-                    mWebView.touchUpOnTextField(event);
-                }
-            }
-            // Necessary for the WebView to reset its state
-            if (mWebView != null && mDragSent) {
-                mWebView.onTouchEvent(event);
-            }
-            mGotTouchDown = false;
-            break;
-        default:
-            break;
-        }
-        return true;
-    }
-
-    @Override
-    public boolean onTrackballEvent(MotionEvent event) {
-        if (isPopupShowing()) {
-            return super.onTrackballEvent(event);
-        }
-        if (event.getAction() != MotionEvent.ACTION_MOVE) {
-            return false;
-        }
-        Spannable text = getText();
-        MovementMethod move = getMovementMethod();
-        if (move != null && getLayout() != null &&
-            move.onTrackballEvent(this, text, event)) {
-            // Selection is changed in onSelectionChanged
-            return true;
-        }
-        return false;
-    }
-
-    @Override
-    public boolean performLongClick() {
-        mHasPerformedLongClick = true;
-        return super.performLongClick();
-    }
-
-    /**
-     * Remove this WebTextView from its host WebView, and return
-     * focus to the host.
-     */
-    /* package */ void remove() {
-        // hide the soft keyboard when the edit text is out of focus
-        InputMethodManager imm = InputMethodManager.getInstance(mContext);
-        if (imm.isActive(this)) {
-            imm.hideSoftInputFromWindow(getWindowToken(), 0);
-        }
-        mInsideRemove = true;
-        boolean isFocused = hasFocus();
-        mWebView.removeView(this);
-        if (isFocused) {
-            mWebView.requestFocus();
-        }
-        mInsideRemove = false;
-        mHandler.removeCallbacksAndMessages(null);
-    }
-
-    @Override
-    public boolean requestRectangleOnScreen(Rect rectangle, boolean immediate) {
-        // Do nothing, since webkit will put the textfield on screen.
-        return true;
-    }
-
-    /**
-     *  Send the DOM events for the specified event.
-     *  @param event    KeyEvent to be translated into a DOM event.
-     */
-    private void sendDomEvent(KeyEvent event) {
-        mWebView.passToJavaScript(getText().toString(), event);
-    }
-
-    /**
-     *  Always use this instead of setAdapter, as this has features specific to
-     *  the WebTextView.
-     */
-    public void setAdapterCustom(AutoCompleteAdapter adapter) {
-        if (adapter != null) {
-            setInputType(getInputType()
-                    | InputType.TYPE_TEXT_FLAG_AUTO_COMPLETE);
-            adapter.setTextView(this);
-            if (mAutoFillable) {
-                setOnItemClickListener(this);
-            } else {
-                setOnItemClickListener(null);
-            }
-            showDropDown();
-        } else {
-            dismissDropDown();
-        }
-        super.setAdapter(adapter);
-    }
-
-    /**
-     *  This is a special version of ArrayAdapter which changes its text size
-     *  to match the text size of its host TextView.
-     */
-    public static class AutoCompleteAdapter extends ArrayAdapter<String> {
-        private TextView mTextView;
-
-        public AutoCompleteAdapter(Context context, ArrayList<String> entries) {
-            super(context, com.android.internal.R.layout
-                    .web_text_view_dropdown, entries);
-        }
-
-        /**
-         * {@inheritDoc}
-         */
-        @Override
-        public View getView(int position, View convertView, ViewGroup parent) {
-            TextView tv =
-                    (TextView) super.getView(position, convertView, parent);
-            if (tv != null && mTextView != null) {
-                tv.setTextSize(TypedValue.COMPLEX_UNIT_PX, mTextView.getTextSize());
-            }
-            return tv;
-        }
-
-        /**
-         * Set the TextView so we can match its text size.
-         */
-        private void setTextView(TextView tv) {
-            mTextView = tv;
-        }
-    }
-
-    /**
-     * Sets the selection when the user clicks on a textfield or textarea with
-     * the trackball or center key, or starts typing into it without clicking on
-     * it.
-     */
-    /* package */ void setDefaultSelection() {
-        Spannable text = (Spannable) getText();
-        int selection = mSingle ? text.length() : 0;
-        if (Selection.getSelectionStart(text) == selection
-                && Selection.getSelectionEnd(text) == selection) {
-            // The selection of the UI copy is set correctly, but the
-            // WebTextView still needs to inform the webkit thread to set the
-            // selection.  Normally that is done in onSelectionChanged, but
-            // onSelectionChanged will not be called because the UI copy is not
-            // changing.  (This can happen when the WebTextView takes focus.
-            // That onSelectionChanged was blocked because the selection set
-            // when focusing is not necessarily the desirable selection for
-            // WebTextView.)
-            if (mWebView != null) {
-                mWebView.setSelection(selection, selection);
-            }
-        } else {
-            Selection.setSelection(text, selection, selection);
-        }
-        if (mWebView != null) mWebView.incrementTextGeneration();
-    }
-
-    @Override
-    public void setInputType(int type) {
-        mFromSetInputType = true;
-        super.setInputType(type);
-        mFromSetInputType = false;
-    }
-
-    private void setMaxLength(int maxLength) {
-        mMaxLength = maxLength;
-        if (-1 == maxLength) {
-            setFilters(NO_FILTERS);
-        } else {
-            setFilters(new InputFilter[] {
-                new InputFilter.LengthFilter(maxLength) });
-        }
-    }
-
-    /**
-     *  Set the pointer for this node so it can be determined which node this
-     *  WebTextView represents.
-     *  @param  ptr Integer representing the pointer to the node which this
-     *          WebTextView represents.
-     */
-    /* package */ void setNodePointer(int ptr) {
-        if (ptr != mNodePointer) {
-            mNodePointer = ptr;
-            setAdapterCustom(null);
-        }
-    }
-
-    /**
-     * Determine the position and size of WebTextView, and add it to the
-     * WebView's view heirarchy.  All parameters are presumed to be in
-     * view coordinates.  Also requests Focus and sets the cursor to not
-     * request to be in view.
-     * @param x         x-position of the textfield.
-     * @param y         y-position of the textfield.
-     * @param width     width of the textfield.
-     * @param height    height of the textfield.
-     */
-    /* package */ void setRect(int x, int y, int width, int height) {
-        LayoutParams lp = (LayoutParams) getLayoutParams();
-        x -= mRingInset;
-        y -= mRingInset;
-        width += 2 * mRingInset;
-        height += 2 * mRingInset;
-        boolean needsUpdate = false;
-        if (null == lp) {
-            lp = new LayoutParams(width, height, x, y);
-        } else {
-            if ((lp.x != x) || (lp.y != y) || (lp.width != width)
-                    || (lp.height != height)) {
-                needsUpdate = true;
-                lp.x = x;
-                lp.y = y;
-                lp.width = width;
-                lp.height = height;
-            }
-        }
-        if (getParent() == null) {
-            // Insert the view so that it's drawn first (at index 0)
-            mWebView.addView(this, 0, lp);
-        } else if (needsUpdate) {
-            setLayoutParams(lp);
-        }
-        // Set up a measure spec so a layout can always be recreated.
-        mWidthSpec = MeasureSpec.makeMeasureSpec(width, MeasureSpec.EXACTLY);
-        mHeightSpec = MeasureSpec.makeMeasureSpec(height, MeasureSpec.EXACTLY);
-    }
-
-    /**
-     * Set the selection, and disable our onSelectionChanged action.
-     */
-    /* package */ void setSelectionFromWebKit(int start, int end) {
-        if (start < 0 || end < 0) return;
-        Spannable text = (Spannable) getText();
-        int length = text.length();
-        if (start > length || end > length) return;
-        mFromWebKit = true;
-        Selection.setSelection(text, start, end);
-        mFromWebKit = false;
-    }
-
-    /**
-     * Update the text size according to the size of the focus candidate's text
-     * size in mWebView.  Should only be called from mWebView.
-     */
-    /* package */ void updateTextSize() {
-        Assert.assertNotNull("updateTextSize should only be called from "
-                + "mWebView, so mWebView should never be null!", mWebView);
-        // Note that this is approximately WebView.contentToViewDimension,
-        // without being rounded.
-        float size = mWebView.nativeFocusCandidateTextSize()
-                * mWebView.getScale();
-        setTextSize(TypedValue.COMPLEX_UNIT_PX, size);
-    }
-
-    /**
-     * Set the text to the new string, but use the old selection, making sure
-     * to keep it within the new string.
-     * @param   text    The new text to place in the textfield.
-     */
-    /* package */ void setTextAndKeepSelection(String text) {
-        Editable edit = getText();
-        mPreChange = text;
-        if (edit.toString().equals(text)) {
-            return;
-        }
-        int selStart = Selection.getSelectionStart(edit);
-        int selEnd = Selection.getSelectionEnd(edit);
-        mInSetTextAndKeepSelection = true;
-        edit.replace(0, edit.length(), text);
-        int newLength = edit.length();
-        if (selStart > newLength) selStart = newLength;
-        if (selEnd > newLength) selEnd = newLength;
-        Selection.setSelection(edit, selStart, selEnd);
-        mInSetTextAndKeepSelection = false;
-        InputMethodManager imm = InputMethodManager.peekInstance();
-        if (imm != null && imm.isActive(this)) {
-            // Since the text has changed, do not allow the IME to replace the
-            // existing text as though it were a completion.
-            imm.restartInput(this);
-        }
-        updateCachedTextfield();
-    }
-
-    /**
-     * Called by WebView.rebuildWebTextView().  Based on the type of the <input>
-     * element, set up the WebTextView, its InputType, and IME Options properly.
-     * @param type int corresponding to enum "Type" defined in CachedInput.h.
-     *              Does not correspond to HTMLInputElement::InputType so this
-     *              is unaffected if that changes, and also because that has no
-     *              type corresponding to textarea (which is its own tag).
-     */
-    /* package */ void setType(int type) {
-        if (mWebView == null) return;
-        boolean single = true;
-        int maxLength = -1;
-        int inputType = InputType.TYPE_CLASS_TEXT
-                | InputType.TYPE_TEXT_VARIATION_WEB_EDIT_TEXT;
-        int imeOptions = EditorInfo.IME_FLAG_NO_EXTRACT_UI
-                | EditorInfo.IME_FLAG_NO_FULLSCREEN;
-        if (!mWebView.nativeFocusCandidateIsSpellcheck()) {
-            inputType |= InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS;
-        }
-        if (TEXT_AREA != type
-                && mWebView.nativeFocusCandidateHasNextTextfield()) {
-            imeOptions |= EditorInfo.IME_FLAG_NAVIGATE_NEXT;
-        }
-        switch (type) {
-            case NORMAL_TEXT_FIELD:
-                imeOptions |= EditorInfo.IME_ACTION_GO;
-                break;
-            case TEXT_AREA:
-                single = false;
-                inputType |= InputType.TYPE_TEXT_FLAG_MULTI_LINE
-                        | InputType.TYPE_TEXT_FLAG_CAP_SENTENCES
-                        | InputType.TYPE_TEXT_FLAG_AUTO_CORRECT;
-                imeOptions |= EditorInfo.IME_ACTION_NONE;
-                break;
-            case PASSWORD:
-                inputType |= EditorInfo.TYPE_TEXT_VARIATION_WEB_PASSWORD;
-                imeOptions |= EditorInfo.IME_ACTION_GO;
-                break;
-            case SEARCH:
-                imeOptions |= EditorInfo.IME_ACTION_SEARCH;
-                break;
-            case EMAIL:
-                // inputType needs to be overwritten because of the different text variation.
-                inputType = InputType.TYPE_CLASS_TEXT
-                        | InputType.TYPE_TEXT_VARIATION_WEB_EMAIL_ADDRESS;
-                imeOptions |= EditorInfo.IME_ACTION_GO;
-                break;
-            case NUMBER:
-                // inputType needs to be overwritten because of the different class.
-                inputType = InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_VARIATION_NORMAL
-                        | InputType.TYPE_NUMBER_FLAG_SIGNED | InputType.TYPE_NUMBER_FLAG_DECIMAL;
-                // Number and telephone do not have both a Tab key and an
-                // action, so set the action to NEXT
-                imeOptions |= EditorInfo.IME_ACTION_NEXT;
-                break;
-            case TELEPHONE:
-                // inputType needs to be overwritten because of the different class.
-                inputType = InputType.TYPE_CLASS_PHONE;
-                imeOptions |= EditorInfo.IME_ACTION_NEXT;
-                break;
-            case URL:
-                // TYPE_TEXT_VARIATION_URI prevents Tab key from showing, so
-                // exclude it for now.
-                imeOptions |= EditorInfo.IME_ACTION_GO;
-                break;
-            default:
-                imeOptions |= EditorInfo.IME_ACTION_GO;
-                break;
-        }
-        setHint(null);
-        setThreshold(1);
-        boolean autoComplete = false;
-        if (single) {
-            mWebView.requestLabel(mWebView.nativeFocusCandidateFramePointer(),
-                    mNodePointer);
-            maxLength = mWebView.nativeFocusCandidateMaxLength();
-            autoComplete = mWebView.nativeFocusCandidateIsAutoComplete();
-            if (type != PASSWORD && (mAutoFillable || autoComplete)) {
-                String name = mWebView.nativeFocusCandidateName();
-                if (name != null && name.length() > 0) {
-                    mWebView.requestFormData(name, mNodePointer, mAutoFillable,
-                            autoComplete);
-                }
-            }
-        }
-        mSingle = single;
-        setMaxLength(maxLength);
-        setHorizontallyScrolling(single);
-        setInputType(inputType);
-        clearComposingText();
-        setImeOptions(imeOptions);
-        setVisibility(VISIBLE);
-        if (!autoComplete) {
-            setAdapterCustom(null);
-        }
-    }
-
-    /**
-     *  Update the cache to reflect the current text.
-     */
-    /* package */ void updateCachedTextfield() {
-        mWebView.updateCachedTextfield(getText().toString());
-    }
-
-    /* package */ void setAutoFillProfileIsSet(boolean autoFillProfileIsSet) {
-        mAutoFillProfileIsSet = autoFillProfileIsSet;
-    }
+    static final int FORM_NOT_AUTOFILLABLE = -1;
 
     static String urlForAutoCompleteData(String urlString) {
         // Remove any fragment or query string.
@@ -1182,10 +50,4 @@
         return url != null ? url.getProtocol() + "://" + url.getHost() + url.getPath() : null;
     }
 
-    public void setGravityForRtl(boolean rtl) {
-        int gravity = rtl ? Gravity.RIGHT : Gravity.LEFT;
-        gravity |= mSingle ? Gravity.CENTER_VERTICAL : Gravity.TOP;
-        setGravity(gravity);
-    }
-
 }
diff --git a/core/java/android/webkit/WebView.java b/core/java/android/webkit/WebView.java
index a850379..a561577 100644
--- a/core/java/android/webkit/WebView.java
+++ b/core/java/android/webkit/WebView.java
@@ -16,126 +16,35 @@
 
 package android.webkit;
 
-import android.animation.ObjectAnimator;
 import android.annotation.Widget;
-import android.app.ActivityManager;
-import android.app.AlertDialog;
-import android.content.BroadcastReceiver;
-import android.content.ClipData;
-import android.content.ClipboardManager;
-import android.content.ComponentCallbacks2;
 import android.content.Context;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnCancelListener;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.content.pm.PackageManager;
 import android.content.res.Configuration;
-import android.database.DataSetObserver;
 import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapShader;
 import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.ColorFilter;
-import android.graphics.DrawFilter;
-import android.graphics.Paint;
-import android.graphics.PaintFlagsDrawFilter;
 import android.graphics.Picture;
-import android.graphics.Point;
 import android.graphics.Rect;
-import android.graphics.RectF;
-import android.graphics.Region;
-import android.graphics.RegionIterator;
-import android.graphics.Shader;
 import android.graphics.drawable.Drawable;
-import android.net.Proxy;
-import android.net.ProxyProperties;
-import android.net.Uri;
 import android.net.http.SslCertificate;
-import android.os.AsyncTask;
 import android.os.Bundle;
-import android.os.Handler;
 import android.os.Looper;
 import android.os.Message;
 import android.os.StrictMode;
-import android.os.SystemClock;
-import android.provider.Settings;
-import android.security.KeyChain;
-import android.speech.tts.TextToSpeech;
-import android.text.Editable;
-import android.text.InputType;
-import android.text.Selection;
-import android.text.TextUtils;
 import android.util.AttributeSet;
-import android.util.DisplayMetrics;
-import android.util.EventLog;
 import android.util.Log;
-import android.view.Display;
-import android.view.Gravity;
-import android.view.HapticFeedbackConstants;
-import android.view.HardwareCanvas;
-import android.view.InputDevice;
-import android.view.KeyCharacterMap;
 import android.view.KeyEvent;
-import android.view.LayoutInflater;
 import android.view.MotionEvent;
-import android.view.ScaleGestureDetector;
-import android.view.SoundEffectConstants;
-import android.view.VelocityTracker;
 import android.view.View;
-import android.view.ViewConfiguration;
 import android.view.ViewGroup;
-import android.view.ViewParent;
+import android.view.ViewGroup.LayoutParams;
 import android.view.ViewTreeObserver;
-import android.view.WindowManager;
 import android.view.accessibility.AccessibilityEvent;
-import android.view.accessibility.AccessibilityManager;
 import android.view.accessibility.AccessibilityNodeInfo;
-import android.view.inputmethod.BaseInputConnection;
 import android.view.inputmethod.EditorInfo;
 import android.view.inputmethod.InputConnection;
-import android.view.inputmethod.InputMethodManager;
-import android.webkit.HTML5VideoInline;
-import android.webkit.WebTextView.AutoCompleteAdapter;
-import android.webkit.WebViewCore.DrawData;
-import android.webkit.WebViewCore.EventHub;
-import android.webkit.WebViewCore.TextFieldInitData;
-import android.webkit.WebViewCore.TouchEventData;
-import android.webkit.WebViewCore.TouchHighlightData;
-import android.webkit.WebViewCore.WebKitHitTest;
 import android.widget.AbsoluteLayout;
-import android.widget.Adapter;
-import android.widget.AdapterView;
-import android.widget.AdapterView.OnItemClickListener;
-import android.widget.ArrayAdapter;
-import android.widget.CheckedTextView;
-import android.widget.LinearLayout;
-import android.widget.ListView;
-import android.widget.OverScroller;
-import android.widget.PopupWindow;
-import android.widget.TextView;
-import android.widget.Toast;
-
-import junit.framework.Assert;
 
 import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.net.URLDecoder;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.HashSet;
-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;
 
 /**
  * <p>A View that displays web pages. This class is the basis upon which you
@@ -345,452 +254,25 @@
  *
  *
  */
+/*
+ * Implementation notes.
+ * The WebView is a thin API class that delegates its public API to a backend WebViewProvider
+ * class instance. WebView extends {@link AbsoluteLayout} for backward compatibility reasons.
+ * Methods are delegated to the provider implementation: all public API methods introduced in this
+ * file are fully delegated, whereas public and protected methods from the View base classes are
+ * only delegated where a specific need exists for them to do so.
+ */
 @Widget
 public class WebView extends AbsoluteLayout
         implements ViewTreeObserver.OnGlobalFocusChangeListener,
         ViewGroup.OnHierarchyChangeListener {
 
-    private class InnerGlobalLayoutListener implements ViewTreeObserver.OnGlobalLayoutListener {
-        @Override
-        public void onGlobalLayout() {
-            if (isShown()) {
-                setGLRectViewport();
-            }
-        }
-    }
+    // Default Provider factory class name.
+    private static final String DEFAULT_WEB_VIEW_FACTORY = "android.webkit.WebViewClassic$Factory";
 
-    private class InnerScrollChangedListener implements ViewTreeObserver.OnScrollChangedListener {
-        @Override
-        public void onScrollChanged() {
-            if (isShown()) {
-                setGLRectViewport();
-            }
-        }
-    }
-
-    /**
-     * InputConnection used for ContentEditable. This captures changes
-     * to the text and sends them either as key strokes or text changes.
-     */
-    private class WebViewInputConnection extends BaseInputConnection {
-        // Used for mapping characters to keys typed.
-        private KeyCharacterMap mKeyCharacterMap;
-        private boolean mIsKeySentByMe;
-        private int mInputType;
-        private int mImeOptions;
-        private String mHint;
-        private int mMaxLength;
-
-        public WebViewInputConnection() {
-            super(WebView.this, true);
-        }
-
-        @Override
-        public boolean sendKeyEvent(KeyEvent event) {
-            // Some IMEs send key events directly using sendKeyEvents.
-            // WebViewInputConnection should treat these as text changes.
-            if (!mIsKeySentByMe) {
-                if (event.getAction() == KeyEvent.ACTION_UP) {
-                    if (event.getKeyCode() == KeyEvent.KEYCODE_DEL) {
-                        return deleteSurroundingText(1, 0);
-                    } else if (event.getKeyCode() == KeyEvent.KEYCODE_FORWARD_DEL) {
-                        return deleteSurroundingText(0, 1);
-                    } else if (event.getUnicodeChar() != 0){
-                        String newComposingText =
-                                Character.toString((char)event.getUnicodeChar());
-                        return commitText(newComposingText, 1);
-                    }
-                } else if (event.getAction() == KeyEvent.ACTION_DOWN &&
-                        (event.getKeyCode() == KeyEvent.KEYCODE_DEL
-                        || event.getKeyCode() == KeyEvent.KEYCODE_FORWARD_DEL
-                        || event.getUnicodeChar() != 0)) {
-                    return true; // only act on action_down
-                }
-            }
-            return super.sendKeyEvent(event);
-        }
-
-        public void setTextAndKeepSelection(CharSequence text) {
-            Editable editable = getEditable();
-            int selectionStart = Selection.getSelectionStart(editable);
-            int selectionEnd = Selection.getSelectionEnd(editable);
-            text = limitReplaceTextByMaxLength(text, editable.length());
-            editable.replace(0, editable.length(), text);
-            restartInput();
-            // Keep the previous selection.
-            selectionStart = Math.min(selectionStart, editable.length());
-            selectionEnd = Math.min(selectionEnd, editable.length());
-            setSelection(selectionStart, selectionEnd);
-        }
-
-        public void replaceSelection(CharSequence text) {
-            Editable editable = getEditable();
-            int selectionStart = Selection.getSelectionStart(editable);
-            int selectionEnd = Selection.getSelectionEnd(editable);
-            text = limitReplaceTextByMaxLength(text, selectionEnd - selectionStart);
-            setNewText(selectionStart, selectionEnd, text);
-            editable.replace(selectionStart, selectionEnd, text);
-            restartInput();
-            // Move caret to the end of the new text
-            int newCaret = selectionStart + text.length();
-            setSelection(newCaret, newCaret);
-        }
-
-        @Override
-        public boolean setComposingText(CharSequence text, int newCursorPosition) {
-            Editable editable = getEditable();
-            int start = getComposingSpanStart(editable);
-            int end = getComposingSpanEnd(editable);
-            if (start < 0 || end < 0) {
-                start = Selection.getSelectionStart(editable);
-                end = Selection.getSelectionEnd(editable);
-            }
-            if (end < start) {
-                int temp = end;
-                end = start;
-                start = temp;
-            }
-            CharSequence limitedText = limitReplaceTextByMaxLength(text, end - start);
-            setNewText(start, end, limitedText);
-            if (limitedText != text) {
-                newCursorPosition -= text.length() - limitedText.length();
-            }
-            super.setComposingText(limitedText, newCursorPosition);
-            if (limitedText != text) {
-                restartInput();
-                int lastCaret = start + limitedText.length();
-                finishComposingText();
-                setSelection(lastCaret, lastCaret);
-            }
-            return true;
-        }
-
-        @Override
-        public boolean commitText(CharSequence text, int newCursorPosition) {
-            setComposingText(text, newCursorPosition);
-            int cursorPosition = Selection.getSelectionEnd(getEditable());
-            setComposingRegion(cursorPosition, cursorPosition);
-            return true;
-        }
-
-        @Override
-        public boolean deleteSurroundingText(int leftLength, int rightLength) {
-            Editable editable = getEditable();
-            int cursorPosition = Selection.getSelectionEnd(editable);
-            int startDelete = Math.max(0, cursorPosition - leftLength);
-            int endDelete = Math.min(editable.length(),
-                    cursorPosition + rightLength);
-            setNewText(startDelete, endDelete, "");
-            return super.deleteSurroundingText(leftLength, rightLength);
-        }
-
-        @Override
-        public boolean performEditorAction(int editorAction) {
-
-            boolean handled = true;
-            switch (editorAction) {
-            case EditorInfo.IME_ACTION_NEXT:
-                WebView.this.requestFocus(FOCUS_FORWARD);
-                break;
-            case EditorInfo.IME_ACTION_PREVIOUS:
-                WebView.this.requestFocus(FOCUS_BACKWARD);
-                break;
-            case EditorInfo.IME_ACTION_DONE:
-                WebView.this.hideSoftKeyboard();
-                break;
-            case EditorInfo.IME_ACTION_GO:
-            case EditorInfo.IME_ACTION_SEARCH:
-                WebView.this.hideSoftKeyboard();
-                String text = getEditable().toString();
-                passToJavaScript(text, new KeyEvent(KeyEvent.ACTION_DOWN,
-                        KeyEvent.KEYCODE_ENTER));
-                passToJavaScript(text, new KeyEvent(KeyEvent.ACTION_UP,
-                        KeyEvent.KEYCODE_ENTER));
-                break;
-
-            default:
-                handled = super.performEditorAction(editorAction);
-                break;
-            }
-
-            return handled;
-        }
-
-        public void initEditorInfo(WebViewCore.TextFieldInitData initData) {
-            int type = initData.mType;
-            int inputType = InputType.TYPE_CLASS_TEXT
-                    | InputType.TYPE_TEXT_VARIATION_WEB_EDIT_TEXT;
-            int imeOptions = EditorInfo.IME_FLAG_NO_EXTRACT_UI
-                    | EditorInfo.IME_FLAG_NO_FULLSCREEN;
-            if (!initData.mIsSpellCheckEnabled) {
-                inputType |= InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS;
-            }
-            if (WebTextView.TEXT_AREA != type
-                    && initData.mIsTextFieldNext) {
-                imeOptions |= EditorInfo.IME_FLAG_NAVIGATE_NEXT;
-            }
-            switch (type) {
-                case WebTextView.NORMAL_TEXT_FIELD:
-                    imeOptions |= EditorInfo.IME_ACTION_GO;
-                    break;
-                case WebTextView.TEXT_AREA:
-                    inputType |= InputType.TYPE_TEXT_FLAG_MULTI_LINE
-                            | InputType.TYPE_TEXT_FLAG_CAP_SENTENCES
-                            | InputType.TYPE_TEXT_FLAG_AUTO_CORRECT;
-                    imeOptions |= EditorInfo.IME_ACTION_NONE;
-                    break;
-                case WebTextView.PASSWORD:
-                    inputType |= EditorInfo.TYPE_TEXT_VARIATION_WEB_PASSWORD;
-                    imeOptions |= EditorInfo.IME_ACTION_GO;
-                    break;
-                case WebTextView.SEARCH:
-                    imeOptions |= EditorInfo.IME_ACTION_SEARCH;
-                    break;
-                case WebTextView.EMAIL:
-                    // inputType needs to be overwritten because of the different text variation.
-                    inputType = InputType.TYPE_CLASS_TEXT
-                            | InputType.TYPE_TEXT_VARIATION_WEB_EMAIL_ADDRESS;
-                    imeOptions |= EditorInfo.IME_ACTION_GO;
-                    break;
-                case WebTextView.NUMBER:
-                    // inputType needs to be overwritten because of the different class.
-                    inputType = InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_VARIATION_NORMAL
-                            | InputType.TYPE_NUMBER_FLAG_SIGNED | InputType.TYPE_NUMBER_FLAG_DECIMAL;
-                    // Number and telephone do not have both a Tab key and an
-                    // action, so set the action to NEXT
-                    imeOptions |= EditorInfo.IME_ACTION_NEXT;
-                    break;
-                case WebTextView.TELEPHONE:
-                    // inputType needs to be overwritten because of the different class.
-                    inputType = InputType.TYPE_CLASS_PHONE;
-                    imeOptions |= EditorInfo.IME_ACTION_NEXT;
-                    break;
-                case WebTextView.URL:
-                    // TYPE_TEXT_VARIATION_URI prevents Tab key from showing, so
-                    // exclude it for now.
-                    imeOptions |= EditorInfo.IME_ACTION_GO;
-                    inputType |= InputType.TYPE_TEXT_VARIATION_URI;
-                    break;
-                default:
-                    imeOptions |= EditorInfo.IME_ACTION_GO;
-                    break;
-            }
-            mHint = initData.mLabel;
-            mInputType = inputType;
-            mImeOptions = imeOptions;
-            mMaxLength = initData.mMaxLength;
-        }
-
-        public void setupEditorInfo(EditorInfo outAttrs) {
-            outAttrs.inputType = mInputType;
-            outAttrs.imeOptions = mImeOptions;
-            outAttrs.hintText = mHint;
-            outAttrs.initialCapsMode = getCursorCapsMode(InputType.TYPE_CLASS_TEXT);
-        }
-
-        /**
-         * Sends a text change to webkit indirectly. If it is a single-
-         * character add or delete, it sends it as a key stroke. If it cannot
-         * be represented as a key stroke, it sends it as a field change.
-         * @param start The start offset (inclusive) of the text being changed.
-         * @param end The end offset (exclusive) of the text being changed.
-         * @param text The new text to replace the changed text.
-         */
-        private void setNewText(int start, int end, CharSequence text) {
-            mIsKeySentByMe = true;
-            Editable editable = getEditable();
-            CharSequence original = editable.subSequence(start, end);
-            boolean isCharacterAdd = false;
-            boolean isCharacterDelete = false;
-            int textLength = text.length();
-            int originalLength = original.length();
-            if (textLength > originalLength) {
-                isCharacterAdd = (textLength == originalLength + 1)
-                        && TextUtils.regionMatches(text, 0, original, 0,
-                                originalLength);
-            } else if (originalLength > textLength) {
-                isCharacterDelete = (textLength == originalLength - 1)
-                        && TextUtils.regionMatches(text, 0, original, 0,
-                                textLength);
-            }
-            if (isCharacterAdd) {
-                sendCharacter(text.charAt(textLength - 1));
-            } else if (isCharacterDelete) {
-                sendKey(KeyEvent.KEYCODE_DEL);
-            } else if ((textLength != originalLength) ||
-                    !TextUtils.regionMatches(text, 0, original, 0,
-                            textLength)) {
-                // Send a message so that key strokes and text replacement
-                // do not come out of order.
-                Message replaceMessage = mPrivateHandler.obtainMessage(
-                        REPLACE_TEXT, start,  end, text.toString());
-                mPrivateHandler.sendMessage(replaceMessage);
-            }
-            mIsKeySentByMe = false;
-        }
-
-        /**
-         * Send a single character to the WebView as a key down and up event.
-         * @param c The character to be sent.
-         */
-        private void sendCharacter(char c) {
-            if (mKeyCharacterMap == null) {
-                mKeyCharacterMap = KeyCharacterMap.load(KeyCharacterMap.VIRTUAL_KEYBOARD);
-            }
-            char[] chars = new char[1];
-            chars[0] = c;
-            KeyEvent[] events = mKeyCharacterMap.getEvents(chars);
-            if (events != null) {
-                for (KeyEvent event : events) {
-                    sendKeyEvent(event);
-                }
-            } else {
-                Message msg = mPrivateHandler.obtainMessage(KEY_PRESS, (int) c, 0);
-                mPrivateHandler.sendMessage(msg);
-            }
-        }
-
-        /**
-         * Send a key event for a specific key code, not a standard
-         * unicode character.
-         * @param keyCode The key code to send.
-         */
-        private void sendKey(int keyCode) {
-            long eventTime = SystemClock.uptimeMillis();
-            sendKeyEvent(new KeyEvent(eventTime, eventTime,
-                    KeyEvent.ACTION_DOWN, keyCode, 0, 0,
-                    KeyCharacterMap.VIRTUAL_KEYBOARD, 0,
-                    KeyEvent.FLAG_SOFT_KEYBOARD));
-            sendKeyEvent(new KeyEvent(SystemClock.uptimeMillis(), eventTime,
-                    KeyEvent.ACTION_UP, keyCode, 0, 0,
-                    KeyCharacterMap.VIRTUAL_KEYBOARD, 0,
-                    KeyEvent.FLAG_SOFT_KEYBOARD));
-        }
-
-        private CharSequence limitReplaceTextByMaxLength(CharSequence text,
-                int numReplaced) {
-            if (mMaxLength > 0) {
-                Editable editable = getEditable();
-                int maxReplace = mMaxLength - editable.length() + numReplaced;
-                if (maxReplace < text.length()) {
-                    maxReplace = Math.max(maxReplace, 0);
-                    // New length is greater than the maximum. trim it down.
-                    text = text.subSequence(0, maxReplace);
-                }
-            }
-            return text;
-        }
-
-        private void restartInput() {
-            InputMethodManager imm = InputMethodManager.peekInstance();
-            if (imm != null) {
-                // Since the text has changed, do not allow the IME to replace the
-                // existing text as though it were a completion.
-                imm.restartInput(WebView.this);
-            }
-        }
-    }
-
-    private class PastePopupWindow extends PopupWindow implements OnClickListener {
-        private ViewGroup mContentView;
-        private TextView mPasteTextView;
-
-        public PastePopupWindow() {
-            super(WebView.this.mContext, null,
-                    com.android.internal.R.attr.textSelectHandleWindowStyle);
-            setClippingEnabled(true);
-            LinearLayout linearLayout = new LinearLayout(WebView.this.getContext());
-            linearLayout.setOrientation(LinearLayout.HORIZONTAL);
-            mContentView = linearLayout;
-            mContentView.setBackgroundResource(
-                    com.android.internal.R.drawable.text_edit_paste_window);
-
-            LayoutInflater inflater = (LayoutInflater)WebView.this.mContext.
-                    getSystemService(Context.LAYOUT_INFLATER_SERVICE);
-
-            ViewGroup.LayoutParams wrapContent = new ViewGroup.LayoutParams(
-                    ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
-
-            mPasteTextView = (TextView) inflater.inflate(
-                    com.android.internal.R.layout.text_edit_action_popup_text, null);
-            mPasteTextView.setLayoutParams(wrapContent);
-            mContentView.addView(mPasteTextView);
-            mPasteTextView.setText(com.android.internal.R.string.paste);
-            mPasteTextView.setOnClickListener(this);
-            this.setContentView(mContentView);
-        }
-
-        public void show(Rect cursorRect, int windowLeft, int windowTop) {
-            measureContent();
-
-            int width = mContentView.getMeasuredWidth();
-            int height = mContentView.getMeasuredHeight();
-            int y = cursorRect.top - height;
-            if (y < windowTop) {
-                // There's not enough room vertically, move it below the
-                // handle.
-                // The selection handle is vertically offset by 1/4 of the
-                // line height.
-                y = cursorRect.bottom - (cursorRect.height() / 4) +
-                        mSelectHandleCenter.getIntrinsicHeight();
-            }
-            int x = cursorRect.centerX() - (width / 2);
-            if (x < windowLeft) {
-                x = windowLeft;
-            }
-            if (!isShowing()) {
-                showAtLocation(WebView.this, Gravity.NO_GRAVITY, x, y);
-            }
-            update(x, y, width, height);
-        }
-
-        public void hide() {
-            dismiss();
-        }
-
-        @Override
-        public void onClick(View view) {
-            pasteFromClipboard();
-            selectionDone();
-        }
-
-        protected void measureContent() {
-            final DisplayMetrics displayMetrics = mContext.getResources().getDisplayMetrics();
-            mContentView.measure(
-                    View.MeasureSpec.makeMeasureSpec(displayMetrics.widthPixels,
-                            View.MeasureSpec.AT_MOST),
-                    View.MeasureSpec.makeMeasureSpec(displayMetrics.heightPixels,
-                            View.MeasureSpec.AT_MOST));
-        }
-    }
-
-    // The listener to capture global layout change event.
-    private InnerGlobalLayoutListener mGlobalLayoutListener = null;
-
-    // The listener to capture scroll event.
-    private InnerScrollChangedListener mScrollChangedListener = null;
-
-    // if AUTO_REDRAW_HACK is true, then the CALL key will toggle redrawing
-    // the screen all-the-time. Good for profiling our drawing code
-    static private final boolean AUTO_REDRAW_HACK = false;
-    // true means redraw the screen all-the-time. Only with AUTO_REDRAW_HACK
-    private boolean mAutoRedraw;
-
-    // Reference to the AlertDialog displayed by InvokeListBox.
-    // It's used to dismiss the dialog in destroy if not done before.
-    private AlertDialog mListBoxDialog = null;
-
-    static final String LOGTAG = "webview";
-
-    private ZoomManager mZoomManager;
-
-    private final Rect mGLRectViewport = new Rect();
-    private final Rect mViewRectViewport = new Rect();
-    private final RectF mVisibleContentRect = new RectF();
-    private boolean mGLViewportEmpty = false;
-    WebViewInputConnection mInputConnection = null;
-    private int mFieldPointer;
-    private PastePopupWindow mPasteWindow;
+    private static final String LOGTAG = "webview_proxy";
+    // TODO: flip DEBUG to always be disabled.
+    private static final boolean DEBUG = true;
 
     /**
      *  Transportation object for returning WebView across thread boundaries.
@@ -815,531 +297,6 @@
         }
     }
 
-    private static class OnTrimMemoryListener implements ComponentCallbacks2 {
-        private static OnTrimMemoryListener sInstance = null;
-
-        static void init(Context c) {
-            if (sInstance == null) {
-                sInstance = new OnTrimMemoryListener(c.getApplicationContext());
-            }
-        }
-
-        private OnTrimMemoryListener(Context c) {
-            c.registerComponentCallbacks(this);
-        }
-
-        @Override
-        public void onConfigurationChanged(Configuration newConfig) {
-            // Ignore
-        }
-
-        @Override
-        public void onLowMemory() {
-            // Ignore
-        }
-
-        @Override
-        public void onTrimMemory(int level) {
-            if (DebugFlags.WEB_VIEW) {
-                Log.d("WebView", "onTrimMemory: " + level);
-            }
-            // When framework reset EGL context during high memory pressure, all
-            // the existing GL resources for the html5 video will be destroyed
-            // at native side.
-            // Here we just need to clean up the Surface Texture which is static.
-            HTML5VideoInline.cleanupSurfaceTexture();
-            WebView.nativeOnTrimMemory(level);
-        }
-
-    }
-
-    // A final CallbackProxy shared by WebViewCore and BrowserFrame.
-    private final CallbackProxy mCallbackProxy;
-
-    private final WebViewDatabase mDatabase;
-
-    // SSL certificate for the main top-level page (if secure)
-    private SslCertificate mCertificate;
-
-    // Native WebView pointer that is 0 until the native object has been
-    // created.
-    private int mNativeClass;
-    // This would be final but it needs to be set to null when the WebView is
-    // destroyed.
-    private WebViewCore mWebViewCore;
-    // Handler for dispatching UI messages.
-    /* package */ final Handler mPrivateHandler = new PrivateHandler();
-    private WebTextView mWebTextView;
-    // Used to ignore changes to webkit text that arrives to the UI side after
-    // more key events.
-    private int mTextGeneration;
-
-    /* package */ void incrementTextGeneration() { mTextGeneration++; }
-
-    // Used by WebViewCore to create child views.
-    /* package */ final ViewManager mViewManager;
-
-    // Used to display in full screen mode
-    PluginFullScreenHolder mFullScreenHolder;
-
-    /**
-     * Position of the last touch event in pixels.
-     * Use integer to prevent loss of dragging delta calculation accuracy;
-     * which was done in float and converted to integer, and resulted in gradual
-     * and compounding touch position and view dragging mismatch.
-     */
-    private int mLastTouchX;
-    private int mLastTouchY;
-    private int mStartTouchX;
-    private int mStartTouchY;
-    private float mAverageAngle;
-
-    /**
-     * Time of the last touch event.
-     */
-    private long mLastTouchTime;
-
-    /**
-     * Time of the last time sending touch event to WebViewCore
-     */
-    private long mLastSentTouchTime;
-
-    /**
-     * The minimum elapsed time before sending another ACTION_MOVE event to
-     * WebViewCore. This really should be tuned for each type of the devices.
-     * For example in Google Map api test case, it takes Dream device at least
-     * 150ms to do a full cycle in the WebViewCore by processing a touch event,
-     * triggering the layout and drawing the picture. While the same process
-     * takes 60+ms on the current high speed device. If we make
-     * TOUCH_SENT_INTERVAL too small, there will be multiple touch events sent
-     * to WebViewCore queue and the real layout and draw events will be pushed
-     * to further, which slows down the refresh rate. Choose 50 to favor the
-     * current high speed devices. For Dream like devices, 100 is a better
-     * choice. Maybe make this in the buildspec later.
-     * (Update 12/14/2010: changed to 0 since current device should be able to
-     * handle the raw events and Map team voted to have the raw events too.
-     */
-    private static final int TOUCH_SENT_INTERVAL = 0;
-    private int mCurrentTouchInterval = TOUCH_SENT_INTERVAL;
-
-    /**
-     * Helper class to get velocity for fling
-     */
-    VelocityTracker mVelocityTracker;
-    private int mMaximumFling;
-    private float mLastVelocity;
-    private float mLastVelX;
-    private float mLastVelY;
-
-    // The id of the native layer being scrolled.
-    private int mCurrentScrollingLayerId;
-    private Rect mScrollingLayerRect = new Rect();
-
-    // only trigger accelerated fling if the new velocity is at least
-    // MINIMUM_VELOCITY_RATIO_FOR_ACCELERATION times of the previous velocity
-    private static final float MINIMUM_VELOCITY_RATIO_FOR_ACCELERATION = 0.2f;
-
-    /**
-     * Touch mode
-     */
-    private int mTouchMode = TOUCH_DONE_MODE;
-    private static final int TOUCH_INIT_MODE = 1;
-    private static final int TOUCH_DRAG_START_MODE = 2;
-    private static final int TOUCH_DRAG_MODE = 3;
-    private static final int TOUCH_SHORTPRESS_START_MODE = 4;
-    private static final int TOUCH_SHORTPRESS_MODE = 5;
-    private static final int TOUCH_DOUBLE_TAP_MODE = 6;
-    private static final int TOUCH_DONE_MODE = 7;
-    private static final int TOUCH_PINCH_DRAG = 8;
-    private static final int TOUCH_DRAG_LAYER_MODE = 9;
-
-    // Whether to forward the touch events to WebCore
-    // Can only be set by WebKit via JNI.
-    private boolean mForwardTouchEvents = false;
-
-    // Whether to prevent default during touch. The initial value depends on
-    // mForwardTouchEvents. If WebCore wants all the touch events, it says yes
-    // for touch down. Otherwise UI will wait for the answer of the first
-    // confirmed move before taking over the control.
-    private static final int PREVENT_DEFAULT_NO = 0;
-    private static final int PREVENT_DEFAULT_MAYBE_YES = 1;
-    private static final int PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN = 2;
-    private static final int PREVENT_DEFAULT_YES = 3;
-    private static final int PREVENT_DEFAULT_IGNORE = 4;
-    private int mPreventDefault = PREVENT_DEFAULT_IGNORE;
-
-    // true when the touch movement exceeds the slop
-    private boolean mConfirmMove;
-
-    // if true, touch events will be first processed by WebCore, if prevent
-    // default is not set, the UI will continue handle them.
-    private boolean mDeferTouchProcess;
-
-    // to avoid interfering with the current touch events, track them
-    // separately. Currently no snapping or fling in the deferred process mode
-    private int mDeferTouchMode = TOUCH_DONE_MODE;
-    private float mLastDeferTouchX;
-    private float mLastDeferTouchY;
-
-    // To keep track of whether the current drag was initiated by a WebTextView,
-    // so that we know not to hide the cursor
-    boolean mDragFromTextInput;
-
-    // Whether or not to draw the cursor ring.
-    private boolean mDrawCursorRing = true;
-
-    // true if onPause has been called (and not onResume)
-    private boolean mIsPaused;
-
-    private HitTestResult mInitialHitTestResult;
-    private WebKitHitTest mFocusedNode;
-
-    /**
-     * Customizable constant
-     */
-    // pre-computed square of ViewConfiguration.getScaledTouchSlop()
-    private int mTouchSlopSquare;
-    // pre-computed square of ViewConfiguration.getScaledDoubleTapSlop()
-    private int mDoubleTapSlopSquare;
-    // pre-computed density adjusted navigation slop
-    private int mNavSlop;
-    // This should be ViewConfiguration.getTapTimeout()
-    // But system time out is 100ms, which is too short for the browser.
-    // In the browser, if it switches out of tap too soon, jump tap won't work.
-    // In addition, a double tap on a trackpad will always have a duration of
-    // 300ms, so this value must be at least that (otherwise we will timeout the
-    // first tap and convert it to a long press).
-    private static final int TAP_TIMEOUT = 300;
-    // This should be ViewConfiguration.getLongPressTimeout()
-    // But system time out is 500ms, which is too short for the browser.
-    // With a short timeout, it's difficult to treat trigger a short press.
-    private static final int LONG_PRESS_TIMEOUT = 1000;
-    // needed to avoid flinging after a pause of no movement
-    private static final int MIN_FLING_TIME = 250;
-    // draw unfiltered after drag is held without movement
-    private static final int MOTIONLESS_TIME = 100;
-    // The amount of content to overlap between two screens when going through
-    // pages with the space bar, in pixels.
-    private static final int PAGE_SCROLL_OVERLAP = 24;
-
-    /**
-     * These prevent calling requestLayout if either dimension is fixed. This
-     * depends on the layout parameters and the measure specs.
-     */
-    boolean mWidthCanMeasure;
-    boolean mHeightCanMeasure;
-
-    // Remember the last dimensions we sent to the native side so we can avoid
-    // sending the same dimensions more than once.
-    int mLastWidthSent;
-    int mLastHeightSent;
-    // Since view height sent to webkit could be fixed to avoid relayout, this
-    // value records the last sent actual view height.
-    int mLastActualHeightSent;
-
-    private int mContentWidth;   // cache of value from WebViewCore
-    private int mContentHeight;  // cache of value from WebViewCore
-
-    // Need to have the separate control for horizontal and vertical scrollbar
-    // style than the View's single scrollbar style
-    private boolean mOverlayHorizontalScrollbar = true;
-    private boolean mOverlayVerticalScrollbar = false;
-
-    // our standard speed. this way small distances will be traversed in less
-    // time than large distances, but we cap the duration, so that very large
-    // distances won't take too long to get there.
-    private static final int STD_SPEED = 480;  // pixels per second
-    // time for the longest scroll animation
-    private static final int MAX_DURATION = 750;   // milliseconds
-    private static final int SLIDE_TITLE_DURATION = 500;   // milliseconds
-
-    // Used by OverScrollGlow
-    OverScroller mScroller;
-
-    private boolean mInOverScrollMode = false;
-    private static Paint mOverScrollBackground;
-    private static Paint mOverScrollBorder;
-
-    private boolean mWrapContent;
-    private static final int MOTIONLESS_FALSE           = 0;
-    private static final int MOTIONLESS_PENDING         = 1;
-    private static final int MOTIONLESS_TRUE            = 2;
-    private static final int MOTIONLESS_IGNORE          = 3;
-    private int mHeldMotionless;
-
-    // An instance for injecting accessibility in WebViews with disabled
-    // JavaScript or ones for which no accessibility script exists
-    private AccessibilityInjector mAccessibilityInjector;
-
-    // flag indicating if accessibility script is injected so we
-    // know to handle Shift and arrows natively first
-    private boolean mAccessibilityScriptInjected;
-
-
-    /**
-     * How long the caret handle will last without being touched.
-     */
-    private static final long CARET_HANDLE_STAMINA_MS = 3000;
-
-    private Drawable mSelectHandleLeft;
-    private Drawable mSelectHandleRight;
-    private Drawable mSelectHandleCenter;
-    private Rect mSelectCursorBase = new Rect();
-    private int mSelectCursorBaseLayerId;
-    private Rect mSelectCursorExtent = new Rect();
-    private int mSelectCursorExtentLayerId;
-    private Rect mSelectDraggingCursor;
-    private Point mSelectDraggingOffset = new Point();
-    private boolean mIsCaretSelection;
-    static final int HANDLE_ID_START = 0;
-    static final int HANDLE_ID_END = 1;
-    static final int HANDLE_ID_BASE = 2;
-    static final int HANDLE_ID_EXTENT = 3;
-
-    static boolean sDisableNavcache = false;
-    static boolean sEnableWebTextView = false;
-    // the color used to highlight the touch rectangles
-    static final int HIGHLIGHT_COLOR = 0x6633b5e5;
-    // the region indicating where the user touched on the screen
-    private Region mTouchHighlightRegion = new Region();
-    // the paint for the touch highlight
-    private Paint mTouchHightlightPaint = new Paint();
-    // debug only
-    private static final boolean DEBUG_TOUCH_HIGHLIGHT = true;
-    private static final int TOUCH_HIGHLIGHT_ELAPSE_TIME = 2000;
-    private Paint mTouchCrossHairColor;
-    private int mTouchHighlightX;
-    private int mTouchHighlightY;
-    private long mTouchHighlightRequested;
-
-    // Basically this proxy is used to tell the Video to update layer tree at
-    // SetBaseLayer time and to pause when WebView paused.
-    private HTML5VideoViewProxy mHTML5VideoViewProxy;
-
-    // If we are using a set picture, don't send view updates to webkit
-    private boolean mBlockWebkitViewMessages = false;
-
-    // cached value used to determine if we need to switch drawing models
-    private boolean mHardwareAccelSkia = false;
-
-    /*
-     * Private message ids
-     */
-    private static final int REMEMBER_PASSWORD          = 1;
-    private static final int NEVER_REMEMBER_PASSWORD    = 2;
-    private static final int SWITCH_TO_SHORTPRESS       = 3;
-    private static final int SWITCH_TO_LONGPRESS        = 4;
-    private static final int RELEASE_SINGLE_TAP         = 5;
-    private static final int REQUEST_FORM_DATA          = 6;
-    private static final int DRAG_HELD_MOTIONLESS       = 8;
-    private static final int AWAKEN_SCROLL_BARS         = 9;
-    private static final int PREVENT_DEFAULT_TIMEOUT    = 10;
-    private static final int SCROLL_SELECT_TEXT         = 11;
-
-
-    private static final int FIRST_PRIVATE_MSG_ID = REMEMBER_PASSWORD;
-    private static final int LAST_PRIVATE_MSG_ID = SCROLL_SELECT_TEXT;
-
-    /*
-     * Package message ids
-     */
-    static final int SCROLL_TO_MSG_ID                   = 101;
-    static final int NEW_PICTURE_MSG_ID                 = 105;
-    static final int UPDATE_TEXT_ENTRY_MSG_ID           = 106;
-    static final int WEBCORE_INITIALIZED_MSG_ID         = 107;
-    static final int UPDATE_TEXTFIELD_TEXT_MSG_ID       = 108;
-    static final int UPDATE_ZOOM_RANGE                  = 109;
-    static final int UNHANDLED_NAV_KEY                  = 110;
-    static final int CLEAR_TEXT_ENTRY                   = 111;
-    static final int UPDATE_TEXT_SELECTION_MSG_ID       = 112;
-    static final int SHOW_RECT_MSG_ID                   = 113;
-    static final int LONG_PRESS_CENTER                  = 114;
-    static final int PREVENT_TOUCH_ID                   = 115;
-    static final int WEBCORE_NEED_TOUCH_EVENTS          = 116;
-    // obj=Rect in doc coordinates
-    static final int INVAL_RECT_MSG_ID                  = 117;
-    static final int REQUEST_KEYBOARD                   = 118;
-    static final int DO_MOTION_UP                       = 119;
-    static final int SHOW_FULLSCREEN                    = 120;
-    static final int HIDE_FULLSCREEN                    = 121;
-    static final int DOM_FOCUS_CHANGED                  = 122;
-    static final int REPLACE_BASE_CONTENT               = 123;
-    static final int FORM_DID_BLUR                      = 124;
-    static final int RETURN_LABEL                       = 125;
-    static final int UPDATE_MATCH_COUNT                 = 126;
-    static final int CENTER_FIT_RECT                    = 127;
-    static final int REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID = 128;
-    static final int SET_SCROLLBAR_MODES                = 129;
-    static final int SELECTION_STRING_CHANGED           = 130;
-    static final int HIT_TEST_RESULT                    = 131;
-    static final int SAVE_WEBARCHIVE_FINISHED           = 132;
-
-    static final int SET_AUTOFILLABLE                   = 133;
-    static final int AUTOFILL_COMPLETE                  = 134;
-
-    static final int SELECT_AT                          = 135;
-    static final int SCREEN_ON                          = 136;
-    static final int ENTER_FULLSCREEN_VIDEO             = 137;
-    static final int UPDATE_SELECTION                   = 138;
-    static final int UPDATE_ZOOM_DENSITY                = 139;
-    static final int EXIT_FULLSCREEN_VIDEO              = 140;
-
-    static final int COPY_TO_CLIPBOARD                  = 141;
-    static final int INIT_EDIT_FIELD                    = 142;
-    static final int REPLACE_TEXT                       = 143;
-    static final int CLEAR_CARET_HANDLE                 = 144;
-    static final int KEY_PRESS                          = 145;
-
-    private static final int FIRST_PACKAGE_MSG_ID = SCROLL_TO_MSG_ID;
-    private static final int LAST_PACKAGE_MSG_ID = HIT_TEST_RESULT;
-
-    static final String[] HandlerPrivateDebugString = {
-        "REMEMBER_PASSWORD", //              = 1;
-        "NEVER_REMEMBER_PASSWORD", //        = 2;
-        "SWITCH_TO_SHORTPRESS", //           = 3;
-        "SWITCH_TO_LONGPRESS", //            = 4;
-        "RELEASE_SINGLE_TAP", //             = 5;
-        "REQUEST_FORM_DATA", //              = 6;
-        "RESUME_WEBCORE_PRIORITY", //        = 7;
-        "DRAG_HELD_MOTIONLESS", //           = 8;
-        "AWAKEN_SCROLL_BARS", //             = 9;
-        "PREVENT_DEFAULT_TIMEOUT", //        = 10;
-        "SCROLL_SELECT_TEXT" //              = 11;
-    };
-
-    static final String[] HandlerPackageDebugString = {
-        "SCROLL_TO_MSG_ID", //               = 101;
-        "102", //                            = 102;
-        "103", //                            = 103;
-        "104", //                            = 104;
-        "NEW_PICTURE_MSG_ID", //             = 105;
-        "UPDATE_TEXT_ENTRY_MSG_ID", //       = 106;
-        "WEBCORE_INITIALIZED_MSG_ID", //     = 107;
-        "UPDATE_TEXTFIELD_TEXT_MSG_ID", //   = 108;
-        "UPDATE_ZOOM_RANGE", //              = 109;
-        "UNHANDLED_NAV_KEY", //              = 110;
-        "CLEAR_TEXT_ENTRY", //               = 111;
-        "UPDATE_TEXT_SELECTION_MSG_ID", //   = 112;
-        "SHOW_RECT_MSG_ID", //               = 113;
-        "LONG_PRESS_CENTER", //              = 114;
-        "PREVENT_TOUCH_ID", //               = 115;
-        "WEBCORE_NEED_TOUCH_EVENTS", //      = 116;
-        "INVAL_RECT_MSG_ID", //              = 117;
-        "REQUEST_KEYBOARD", //               = 118;
-        "DO_MOTION_UP", //                   = 119;
-        "SHOW_FULLSCREEN", //                = 120;
-        "HIDE_FULLSCREEN", //                = 121;
-        "DOM_FOCUS_CHANGED", //              = 122;
-        "REPLACE_BASE_CONTENT", //           = 123;
-        "FORM_DID_BLUR", //                  = 124;
-        "RETURN_LABEL", //                   = 125;
-        "UPDATE_MATCH_COUNT", //             = 126;
-        "CENTER_FIT_RECT", //                = 127;
-        "REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID", // = 128;
-        "SET_SCROLLBAR_MODES", //            = 129;
-        "SELECTION_STRING_CHANGED", //       = 130;
-        "SET_TOUCH_HIGHLIGHT_RECTS", //      = 131;
-        "SAVE_WEBARCHIVE_FINISHED", //       = 132;
-        "SET_AUTOFILLABLE", //               = 133;
-        "AUTOFILL_COMPLETE", //              = 134;
-        "SELECT_AT", //                      = 135;
-        "SCREEN_ON", //                      = 136;
-        "ENTER_FULLSCREEN_VIDEO", //         = 137;
-        "UPDATE_SELECTION", //               = 138;
-        "UPDATE_ZOOM_DENSITY" //             = 139;
-    };
-
-    // If the site doesn't use the viewport meta tag to specify the viewport,
-    // use DEFAULT_VIEWPORT_WIDTH as the default viewport width
-    static final int DEFAULT_VIEWPORT_WIDTH = 980;
-
-    // normally we try to fit the content to the minimum preferred width
-    // calculated by the Webkit. To avoid the bad behavior when some site's
-    // minimum preferred width keeps growing when changing the viewport width or
-    // the minimum preferred width is huge, an upper limit is needed.
-    static int sMaxViewportWidth = DEFAULT_VIEWPORT_WIDTH;
-
-    // initial scale in percent. 0 means using default.
-    private int mInitialScaleInPercent = 0;
-
-    // Whether or not a scroll event should be sent to webkit.  This is only set
-    // to false when restoring the scroll position.
-    private boolean mSendScrollEvent = true;
-
-    private int mSnapScrollMode = SNAP_NONE;
-    private static final int SNAP_NONE = 0;
-    private static final int SNAP_LOCK = 1; // not a separate state
-    private static final int SNAP_X = 2; // may be combined with SNAP_LOCK
-    private static final int SNAP_Y = 4; // may be combined with SNAP_LOCK
-    private boolean mSnapPositive;
-
-    // keep these in sync with their counterparts in WebView.cpp
-    private static final int DRAW_EXTRAS_NONE = 0;
-    private static final int DRAW_EXTRAS_SELECTION = 1;
-    private static final int DRAW_EXTRAS_CURSOR_RING = 2;
-
-    // keep this in sync with WebCore:ScrollbarMode in WebKit
-    private static final int SCROLLBAR_AUTO = 0;
-    private static final int SCROLLBAR_ALWAYSOFF = 1;
-    // as we auto fade scrollbar, this is ignored.
-    private static final int SCROLLBAR_ALWAYSON = 2;
-    private int mHorizontalScrollBarMode = SCROLLBAR_AUTO;
-    private int mVerticalScrollBarMode = SCROLLBAR_AUTO;
-
-    // constants for determining script injection strategy
-    private static final int ACCESSIBILITY_SCRIPT_INJECTION_UNDEFINED = -1;
-    private static final int ACCESSIBILITY_SCRIPT_INJECTION_OPTED_OUT = 0;
-    private static final int ACCESSIBILITY_SCRIPT_INJECTION_PROVIDED = 1;
-
-    // the alias via which accessibility JavaScript interface is exposed
-    private static final String ALIAS_ACCESSIBILITY_JS_INTERFACE = "accessibility";
-
-    // Template for JavaScript that injects a screen-reader.
-    private static final String ACCESSIBILITY_SCREEN_READER_JAVASCRIPT_TEMPLATE =
-        "javascript:(function() {" +
-        "    var chooser = document.createElement('script');" +
-        "    chooser.type = 'text/javascript';" +
-        "    chooser.src = '%1s';" +
-        "    document.getElementsByTagName('head')[0].appendChild(chooser);" +
-        "  })();";
-
-    // Regular expression that matches the "axs" URL parameter.
-    // The value of 0 means the accessibility script is opted out
-    // The value of 1 means the accessibility script is already injected
-    private static final String PATTERN_MATCH_AXS_URL_PARAMETER = "(\\?axs=(0|1))|(&axs=(0|1))";
-
-    // TextToSpeech instance exposed to JavaScript to the injected screenreader.
-    private TextToSpeech mTextToSpeech;
-
-    // variable to cache the above pattern in case accessibility is enabled.
-    private Pattern mMatchAxsUrlParameterPattern;
-
-    /**
-     * Max distance to overscroll by in pixels.
-     * This how far content can be pulled beyond its normal bounds by the user.
-     */
-    private int mOverscrollDistance;
-
-    /**
-     * Max distance to overfling by in pixels.
-     * This is how far flinged content can move beyond the end of its normal bounds.
-     */
-    private int mOverflingDistance;
-
-    private OverScrollGlow mOverScrollGlow;
-
-    // Used to match key downs and key ups
-    private Vector<Integer> mKeysPressed;
-
-    /* package */ static boolean mLogEvent = true;
-
-    // for event log
-    private long mLastTouchUpTime = 0;
-
-    private WebViewCore.AutoFillData mAutoFillData;
-
-    private static boolean sNotificationsEnabled = true;
-
     /**
      * URI scheme for telephone number
      */
@@ -1353,26 +310,6 @@
      */
     public static final String SCHEME_GEO = "geo:0,0?q=";
 
-    private int mBackgroundColor = Color.WHITE;
-
-    private static final long SELECT_SCROLL_INTERVAL = 1000 / 60; // 60 / second
-    private int mAutoScrollX = 0;
-    private int mAutoScrollY = 0;
-    private int mMinAutoScrollX = 0;
-    private int mMaxAutoScrollX = 0;
-    private int mMinAutoScrollY = 0;
-    private int mMaxAutoScrollY = 0;
-    private Rect mScrollingLayerBounds = new Rect();
-    private boolean mSentAutoScrollMessage = false;
-
-    // used for serializing asynchronously handled touch events.
-    private final TouchEventQueue mTouchEventQueue = new TouchEventQueue();
-
-    // Used to track whether picture updating was paused due to a window focus change.
-    private boolean mPictureUpdatePausedForFocusChange = false;
-
-    // Used to notify listeners of a new picture.
-    private PictureListener mPictureListener;
     /**
      * Interface to listen for new pictures as they change.
      * @deprecated This interface is now obsolete.
@@ -1440,15 +377,24 @@
         private int mType;
         private String mExtra;
 
-        HitTestResult() {
+        /**
+         * @hide Only for use by WebViewProvider implementations
+         */
+        public HitTestResult() {
             mType = UNKNOWN_TYPE;
         }
 
-        private void setType(int type) {
+        /**
+         * @hide Only for use by WebViewProvider implementations
+         */
+        public void setType(int type) {
             mType = type;
         }
 
-        private void setExtra(String extra) {
+        /**
+         * @hide Only for use by WebViewProvider implementations
+         */
+        public void setExtra(String extra) {
             mExtra = extra;
         }
 
@@ -1471,15 +417,6 @@
     }
 
     /**
-     * Refer to {@link WebView#requestFocusNodeHref(Message)} for more information
-     */
-    static class FocusNodeHref {
-        static final String TITLE = "title";
-        static final String URL = "url";
-        static final String SRC = "src";
-    }
-
-    /**
      * Construct a new WebView with a Context object.
      * @param context A Context object used to access application assets.
      */
@@ -1529,418 +466,20 @@
      * @param javaScriptInterfaces is a Map of interface names, as keys, and
      * object implementing those interfaces, as values.
      * @param privateBrowsing If true the web view will be initialized in private mode.
-     * @hide This is an implementation detail.
+     * @hide This is used internally by dumprendertree, as it requires the javaScript interfaces to
+     * be added synchronously, before a subsequent loadUrl call takes effect.
      */
+    @SuppressWarnings("deprecation")  // for super() call into deprecated base class constructor.
     protected WebView(Context context, AttributeSet attrs, int defStyle,
             Map<String, Object> javaScriptInterfaces, boolean privateBrowsing) {
         super(context, attrs, defStyle);
-        checkThread();
-
         if (context == null) {
             throw new IllegalArgumentException("Invalid context argument");
         }
+        checkThread();
 
-        // Used by the chrome stack to find application paths
-        JniUtil.setContext(context);
-
-        mCallbackProxy = new CallbackProxy(context, this);
-        mViewManager = new ViewManager(this);
-        L10nUtils.setApplicationContext(context.getApplicationContext());
-        mWebViewCore = new WebViewCore(context, this, mCallbackProxy, javaScriptInterfaces);
-        mDatabase = WebViewDatabase.getInstance(context);
-        mScroller = new OverScroller(context, null, 0, 0, false); //TODO Use OverScroller's flywheel
-        mZoomManager = new ZoomManager(this, mCallbackProxy);
-
-        /* The init method must follow the creation of certain member variables,
-         * such as the mZoomManager.
-         */
-        init();
-        setupPackageListener(context);
-        setupProxyListener(context);
-        setupTrustStorageListener(context);
-        updateMultiTouchSupport(context);
-
-        if (privateBrowsing) {
-            startPrivateBrowsing();
-        }
-
-        mAutoFillData = new WebViewCore.AutoFillData();
-    }
-
-    private static class TrustStorageListener extends BroadcastReceiver {
-        @Override
-        public void onReceive(Context context, Intent intent) {
-            if (intent.getAction().equals(KeyChain.ACTION_STORAGE_CHANGED)) {
-                handleCertTrustChanged();
-            }
-        }
-    }
-    private static TrustStorageListener sTrustStorageListener;
-
-    /**
-     * Handles update to the trust storage.
-     */
-    private static void handleCertTrustChanged() {
-        // send a message for indicating trust storage change
-        WebViewCore.sendStaticMessage(EventHub.TRUST_STORAGE_UPDATED, null);
-    }
-
-    /*
-     * @param context This method expects this to be a valid context.
-     */
-    private static void setupTrustStorageListener(Context context) {
-        if (sTrustStorageListener != null ) {
-            return;
-        }
-        IntentFilter filter = new IntentFilter();
-        filter.addAction(KeyChain.ACTION_STORAGE_CHANGED);
-        sTrustStorageListener = new TrustStorageListener();
-        Intent current =
-            context.getApplicationContext().registerReceiver(sTrustStorageListener, filter);
-        if (current != null) {
-            handleCertTrustChanged();
-        }
-    }
-
-    private static class ProxyReceiver extends BroadcastReceiver {
-        @Override
-        public void onReceive(Context context, Intent intent) {
-            if (intent.getAction().equals(Proxy.PROXY_CHANGE_ACTION)) {
-                handleProxyBroadcast(intent);
-            }
-        }
-    }
-
-    /*
-     * Receiver for PROXY_CHANGE_ACTION, will be null when it is not added handling broadcasts.
-     */
-    private static ProxyReceiver sProxyReceiver;
-
-    /*
-     * @param context This method expects this to be a valid context
-     */
-    private static synchronized void setupProxyListener(Context context) {
-        if (sProxyReceiver != null || sNotificationsEnabled == false) {
-            return;
-        }
-        IntentFilter filter = new IntentFilter();
-        filter.addAction(Proxy.PROXY_CHANGE_ACTION);
-        sProxyReceiver = new ProxyReceiver();
-        Intent currentProxy = context.getApplicationContext().registerReceiver(
-                sProxyReceiver, filter);
-        if (currentProxy != null) {
-            handleProxyBroadcast(currentProxy);
-        }
-    }
-
-    /*
-     * @param context This method expects this to be a valid context
-     */
-    private static synchronized void disableProxyListener(Context context) {
-        if (sProxyReceiver == null)
-            return;
-
-        context.getApplicationContext().unregisterReceiver(sProxyReceiver);
-        sProxyReceiver = null;
-    }
-
-    private static void handleProxyBroadcast(Intent intent) {
-        ProxyProperties proxyProperties = (ProxyProperties)intent.getExtra(Proxy.EXTRA_PROXY_INFO);
-        if (proxyProperties == null || proxyProperties.getHost() == null) {
-            WebViewCore.sendStaticMessage(EventHub.PROXY_CHANGED, null);
-            return;
-        }
-        WebViewCore.sendStaticMessage(EventHub.PROXY_CHANGED, proxyProperties);
-    }
-
-    /*
-     * A variable to track if there is a receiver added for ACTION_PACKAGE_ADDED
-     * or ACTION_PACKAGE_REMOVED.
-     */
-    private static boolean sPackageInstallationReceiverAdded = false;
-
-    /*
-     * A set of Google packages we monitor for the
-     * navigator.isApplicationInstalled() API. Add additional packages as
-     * needed.
-     */
-    private static Set<String> sGoogleApps;
-    static {
-        sGoogleApps = new HashSet<String>();
-        sGoogleApps.add("com.google.android.youtube");
-    }
-
-    private static class PackageListener extends 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;
-            }
-
-            if (sGoogleApps.contains(packageName)) {
-                if (Intent.ACTION_PACKAGE_ADDED.equals(action)) {
-                    WebViewCore.sendStaticMessage(EventHub.ADD_PACKAGE_NAME, packageName);
-                } else {
-                    WebViewCore.sendStaticMessage(EventHub.REMOVE_PACKAGE_NAME, packageName);
-                }
-            }
-
-            PluginManager pm = PluginManager.getInstance(context);
-            if (pm.containsPluginPermissionAndSignatures(packageName)) {
-                pm.refreshPlugins(Intent.ACTION_PACKAGE_ADDED.equals(action));
-            }
-        }
-    }
-
-    private void setupPackageListener(Context context) {
-
-        /*
-         * we must synchronize the instance check and the creation of the
-         * receiver to ensure that only ONE receiver exists for all WebView
-         * instances.
-         */
-        synchronized (WebView.class) {
-
-            // if the receiver already exists then we do not need to register it
-            // again
-            if (sPackageInstallationReceiverAdded) {
-                return;
-            }
-
-            IntentFilter filter = new IntentFilter(Intent.ACTION_PACKAGE_ADDED);
-            filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
-            filter.addDataScheme("package");
-            BroadcastReceiver packageListener = new PackageListener();
-            context.getApplicationContext().registerReceiver(packageListener, filter);
-            sPackageInstallationReceiverAdded = true;
-        }
-
-        // check if any of the monitored apps are already installed
-        AsyncTask<Void, Void, Set<String>> task = new AsyncTask<Void, Void, Set<String>>() {
-
-            @Override
-            protected Set<String> doInBackground(Void... unused) {
-                Set<String> installedPackages = new HashSet<String>();
-                PackageManager pm = mContext.getPackageManager();
-                for (String name : sGoogleApps) {
-                    try {
-                        pm.getPackageInfo(name,
-                                PackageManager.GET_ACTIVITIES | PackageManager.GET_SERVICES);
-                        installedPackages.add(name);
-                    } catch (PackageManager.NameNotFoundException e) {
-                        // package not found
-                    }
-                }
-                return installedPackages;
-            }
-
-            // Executes on the UI thread
-            @Override
-            protected void onPostExecute(Set<String> installedPackages) {
-                if (mWebViewCore != null) {
-                    mWebViewCore.sendMessage(EventHub.ADD_PACKAGE_NAMES, installedPackages);
-                }
-            }
-        };
-        task.execute();
-    }
-
-    void updateMultiTouchSupport(Context context) {
-        mZoomManager.updateMultiTouchSupport(context);
-    }
-
-    private void init() {
-        OnTrimMemoryListener.init(getContext());
-        sDisableNavcache = nativeDisableNavcache();
-        setWillNotDraw(false);
-        setFocusable(true);
-        setFocusableInTouchMode(true);
-        setClickable(true);
-        setLongClickable(true);
-
-        final ViewConfiguration configuration = ViewConfiguration.get(getContext());
-        int slop = configuration.getScaledTouchSlop();
-        mTouchSlopSquare = slop * slop;
-        slop = configuration.getScaledDoubleTapSlop();
-        mDoubleTapSlopSquare = slop * slop;
-        final float density = getContext().getResources().getDisplayMetrics().density;
-        // use one line height, 16 based on our current default font, for how
-        // far we allow a touch be away from the edge of a link
-        mNavSlop = (int) (16 * density);
-        mZoomManager.init(density);
-        mMaximumFling = configuration.getScaledMaximumFlingVelocity();
-
-        // Compute the inverse of the density squared.
-        DRAG_LAYER_INVERSE_DENSITY_SQUARED = 1 / (density * density);
-
-        mOverscrollDistance = configuration.getScaledOverscrollDistance();
-        mOverflingDistance = configuration.getScaledOverflingDistance();
-
-        setScrollBarStyle(super.getScrollBarStyle());
-        // Initially use a size of two, since the user is likely to only hold
-        // down two keys at a time (shift + another key)
-        mKeysPressed = new Vector<Integer>(2);
-        mHTML5VideoViewProxy = null ;
-    }
-
-    @Override
-    public boolean shouldDelayChildPressedState() {
-        return true;
-    }
-
-    /**
-     * Adds accessibility APIs to JavaScript.
-     *
-     * Note: This method is responsible to performing the necessary
-     *       check if the accessibility APIs should be exposed.
-     */
-    private void addAccessibilityApisToJavaScript() {
-        if (AccessibilityManager.getInstance(mContext).isEnabled()
-                && getSettings().getJavaScriptEnabled()) {
-            // exposing the TTS for now ...
-            final Context ctx = getContext();
-            if (ctx != null) {
-                final String packageName = ctx.getPackageName();
-                if (packageName != null) {
-                    mTextToSpeech = new TextToSpeech(getContext(), null, null,
-                            packageName + ".**webview**", true);
-                    addJavascriptInterface(mTextToSpeech, ALIAS_ACCESSIBILITY_JS_INTERFACE);
-                }
-            }
-        }
-    }
-
-    /**
-     * Removes accessibility APIs from JavaScript.
-     */
-    private void removeAccessibilityApisFromJavaScript() {
-        // exposing the TTS for now ...
-        if (mTextToSpeech != null) {
-            removeJavascriptInterface(ALIAS_ACCESSIBILITY_JS_INTERFACE);
-            mTextToSpeech.shutdown();
-            mTextToSpeech = null;
-        }
-    }
-
-    @Override
-    public void onInitializeAccessibilityNodeInfo(AccessibilityNodeInfo info) {
-        super.onInitializeAccessibilityNodeInfo(info);
-        info.setScrollable(isScrollableForAccessibility());
-    }
-
-    @Override
-    public void onInitializeAccessibilityEvent(AccessibilityEvent event) {
-        super.onInitializeAccessibilityEvent(event);
-        event.setScrollable(isScrollableForAccessibility());
-        event.setScrollX(mScrollX);
-        event.setScrollY(mScrollY);
-        final int convertedContentWidth = contentToViewX(getContentWidth());
-        final int adjustedViewWidth = getWidth() - mPaddingLeft - mPaddingRight;
-        event.setMaxScrollX(Math.max(convertedContentWidth - adjustedViewWidth, 0));
-        final int convertedContentHeight = contentToViewY(getContentHeight());
-        final int adjustedViewHeight = getHeight() - mPaddingTop - mPaddingBottom;
-        event.setMaxScrollY(Math.max(convertedContentHeight - adjustedViewHeight, 0));
-    }
-
-    private boolean isScrollableForAccessibility() {
-        return (contentToViewX(getContentWidth()) > getWidth() - mPaddingLeft - mPaddingRight
-                || contentToViewY(getContentHeight()) > getHeight() - mPaddingTop - mPaddingBottom);
-    }
-
-    @Override
-    public void setOverScrollMode(int mode) {
-        super.setOverScrollMode(mode);
-        if (mode != OVER_SCROLL_NEVER) {
-            if (mOverScrollGlow == null) {
-                mOverScrollGlow = new OverScrollGlow(this);
-            }
-        } else {
-            mOverScrollGlow = null;
-        }
-    }
-
-    /* package */ void adjustDefaultZoomDensity(int zoomDensity) {
-        final float density = mContext.getResources().getDisplayMetrics().density
-                * 100 / zoomDensity;
-        updateDefaultZoomDensity(density);
-    }
-
-    /* package */ void updateDefaultZoomDensity(float density) {
-        mNavSlop = (int) (16 * density);
-        mZoomManager.updateDefaultZoomDensity(density);
-    }
-
-    /* package */ boolean onSavePassword(String schemePlusHost, String username,
-            String password, final Message resumeMsg) {
-       boolean rVal = false;
-       if (resumeMsg == null) {
-           // null resumeMsg implies saving password silently
-           mDatabase.setUsernamePassword(schemePlusHost, username, password);
-       } else {
-            final Message remember = mPrivateHandler.obtainMessage(
-                    REMEMBER_PASSWORD);
-            remember.getData().putString("host", schemePlusHost);
-            remember.getData().putString("username", username);
-            remember.getData().putString("password", password);
-            remember.obj = resumeMsg;
-
-            final Message neverRemember = mPrivateHandler.obtainMessage(
-                    NEVER_REMEMBER_PASSWORD);
-            neverRemember.getData().putString("host", schemePlusHost);
-            neverRemember.getData().putString("username", username);
-            neverRemember.getData().putString("password", password);
-            neverRemember.obj = resumeMsg;
-
-            new AlertDialog.Builder(getContext())
-                    .setTitle(com.android.internal.R.string.save_password_label)
-                    .setMessage(com.android.internal.R.string.save_password_message)
-                    .setPositiveButton(com.android.internal.R.string.save_password_notnow,
-                    new DialogInterface.OnClickListener() {
-                        @Override
-                        public void onClick(DialogInterface dialog, int which) {
-                            resumeMsg.sendToTarget();
-                        }
-                    })
-                    .setNeutralButton(com.android.internal.R.string.save_password_remember,
-                    new DialogInterface.OnClickListener() {
-                        @Override
-                        public void onClick(DialogInterface dialog, int which) {
-                            remember.sendToTarget();
-                        }
-                    })
-                    .setNegativeButton(com.android.internal.R.string.save_password_never,
-                    new DialogInterface.OnClickListener() {
-                        @Override
-                        public void onClick(DialogInterface dialog, int which) {
-                            neverRemember.sendToTarget();
-                        }
-                    })
-                    .setOnCancelListener(new OnCancelListener() {
-                        @Override
-                        public void onCancel(DialogInterface dialog) {
-                            resumeMsg.sendToTarget();
-                        }
-                    }).show();
-            // Return true so that WebViewCore will pause while the dialog is
-            // up.
-            rVal = true;
-        }
-       return rVal;
-    }
-
-    @Override
-    public void setScrollBarStyle(int style) {
-        if (style == View.SCROLLBARS_INSIDE_INSET
-                || style == View.SCROLLBARS_OUTSIDE_INSET) {
-            mOverlayHorizontalScrollbar = mOverlayVerticalScrollbar = false;
-        } else {
-            mOverlayHorizontalScrollbar = mOverlayVerticalScrollbar = true;
-        }
-        super.setScrollBarStyle(style);
+        ensureProviderCreated();
+        mProvider.init(javaScriptInterfaces, privateBrowsing);
     }
 
     /**
@@ -1949,7 +488,7 @@
      */
     public void setHorizontalScrollbarOverlay(boolean overlay) {
         checkThread();
-        mOverlayHorizontalScrollbar = overlay;
+        mProvider.setHorizontalScrollbarOverlay(overlay);
     }
 
     /**
@@ -1958,7 +497,7 @@
      */
     public void setVerticalScrollbarOverlay(boolean overlay) {
         checkThread();
-        mOverlayVerticalScrollbar = overlay;
+        mProvider.setVerticalScrollbarOverlay(overlay);
     }
 
     /**
@@ -1967,7 +506,7 @@
      */
     public boolean overlayHorizontalScrollbar() {
         checkThread();
-        return mOverlayHorizontalScrollbar;
+        return mProvider.overlayHorizontalScrollbar();
     }
 
     /**
@@ -1976,80 +515,17 @@
      */
     public boolean overlayVerticalScrollbar() {
         checkThread();
-        return mOverlayVerticalScrollbar;
-    }
-
-    /*
-     * Return the width of the view where the content of WebView should render
-     * to.
-     * Note: this can be called from WebCoreThread.
-     */
-    /* package */ int getViewWidth() {
-        if (!isVerticalScrollBarEnabled() || mOverlayVerticalScrollbar) {
-            return getWidth();
-        } else {
-            return Math.max(0, getWidth() - getVerticalScrollbarWidth());
-        }
-    }
-
-    /**
-     * Returns the height (in pixels) of the embedded title bar (if any). Does not care about
-     * scrolling
-     * @hide
-     */
-    protected int getTitleHeight() {
-        return mTitleBar != null ? mTitleBar.getHeight() : 0;
+        return mProvider.overlayVerticalScrollbar();
     }
 
     /**
      * Return the visible height (in pixels) of the embedded title bar (if any).
      *
-     * @return This method is obsolete and always returns 0.
      * @deprecated This method is now obsolete.
      */
-    @Deprecated
     public int getVisibleTitleHeight() {
-        // Actually, this method returns the height of the embedded title bar if one is set via the
-        // hidden setEmbeddedTitleBar method.
         checkThread();
-        return getVisibleTitleHeightImpl();
-    }
-
-    private int getVisibleTitleHeightImpl() {
-        // need to restrict mScrollY due to over scroll
-        return Math.max(getTitleHeight() - Math.max(0, mScrollY),
-                getOverlappingActionModeHeight());
-    }
-
-    private int mCachedOverlappingActionModeHeight = -1;
-
-    private int getOverlappingActionModeHeight() {
-        if (mFindCallback == null) {
-            return 0;
-        }
-        if (mCachedOverlappingActionModeHeight < 0) {
-            getGlobalVisibleRect(mGlobalVisibleRect, mGlobalVisibleOffset);
-            mCachedOverlappingActionModeHeight = Math.max(0,
-                    mFindCallback.getActionModeGlobalBottom() - mGlobalVisibleRect.top);
-        }
-        return mCachedOverlappingActionModeHeight;
-    }
-
-    /*
-     * Return the height of the view where the content of WebView should render
-     * to.  Note that this excludes mTitleBar, if there is one.
-     * Note: this can be called from WebCoreThread.
-     */
-    /* package */ int getViewHeight() {
-        return getViewHeightWithTitle() - getVisibleTitleHeightImpl();
-    }
-
-    int getViewHeightWithTitle() {
-        int height = getHeight();
-        if (isHorizontalScrollBarEnabled() && !mOverlayHorizontalScrollbar) {
-            height -= getHorizontalScrollbarHeight();
-        }
-        return height;
+        return mProvider.getVisibleTitleHeight();
     }
 
     /**
@@ -2058,7 +534,7 @@
      */
     public SslCertificate getCertificate() {
         checkThread();
-        return mCertificate;
+        return mProvider.getCertificate();
     }
 
     /**
@@ -2066,11 +542,7 @@
      */
     public void setCertificate(SslCertificate certificate) {
         checkThread();
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "setCertificate=" + certificate);
-        }
-        // here, the certificate can be null (if the site is not secure)
-        mCertificate = certificate;
+        mProvider.setCertificate(certificate);
     }
 
     //-------------------------------------------------------------------------
@@ -2086,7 +558,7 @@
      */
     public void savePassword(String host, String username, String password) {
         checkThread();
-        mDatabase.setUsernamePassword(host, username, password);
+        mProvider.savePassword(host, username, password);
     }
 
     /**
@@ -2101,7 +573,7 @@
     public void setHttpAuthUsernamePassword(String host, String realm,
             String username, String password) {
         checkThread();
-        mDatabase.setHttpAuthUsernamePassword(host, realm, username, password);
+        mProvider.setHttpAuthUsernamePassword(host, realm, username, password);
     }
 
     /**
@@ -2115,38 +587,7 @@
      */
     public String[] getHttpAuthUsernamePassword(String host, String realm) {
         checkThread();
-        return mDatabase.getHttpAuthUsernamePassword(host, realm);
-    }
-
-    /**
-     * Remove Find or Select ActionModes, if active.
-     */
-    private void clearActionModes() {
-        if (mSelectCallback != null) {
-            mSelectCallback.finish();
-        }
-        if (mFindCallback != null) {
-            mFindCallback.finish();
-        }
-    }
-
-    /**
-     * Called to clear state when moving from one page to another, or changing
-     * in some other way that makes elements associated with the current page
-     * (such as WebTextView or ActionModes) no longer relevant.
-     */
-    private void clearHelpers() {
-        clearTextEntry();
-        clearActionModes();
-        dismissFullScreenMode();
-        cancelSelectDialog();
-    }
-
-    private void cancelSelectDialog() {
-        if (mListBoxDialog != null) {
-            mListBoxDialog.cancel();
-            mListBoxDialog = null;
-        }
+        return mProvider.getHttpAuthUsernamePassword(host, realm);
     }
 
     /**
@@ -2156,45 +597,7 @@
      */
     public void destroy() {
         checkThread();
-        destroyImpl();
-    }
-
-    private void destroyImpl() {
-        clearHelpers();
-        if (mListBoxDialog != null) {
-            mListBoxDialog.dismiss();
-            mListBoxDialog = null;
-        }
-        // remove so that it doesn't cause events
-        if (mWebTextView != null) {
-            mWebTextView.remove();
-            mWebTextView = null;
-        }
-        if (mNativeClass != 0) nativeStopGL();
-        if (mWebViewCore != null) {
-            // Set the handlers to null before destroying WebViewCore so no
-            // more messages will be posted.
-            mCallbackProxy.setWebViewClient(null);
-            mCallbackProxy.setWebChromeClient(null);
-            // Tell WebViewCore to destroy itself
-            synchronized (this) {
-                WebViewCore webViewCore = mWebViewCore;
-                mWebViewCore = null; // prevent using partial webViewCore
-                webViewCore.destroy();
-            }
-            // Remove any pending messages that might not be serviced yet.
-            mPrivateHandler.removeCallbacksAndMessages(null);
-            mCallbackProxy.removeCallbacksAndMessages(null);
-            // Wake up the WebCore thread just in case it is waiting for a
-            // JavaScript dialog.
-            synchronized (mCallbackProxy) {
-                mCallbackProxy.notify();
-            }
-        }
-        if (mNativeClass != 0) {
-            nativeDestroy();
-            mNativeClass = 0;
-        }
+        mProvider.destroy();
     }
 
     /**
@@ -2206,12 +609,7 @@
     @Deprecated
     public static void enablePlatformNotifications() {
         checkThread();
-        synchronized (WebView.class) {
-            sNotificationsEnabled = true;
-            Context context = JniUtil.getContext();
-            if (context != null)
-                setupProxyListener(context);
-        }
+        getFactory().getStatics().setPlatformNotificationsEnabled(true);
     }
 
     /**
@@ -2223,24 +621,7 @@
     @Deprecated
     public static void disablePlatformNotifications() {
         checkThread();
-        synchronized (WebView.class) {
-            sNotificationsEnabled = false;
-            Context context = JniUtil.getContext();
-            if (context != null)
-                disableProxyListener(context);
-        }
-    }
-
-    /**
-     * Sets JavaScript engine flags.
-     *
-     * @param flags JS engine flags in a String
-     *
-     * @hide This is an implementation detail.
-     */
-    public void setJsFlags(String flags) {
-        checkThread();
-        mWebViewCore.sendMessage(EventHub.SET_JS_FLAGS, flags);
+        getFactory().getStatics().setPlatformNotificationsEnabled(false);
     }
 
     /**
@@ -2251,22 +632,10 @@
      */
     public void setNetworkAvailable(boolean networkUp) {
         checkThread();
-        mWebViewCore.sendMessage(EventHub.SET_NETWORK_STATE,
-                networkUp ? 1 : 0, 0);
+        mProvider.setNetworkAvailable(networkUp);
     }
 
     /**
-     * Inform WebView about the current network type.
-     * {@hide}
-     */
-    public void setNetworkType(String type, String subtype) {
-        checkThread();
-        Map<String, String> map = new HashMap<String, String>();
-        map.put("type", type);
-        map.put("subtype", subtype);
-        mWebViewCore.sendMessage(EventHub.SET_NETWORK_TYPE, map);
-    }
-    /**
      * Save the state of this WebView used in
      * {@link android.app.Activity#onSaveInstanceState}. Please note that this
      * method no longer stores the display data for this WebView. The previous
@@ -2281,49 +650,7 @@
      */
     public WebBackForwardList saveState(Bundle outState) {
         checkThread();
-        if (outState == null) {
-            return null;
-        }
-        // We grab a copy of the back/forward list because a client of WebView
-        // may have invalidated the history list by calling clearHistory.
-        WebBackForwardList list = copyBackForwardList();
-        final int currentIndex = list.getCurrentIndex();
-        final int size = list.getSize();
-        // We should fail saving the state if the list is empty or the index is
-        // not in a valid range.
-        if (currentIndex < 0 || currentIndex >= size || size == 0) {
-            return null;
-        }
-        outState.putInt("index", currentIndex);
-        // FIXME: This should just be a byte[][] instead of ArrayList but
-        // Parcel.java does not have the code to handle multi-dimensional
-        // arrays.
-        ArrayList<byte[]> history = new ArrayList<byte[]>(size);
-        for (int i = 0; i < size; i++) {
-            WebHistoryItem item = list.getItemAtIndex(i);
-            if (null == item) {
-                // FIXME: this shouldn't happen
-                // need to determine how item got set to null
-                Log.w(LOGTAG, "saveState: Unexpected null history item.");
-                return null;
-            }
-            byte[] data = item.getFlattenedData();
-            if (data == null) {
-                // It would be very odd to not have any data for a given history
-                // item. And we will fail to rebuild the history list without
-                // flattened data.
-                return null;
-            }
-            history.add(data);
-        }
-        outState.putSerializable("history", history);
-        if (mCertificate != null) {
-            outState.putBundle("certificate",
-                               SslCertificate.saveState(mCertificate));
-        }
-        outState.putBoolean("privateBrowsingEnabled", isPrivateBrowsingEnabled());
-        mZoomManager.saveZoomState(outState);
-        return list;
+        return mProvider.saveState(outState);
     }
 
     /**
@@ -2338,59 +665,7 @@
     @Deprecated
     public boolean savePicture(Bundle b, final File dest) {
         checkThread();
-        if (dest == null || b == null) {
-            return false;
-        }
-        final Picture p = capturePicture();
-        // Use a temporary file while writing to ensure the destination file
-        // contains valid data.
-        final File temp = new File(dest.getPath() + ".writing");
-        new Thread(new Runnable() {
-            @Override
-            public void run() {
-                FileOutputStream out = null;
-                try {
-                    out = new FileOutputStream(temp);
-                    p.writeToStream(out);
-                    // Writing the picture succeeded, rename the temporary file
-                    // to the destination.
-                    temp.renameTo(dest);
-                } catch (Exception e) {
-                    // too late to do anything about it.
-                } finally {
-                    if (out != null) {
-                        try {
-                            out.close();
-                        } catch (Exception e) {
-                            // Can't do anything about that
-                        }
-                    }
-                    temp.delete();
-                }
-            }
-        }).start();
-        // now update the bundle
-        b.putInt("scrollX", mScrollX);
-        b.putInt("scrollY", mScrollY);
-        mZoomManager.saveZoomState(b);
-        return true;
-    }
-
-    private void restoreHistoryPictureFields(Picture p, Bundle b) {
-        int sx = b.getInt("scrollX", 0);
-        int sy = b.getInt("scrollY", 0);
-
-        mDrawHistory = true;
-        mHistoryPicture = p;
-
-        mScrollX = sx;
-        mScrollY = sy;
-        mZoomManager.restoreZoomState(b);
-        final float scale = mZoomManager.getScale();
-        mHistoryWidth = Math.round(p.getWidth() * scale);
-        mHistoryHeight = Math.round(p.getHeight() * scale);
-
-        invalidate();
+        return mProvider.savePicture(b, dest);
     }
 
     /**
@@ -2406,91 +681,7 @@
     @Deprecated
     public boolean restorePicture(Bundle b, File src) {
         checkThread();
-        if (src == null || b == null) {
-            return false;
-        }
-        if (!src.exists()) {
-            return false;
-        }
-        try {
-            final FileInputStream in = new FileInputStream(src);
-            final Bundle copy = new Bundle(b);
-            new Thread(new Runnable() {
-                @Override
-                public void run() {
-                    try {
-                        final Picture p = Picture.createFromStream(in);
-                        if (p != null) {
-                            // Post a runnable on the main thread to update the
-                            // history picture fields.
-                            mPrivateHandler.post(new Runnable() {
-                                @Override
-                                public void run() {
-                                    restoreHistoryPictureFields(p, copy);
-                                }
-                            });
-                        }
-                    } finally {
-                        try {
-                            in.close();
-                        } catch (Exception e) {
-                            // Nothing we can do now.
-                        }
-                    }
-                }
-            }).start();
-        } catch (FileNotFoundException e){
-            e.printStackTrace();
-        }
-        return true;
-    }
-
-    /**
-     * Saves the view data to the output stream. The output is highly
-     * version specific, and may not be able to be loaded by newer versions
-     * of WebView.
-     * @param stream The {@link OutputStream} to save to
-     * @return True if saved successfully
-     * @hide
-     */
-    public boolean saveViewState(OutputStream stream) {
-        try {
-            return ViewStateSerializer.serializeViewState(stream, this);
-        } catch (IOException e) {
-            Log.w(LOGTAG, "Failed to saveViewState", e);
-        }
-        return false;
-    }
-
-    /**
-     * Loads the view data from the input stream. See
-     * {@link #saveViewState(OutputStream)} for more information.
-     * @param stream The {@link InputStream} to load from
-     * @return True if loaded successfully
-     * @hide
-     */
-    public boolean loadViewState(InputStream stream) {
-        try {
-            mLoadedPicture = ViewStateSerializer.deserializeViewState(stream, this);
-            mBlockWebkitViewMessages = true;
-            setNewPicture(mLoadedPicture, true);
-            mLoadedPicture.mViewState = null;
-            return true;
-        } catch (IOException e) {
-            Log.w(LOGTAG, "Failed to loadViewState", e);
-        }
-        return false;
-    }
-
-    /**
-     * Clears the view state set with {@link #loadViewState(InputStream)}.
-     * This WebView will then switch to showing the content from webkit
-     * @hide
-     */
-    public void clearViewState() {
-        mBlockWebkitViewMessages = false;
-        mLoadedPicture = null;
-        invalidate();
+        return mProvider.restorePicture(b, src);
     }
 
     /**
@@ -2509,55 +700,7 @@
      */
     public WebBackForwardList restoreState(Bundle inState) {
         checkThread();
-        WebBackForwardList returnList = null;
-        if (inState == null) {
-            return returnList;
-        }
-        if (inState.containsKey("index") && inState.containsKey("history")) {
-            mCertificate = SslCertificate.restoreState(
-                inState.getBundle("certificate"));
-
-            final WebBackForwardList list = mCallbackProxy.getBackForwardList();
-            final int index = inState.getInt("index");
-            // We can't use a clone of the list because we need to modify the
-            // shared copy, so synchronize instead to prevent concurrent
-            // modifications.
-            synchronized (list) {
-                final List<byte[]> history =
-                        (List<byte[]>) inState.getSerializable("history");
-                final int size = history.size();
-                // Check the index bounds so we don't crash in native code while
-                // restoring the history index.
-                if (index < 0 || index >= size) {
-                    return null;
-                }
-                for (int i = 0; i < size; i++) {
-                    byte[] data = history.remove(0);
-                    if (data == null) {
-                        // If we somehow have null data, we cannot reconstruct
-                        // the item and thus our history list cannot be rebuilt.
-                        return null;
-                    }
-                    WebHistoryItem item = new WebHistoryItem(data);
-                    list.addHistoryItem(item);
-                }
-                // Grab the most recent copy to return to the caller.
-                returnList = copyBackForwardList();
-                // Update the copy to have the correct index.
-                returnList.setCurrentIndex(index);
-            }
-            // Restore private browsing setting.
-            if (inState.getBoolean("privateBrowsingEnabled")) {
-                getSettings().setPrivateBrowsingEnabled(true);
-            }
-            mZoomManager.restoreZoomState(inState);
-            // Remove all pending messages because we are restoring previous
-            // state.
-            mWebViewCore.removeMessages();
-            // Send a restore state message.
-            mWebViewCore.sendMessage(EventHub.RESTORE_STATE, index);
-        }
-        return returnList;
+        return mProvider.restoreState(inState);
     }
 
     /**
@@ -2572,16 +715,7 @@
      */
     public void loadUrl(String url, Map<String, String> additionalHttpHeaders) {
         checkThread();
-        loadUrlImpl(url, additionalHttpHeaders);
-    }
-
-    private void loadUrlImpl(String url, Map<String, String> extraHeaders) {
-        switchOutDrawHistory();
-        WebViewCore.GetUrlData arg = new WebViewCore.GetUrlData();
-        arg.mUrl = url;
-        arg.mExtraHeaders = extraHeaders;
-        mWebViewCore.sendMessage(EventHub.LOAD_URL, arg);
-        clearHelpers();
+        mProvider.loadUrl(url, additionalHttpHeaders);
     }
 
     /**
@@ -2590,14 +724,7 @@
      */
     public void loadUrl(String url) {
         checkThread();
-        loadUrlImpl(url);
-    }
-
-    private void loadUrlImpl(String url) {
-        if (url == null) {
-            return;
-        }
-        loadUrlImpl(url, null);
+        mProvider.loadUrl(url);
     }
 
     /**
@@ -2610,16 +737,7 @@
      */
     public void postUrl(String url, byte[] postData) {
         checkThread();
-        if (URLUtil.isNetworkUrl(url)) {
-            switchOutDrawHistory();
-            WebViewCore.PostUrlData arg = new WebViewCore.PostUrlData();
-            arg.mUrl = url;
-            arg.mPostData = postData;
-            mWebViewCore.sendMessage(EventHub.POST_URL, arg);
-            clearHelpers();
-        } else {
-            loadUrlImpl(url);
-        }
+        mProvider.postUrl(url, postData);
     }
 
     /**
@@ -2650,18 +768,7 @@
      */
     public void loadData(String data, String mimeType, String encoding) {
         checkThread();
-        loadDataImpl(data, mimeType, encoding);
-    }
-
-    private void loadDataImpl(String data, String mimeType, String encoding) {
-        StringBuilder dataUrl = new StringBuilder("data:");
-        dataUrl.append(mimeType);
-        if ("base64".equals(encoding)) {
-            dataUrl.append(";base64");
-        }
-        dataUrl.append(",");
-        dataUrl.append(data);
-        loadUrlImpl(dataUrl.toString());
+        mProvider.loadData(data, mimeType, encoding);
     }
 
     /**
@@ -2689,20 +796,7 @@
     public void loadDataWithBaseURL(String baseUrl, String data,
             String mimeType, String encoding, String historyUrl) {
         checkThread();
-
-        if (baseUrl != null && baseUrl.toLowerCase().startsWith("data:")) {
-            loadDataImpl(data, mimeType, encoding);
-            return;
-        }
-        switchOutDrawHistory();
-        WebViewCore.BaseUrlData arg = new WebViewCore.BaseUrlData();
-        arg.mBaseUrl = baseUrl;
-        arg.mData = data;
-        arg.mMimeType = mimeType;
-        arg.mEncoding = encoding;
-        arg.mHistoryUrl = historyUrl;
-        mWebViewCore.sendMessage(EventHub.LOAD_DATA, arg);
-        clearHelpers();
+        mProvider.loadDataWithBaseURL(baseUrl, data, mimeType, encoding, historyUrl);
     }
 
     /**
@@ -2712,20 +806,7 @@
      */
     public void saveWebArchive(String filename) {
         checkThread();
-        saveWebArchiveImpl(filename, false, null);
-    }
-
-    /* package */ static class SaveWebArchiveMessage {
-        SaveWebArchiveMessage (String basename, boolean autoname, ValueCallback<String> callback) {
-            mBasename = basename;
-            mAutoname = autoname;
-            mCallback = callback;
-        }
-
-        /* package */ final String mBasename;
-        /* package */ final boolean mAutoname;
-        /* package */ final ValueCallback<String> mCallback;
-        /* package */ String mResultFile;
+        mProvider.saveWebArchive(filename);
     }
 
     /**
@@ -2742,13 +823,7 @@
      */
     public void saveWebArchive(String basename, boolean autoname, ValueCallback<String> callback) {
         checkThread();
-        saveWebArchiveImpl(basename, autoname, callback);
-    }
-
-    private void saveWebArchiveImpl(String basename, boolean autoname,
-            ValueCallback<String> callback) {
-        mWebViewCore.sendMessage(EventHub.SAVE_WEBARCHIVE,
-            new SaveWebArchiveMessage(basename, autoname, callback));
+        mProvider.saveWebArchive(basename, autoname, callback);
     }
 
     /**
@@ -2756,10 +831,7 @@
      */
     public void stopLoading() {
         checkThread();
-        // TODO: should we clear all the messages in the queue before sending
-        // STOP_LOADING?
-        switchOutDrawHistory();
-        mWebViewCore.sendMessage(EventHub.STOP_LOADING);
+        mProvider.stopLoading();
     }
 
     /**
@@ -2767,9 +839,7 @@
      */
     public void reload() {
         checkThread();
-        clearHelpers();
-        switchOutDrawHistory();
-        mWebViewCore.sendMessage(EventHub.RELOAD);
+        mProvider.reload();
     }
 
     /**
@@ -2778,14 +848,7 @@
      */
     public boolean canGoBack() {
         checkThread();
-        WebBackForwardList l = mCallbackProxy.getBackForwardList();
-        synchronized (l) {
-            if (l.getClearPending()) {
-                return false;
-            } else {
-                return l.getCurrentIndex() > 0;
-            }
-        }
+        return mProvider.canGoBack();
     }
 
     /**
@@ -2793,7 +856,7 @@
      */
     public void goBack() {
         checkThread();
-        goBackOrForwardImpl(-1);
+        mProvider.goBack();
     }
 
     /**
@@ -2802,14 +865,7 @@
      */
     public boolean canGoForward() {
         checkThread();
-        WebBackForwardList l = mCallbackProxy.getBackForwardList();
-        synchronized (l) {
-            if (l.getClearPending()) {
-                return false;
-            } else {
-                return l.getCurrentIndex() < l.getSize() - 1;
-            }
-        }
+        return mProvider.canGoForward();
     }
 
     /**
@@ -2817,7 +873,7 @@
      */
     public void goForward() {
         checkThread();
-        goBackOrForwardImpl(1);
+        mProvider.goForward();
     }
 
     /**
@@ -2828,15 +884,7 @@
      */
     public boolean canGoBackOrForward(int steps) {
         checkThread();
-        WebBackForwardList l = mCallbackProxy.getBackForwardList();
-        synchronized (l) {
-            if (l.getClearPending()) {
-                return false;
-            } else {
-                int newIndex = l.getCurrentIndex() + steps;
-                return newIndex >= 0 && newIndex < l.getSize();
-            }
-        }
+        return mProvider.canGoBackOrForward(steps);
     }
 
     /**
@@ -2848,19 +896,7 @@
      */
     public void goBackOrForward(int steps) {
         checkThread();
-        goBackOrForwardImpl(steps);
-    }
-
-    private void goBackOrForwardImpl(int steps) {
-        goBackOrForward(steps, false);
-    }
-
-    private void goBackOrForward(int steps, boolean ignoreSnapshot) {
-        if (steps != 0) {
-            clearHelpers();
-            mWebViewCore.sendMessage(EventHub.GO_BACK_FORWARD, steps,
-                    ignoreSnapshot ? 1 : 0);
-        }
+        mProvider.goBackOrForward(steps);
     }
 
     /**
@@ -2868,20 +904,7 @@
      */
     public boolean isPrivateBrowsingEnabled() {
         checkThread();
-        return getSettings().isPrivateBrowsingEnabled();
-    }
-
-    private void startPrivateBrowsing() {
-        getSettings().setPrivateBrowsingEnabled(true);
-    }
-
-    private boolean extendScroll(int y) {
-        int finalY = mScroller.getFinalY();
-        int newY = pinLocY(finalY + y);
-        if (newY == finalY) return false;
-        mScroller.setFinalY(newY);
-        mScroller.extendDuration(computeDuration(0, y));
-        return true;
+        return mProvider.isPrivateBrowsingEnabled();
     }
 
     /**
@@ -2891,24 +914,7 @@
      */
     public boolean pageUp(boolean top) {
         checkThread();
-        if (mNativeClass == 0) {
-            return false;
-        }
-        nativeClearCursor(); // start next trackball movement from page edge
-        if (top) {
-            // go to the top of the document
-            return pinScrollTo(mScrollX, 0, true, 0);
-        }
-        // Page up
-        int h = getHeight();
-        int y;
-        if (h > 2 * PAGE_SCROLL_OVERLAP) {
-            y = -h + PAGE_SCROLL_OVERLAP;
-        } else {
-            y = -h / 2;
-        }
-        return mScroller.isFinished() ? pinScrollBy(0, y, true, 0)
-                : extendScroll(y);
+        return mProvider.pageUp(top);
     }
 
     /**
@@ -2918,23 +924,7 @@
      */
     public boolean pageDown(boolean bottom) {
         checkThread();
-        if (mNativeClass == 0) {
-            return false;
-        }
-        nativeClearCursor(); // start next trackball movement from page edge
-        if (bottom) {
-            return pinScrollTo(mScrollX, computeRealVerticalScrollRange(), true, 0);
-        }
-        // Page down.
-        int h = getHeight();
-        int y;
-        if (h > 2 * PAGE_SCROLL_OVERLAP) {
-            y = h - PAGE_SCROLL_OVERLAP;
-        } else {
-            y = h / 2;
-        }
-        return mScroller.isFinished() ? pinScrollBy(0, y, true, 0)
-                : extendScroll(y);
+        return mProvider.pageDown(bottom);
     }
 
     /**
@@ -2943,10 +933,7 @@
      */
     public void clearView() {
         checkThread();
-        mContentWidth = 0;
-        mContentHeight = 0;
-        setBaseLayer(0, null, false, false);
-        mWebViewCore.sendMessage(EventHub.CLEAR_CONTENT);
+        mProvider.clearView();
     }
 
     /**
@@ -2960,29 +947,7 @@
      */
     public Picture capturePicture() {
         checkThread();
-        if (mNativeClass == 0) return null;
-        Picture result = new Picture();
-        nativeCopyBaseContentToPicture(result);
-        return result;
-    }
-
-    /**
-     *  Return true if the browser is displaying a TextView for text input.
-     */
-    private boolean inEditingMode() {
-        return mWebTextView != null && mWebTextView.getParent() != null;
-    }
-
-    /**
-     * Remove the WebTextView.
-     */
-    private void clearTextEntry() {
-        if (inEditingMode()) {
-            mWebTextView.remove();
-        } else {
-            // The keyboard may be open with the WebView as the served view
-            hideSoftKeyboard();
-        }
+        return mProvider.capturePicture();
     }
 
     /**
@@ -2991,16 +956,7 @@
      */
     public float getScale() {
         checkThread();
-        return mZoomManager.getScale();
-    }
-
-    /**
-     * Compute the reading level scale of the WebView
-     * @param scale The current scale.
-     * @return The reading level scale.
-     */
-    /*package*/ float computeReadingLevelScale(float scale) {
-        return mZoomManager.computeReadingLevelScale(scale);
+        return mProvider.getScale();
     }
 
     /**
@@ -3015,7 +971,7 @@
      */
     public void setInitialScale(int scaleInPercent) {
         checkThread();
-        mZoomManager.setInitialScaleInPercent(scaleInPercent);
+        mProvider.setInitialScale(scaleInPercent);
     }
 
     /**
@@ -3025,12 +981,7 @@
      */
     public void invokeZoomPicker() {
         checkThread();
-        if (!getSettings().supportZoom()) {
-            Log.w(LOGTAG, "This WebView doesn't support zoom.");
-            return;
-        }
-        clearHelpers();
-        mZoomManager.invokeZoomPicker();
+        mProvider.invokeZoomPicker();
     }
 
     /**
@@ -3053,101 +1004,9 @@
      */
     public HitTestResult getHitTestResult() {
         checkThread();
-        return hitTestResult(mInitialHitTestResult);
+        return mProvider.getHitTestResult();
     }
 
-    private HitTestResult hitTestResult(HitTestResult fallback) {
-        if (mNativeClass == 0 || sDisableNavcache) {
-            return fallback;
-        }
-
-        HitTestResult result = new HitTestResult();
-        if (nativeHasCursorNode()) {
-            if (nativeCursorIsTextInput()) {
-                result.setType(HitTestResult.EDIT_TEXT_TYPE);
-            } else {
-                String text = nativeCursorText();
-                if (text != null) {
-                    if (text.startsWith(SCHEME_TEL)) {
-                        result.setType(HitTestResult.PHONE_TYPE);
-                        result.setExtra(URLDecoder.decode(text
-                                .substring(SCHEME_TEL.length())));
-                    } else if (text.startsWith(SCHEME_MAILTO)) {
-                        result.setType(HitTestResult.EMAIL_TYPE);
-                        result.setExtra(text.substring(SCHEME_MAILTO.length()));
-                    } else if (text.startsWith(SCHEME_GEO)) {
-                        result.setType(HitTestResult.GEO_TYPE);
-                        result.setExtra(URLDecoder.decode(text
-                                .substring(SCHEME_GEO.length())));
-                    } else if (nativeCursorIsAnchor()) {
-                        result.setType(HitTestResult.SRC_ANCHOR_TYPE);
-                        result.setExtra(text);
-                    }
-                }
-            }
-        } else if (fallback != null) {
-            /* If webkit causes a rebuild while the long press is in progress,
-             * the cursor node may be reset, even if it is still around. This
-             * uses the cursor node saved when the touch began. Since the
-             * nativeImageURI below only changes the result if it is successful,
-             * this uses the data beneath the touch if available or the original
-             * tap data otherwise.
-             */
-            Log.v(LOGTAG, "hitTestResult use fallback");
-            result = fallback;
-        }
-        int type = result.getType();
-        if (type == HitTestResult.UNKNOWN_TYPE
-                || type == HitTestResult.SRC_ANCHOR_TYPE) {
-            // Now check to see if it is an image.
-            int contentX = viewToContentX(mLastTouchX + mScrollX);
-            int contentY = viewToContentY(mLastTouchY + mScrollY);
-            String text = nativeImageURI(contentX, contentY);
-            if (text != null) {
-                result.setType(type == HitTestResult.UNKNOWN_TYPE ?
-                        HitTestResult.IMAGE_TYPE :
-                        HitTestResult.SRC_IMAGE_ANCHOR_TYPE);
-                result.setExtra(text);
-            }
-        }
-        return result;
-    }
-
-    int getBlockLeftEdge(int x, int y, float readingScale) {
-        if (!sDisableNavcache) {
-            return nativeGetBlockLeftEdge(x, y, readingScale);
-        }
-
-        float invReadingScale = 1.0f / readingScale;
-        int readingWidth = (int) (getViewWidth() * invReadingScale);
-        int left = NO_LEFTEDGE;
-        if (mFocusedNode != null) {
-            final int length = mFocusedNode.mEnclosingParentRects.length;
-            for (int i = 0; i < length; i++) {
-                Rect rect = mFocusedNode.mEnclosingParentRects[i];
-                if (rect.width() < mFocusedNode.mHitTestSlop) {
-                    // ignore bounding boxes that are too small
-                    continue;
-                } else if (left != NO_LEFTEDGE && rect.width() > readingWidth) {
-                    // stop when bounding box doesn't fit the screen width
-                    // at reading scale
-                    break;
-                }
-
-                left = rect.left;
-            }
-        }
-
-        return left;
-    }
-
-    // Called by JNI when the DOM has changed the focus.  Clear the focus so
-    // that new keys will go to the newly focused field
-    private void domChangedFocus() {
-        if (inEditingMode()) {
-            mPrivateHandler.obtainMessage(DOM_FOCUS_CHANGED).sendToTarget();
-        }
-    }
     /**
      * Request the anchor or image element URL at the last tapped point.
      * If hrefMsg is null, this method returns immediately and does not
@@ -3164,32 +1023,7 @@
      */
     public void requestFocusNodeHref(Message hrefMsg) {
         checkThread();
-        if (hrefMsg == null) {
-            return;
-        }
-        int contentX = viewToContentX(mLastTouchX + mScrollX);
-        int contentY = viewToContentY(mLastTouchY + mScrollY);
-        if (mFocusedNode != null && mFocusedNode.mHitTestX == contentX
-                && mFocusedNode.mHitTestY == contentY) {
-            hrefMsg.getData().putString(FocusNodeHref.URL, mFocusedNode.mLinkUrl);
-            hrefMsg.getData().putString(FocusNodeHref.TITLE, mFocusedNode.mAnchorText);
-            hrefMsg.getData().putString(FocusNodeHref.SRC, mFocusedNode.mImageUrl);
-            hrefMsg.sendToTarget();
-            return;
-        }
-        if (nativeHasCursorNode()) {
-            Rect cursorBounds = cursorRingBounds();
-            if (!cursorBounds.contains(contentX, contentY)) {
-                int slop = viewToContentDimension(mNavSlop);
-                cursorBounds.inset(-slop, -slop);
-                if (cursorBounds.contains(contentX, contentY)) {
-                    contentX = cursorBounds.centerX();
-                    contentY = cursorBounds.centerY();
-                }
-            }
-        }
-        mWebViewCore.sendMessage(EventHub.REQUEST_CURSOR_HREF,
-                contentX, contentY, hrefMsg);
+        mProvider.requestFocusNodeHref(hrefMsg);
     }
 
     /**
@@ -3201,503 +1035,7 @@
      */
     public void requestImageRef(Message msg) {
         checkThread();
-        if (0 == mNativeClass) return; // client isn't initialized
-        int contentX = viewToContentX(mLastTouchX + mScrollX);
-        int contentY = viewToContentY(mLastTouchY + mScrollY);
-        String ref = nativeImageURI(contentX, contentY);
-        Bundle data = msg.getData();
-        data.putString("url", ref);
-        msg.setData(data);
-        msg.sendToTarget();
-    }
-
-    static int pinLoc(int x, int viewMax, int docMax) {
-//        Log.d(LOGTAG, "-- pinLoc " + x + " " + viewMax + " " + docMax);
-        if (docMax < viewMax) {   // the doc has room on the sides for "blank"
-            // pin the short document to the top/left of the screen
-            x = 0;
-//            Log.d(LOGTAG, "--- center " + x);
-        } else if (x < 0) {
-            x = 0;
-//            Log.d(LOGTAG, "--- zero");
-        } else if (x + viewMax > docMax) {
-            x = docMax - viewMax;
-//            Log.d(LOGTAG, "--- pin " + x);
-        }
-        return x;
-    }
-
-    // Expects x in view coordinates
-    int pinLocX(int x) {
-        if (mInOverScrollMode) return x;
-        return pinLoc(x, getViewWidth(), computeRealHorizontalScrollRange());
-    }
-
-    // Expects y in view coordinates
-    int pinLocY(int y) {
-        if (mInOverScrollMode) return y;
-        return pinLoc(y, getViewHeightWithTitle(),
-                      computeRealVerticalScrollRange() + getTitleHeight());
-    }
-
-    /**
-     * A title bar which is embedded in this WebView, and scrolls along with it
-     * vertically, but not horizontally.
-     */
-    private View mTitleBar;
-
-    /**
-     * the title bar rendering gravity
-     */
-    private int mTitleGravity;
-
-    /**
-     * Add or remove a title bar to be embedded into the WebView, and scroll
-     * along with it vertically, while remaining in view horizontally. Pass
-     * null to remove the title bar from the WebView, and return to drawing
-     * the WebView normally without translating to account for the title bar.
-     * @hide
-     */
-    public void setEmbeddedTitleBar(View v) {
-        if (mTitleBar == v) return;
-        if (mTitleBar != null) {
-            removeView(mTitleBar);
-        }
-        if (null != v) {
-            addView(v, new AbsoluteLayout.LayoutParams(
-                    ViewGroup.LayoutParams.MATCH_PARENT,
-                    ViewGroup.LayoutParams.WRAP_CONTENT, 0, 0));
-        }
-        mTitleBar = v;
-    }
-
-    /**
-     * Set where to render the embedded title bar
-     * NO_GRAVITY at the top of the page
-     * TOP        at the top of the screen
-     * @hide
-     */
-    public void setTitleBarGravity(int gravity) {
-        mTitleGravity = gravity;
-        // force refresh
-        invalidate();
-    }
-
-    /**
-     * Given a distance in view space, convert it to content space. Note: this
-     * does not reflect translation, just scaling, so this should not be called
-     * with coordinates, but should be called for dimensions like width or
-     * height.
-     */
-    private int viewToContentDimension(int d) {
-        return Math.round(d * mZoomManager.getInvScale());
-    }
-
-    /**
-     * Given an x coordinate in view space, convert it to content space.  Also
-     * may be used for absolute heights (such as for the WebTextView's
-     * textSize, which is unaffected by the height of the title bar).
-     */
-    /*package*/ int viewToContentX(int x) {
-        return viewToContentDimension(x);
-    }
-
-    /**
-     * Given a y coordinate in view space, convert it to content space.
-     * Takes into account the height of the title bar if there is one
-     * embedded into the WebView.
-     */
-    /*package*/ int viewToContentY(int y) {
-        return viewToContentDimension(y - getTitleHeight());
-    }
-
-    /**
-     * Given a x coordinate in view space, convert it to content space.
-     * Returns the result as a float.
-     */
-    private float viewToContentXf(int x) {
-        return x * mZoomManager.getInvScale();
-    }
-
-    /**
-     * Given a y coordinate in view space, convert it to content space.
-     * Takes into account the height of the title bar if there is one
-     * embedded into the WebView. Returns the result as a float.
-     */
-    private float viewToContentYf(int y) {
-        return (y - getTitleHeight()) * mZoomManager.getInvScale();
-    }
-
-    /**
-     * Given a distance in content space, convert it to view space. Note: this
-     * does not reflect translation, just scaling, so this should not be called
-     * with coordinates, but should be called for dimensions like width or
-     * height.
-     */
-    /*package*/ int contentToViewDimension(int d) {
-        return Math.round(d * mZoomManager.getScale());
-    }
-
-    /**
-     * Given an x coordinate in content space, convert it to view
-     * space.
-     */
-    /*package*/ int contentToViewX(int x) {
-        return contentToViewDimension(x);
-    }
-
-    /**
-     * Given a y coordinate in content space, convert it to view
-     * space.  Takes into account the height of the title bar.
-     */
-    /*package*/ int contentToViewY(int y) {
-        return contentToViewDimension(y) + getTitleHeight();
-    }
-
-    private Rect contentToViewRect(Rect x) {
-        return new Rect(contentToViewX(x.left), contentToViewY(x.top),
-                        contentToViewX(x.right), contentToViewY(x.bottom));
-    }
-
-    /*  To invalidate a rectangle in content coordinates, we need to transform
-        the rect into view coordinates, so we can then call invalidate(...).
-
-        Normally, we would just call contentToView[XY](...), which eventually
-        calls Math.round(coordinate * mActualScale). However, for invalidates,
-        we need to account for the slop that occurs with antialiasing. To
-        address that, we are a little more liberal in the size of the rect that
-        we invalidate.
-
-        This liberal calculation calls floor() for the top/left, and ceil() for
-        the bottom/right coordinates. This catches the possible extra pixels of
-        antialiasing that we might have missed with just round().
-     */
-
-    // Called by JNI to invalidate the View, given rectangle coordinates in
-    // content space
-    private void viewInvalidate(int l, int t, int r, int b) {
-        final float scale = mZoomManager.getScale();
-        final int dy = getTitleHeight();
-        invalidate((int)Math.floor(l * scale),
-                   (int)Math.floor(t * scale) + dy,
-                   (int)Math.ceil(r * scale),
-                   (int)Math.ceil(b * scale) + dy);
-    }
-
-    // Called by JNI to invalidate the View after a delay, given rectangle
-    // coordinates in content space
-    private void viewInvalidateDelayed(long delay, int l, int t, int r, int b) {
-        final float scale = mZoomManager.getScale();
-        final int dy = getTitleHeight();
-        postInvalidateDelayed(delay,
-                              (int)Math.floor(l * scale),
-                              (int)Math.floor(t * scale) + dy,
-                              (int)Math.ceil(r * scale),
-                              (int)Math.ceil(b * scale) + dy);
-    }
-
-    private void invalidateContentRect(Rect r) {
-        viewInvalidate(r.left, r.top, r.right, r.bottom);
-    }
-
-    // stop the scroll animation, and don't let a subsequent fling add
-    // to the existing velocity
-    private void abortAnimation() {
-        mScroller.abortAnimation();
-        mLastVelocity = 0;
-    }
-
-    /* call from webcoreview.draw(), so we're still executing in the UI thread
-    */
-    private void recordNewContentSize(int w, int h, boolean updateLayout) {
-
-        // premature data from webkit, ignore
-        if ((w | h) == 0) {
-            return;
-        }
-
-        // don't abort a scroll animation if we didn't change anything
-        if (mContentWidth != w || mContentHeight != h) {
-            // record new dimensions
-            mContentWidth = w;
-            mContentHeight = h;
-            // If history Picture is drawn, don't update scroll. They will be
-            // updated when we get out of that mode.
-            if (!mDrawHistory) {
-                // repin our scroll, taking into account the new content size
-                updateScrollCoordinates(pinLocX(mScrollX), pinLocY(mScrollY));
-                if (!mScroller.isFinished()) {
-                    // We are in the middle of a scroll.  Repin the final scroll
-                    // position.
-                    mScroller.setFinalX(pinLocX(mScroller.getFinalX()));
-                    mScroller.setFinalY(pinLocY(mScroller.getFinalY()));
-                }
-            }
-        }
-        contentSizeChanged(updateLayout);
-    }
-
-    // Used to avoid sending many visible rect messages.
-    private Rect mLastVisibleRectSent = new Rect();
-    private Rect mLastGlobalRect = new Rect();
-    private Rect mVisibleRect = new Rect();
-    private Rect mGlobalVisibleRect = new Rect();
-    private Point mScrollOffset = new Point();
-
-    Rect sendOurVisibleRect() {
-        if (mZoomManager.isPreventingWebkitUpdates()) return mLastVisibleRectSent;
-        calcOurContentVisibleRect(mVisibleRect);
-        // Rect.equals() checks for null input.
-        if (!mVisibleRect.equals(mLastVisibleRectSent)) {
-            if (!mBlockWebkitViewMessages) {
-                mScrollOffset.set(mVisibleRect.left, mVisibleRect.top);
-                mWebViewCore.removeMessages(EventHub.SET_SCROLL_OFFSET);
-                mWebViewCore.sendMessage(EventHub.SET_SCROLL_OFFSET,
-                        nativeMoveGeneration(), mSendScrollEvent ? 1 : 0, mScrollOffset);
-            }
-            mLastVisibleRectSent.set(mVisibleRect);
-            mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-        }
-        if (getGlobalVisibleRect(mGlobalVisibleRect)
-                && !mGlobalVisibleRect.equals(mLastGlobalRect)) {
-            if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "sendOurVisibleRect=(" + mGlobalVisibleRect.left + ","
-                        + mGlobalVisibleRect.top + ",r=" + mGlobalVisibleRect.right + ",b="
-                        + mGlobalVisibleRect.bottom);
-            }
-            // TODO: the global offset is only used by windowRect()
-            // in ChromeClientAndroid ; other clients such as touch
-            // and mouse events could return view + screen relative points.
-            if (!mBlockWebkitViewMessages) {
-                mWebViewCore.sendMessage(EventHub.SET_GLOBAL_BOUNDS, mGlobalVisibleRect);
-            }
-            mLastGlobalRect.set(mGlobalVisibleRect);
-        }
-        return mVisibleRect;
-    }
-
-    private Point mGlobalVisibleOffset = new Point();
-    // Sets r to be the visible rectangle of our webview in view coordinates
-    private void calcOurVisibleRect(Rect r) {
-        getGlobalVisibleRect(r, mGlobalVisibleOffset);
-        r.offset(-mGlobalVisibleOffset.x, -mGlobalVisibleOffset.y);
-    }
-
-    // Sets r to be our visible rectangle in content coordinates
-    private void calcOurContentVisibleRect(Rect r) {
-        calcOurVisibleRect(r);
-        r.left = viewToContentX(r.left);
-        // viewToContentY will remove the total height of the title bar.  Add
-        // the visible height back in to account for the fact that if the title
-        // bar is partially visible, the part of the visible rect which is
-        // displaying our content is displaced by that amount.
-        r.top = viewToContentY(r.top + getVisibleTitleHeightImpl());
-        r.right = viewToContentX(r.right);
-        r.bottom = viewToContentY(r.bottom);
-    }
-
-    private Rect mContentVisibleRect = new Rect();
-    // Sets r to be our visible rectangle in content coordinates. We use this
-    // method on the native side to compute the position of the fixed layers.
-    // Uses floating coordinates (necessary to correctly place elements when
-    // the scale factor is not 1)
-    private void calcOurContentVisibleRectF(RectF r) {
-        calcOurVisibleRect(mContentVisibleRect);
-        r.left = viewToContentXf(mContentVisibleRect.left);
-        // viewToContentY will remove the total height of the title bar.  Add
-        // the visible height back in to account for the fact that if the title
-        // bar is partially visible, the part of the visible rect which is
-        // displaying our content is displaced by that amount.
-        r.top = viewToContentYf(mContentVisibleRect.top + getVisibleTitleHeightImpl());
-        r.right = viewToContentXf(mContentVisibleRect.right);
-        r.bottom = viewToContentYf(mContentVisibleRect.bottom);
-    }
-
-    static class ViewSizeData {
-        int mWidth;
-        int mHeight;
-        float mHeightWidthRatio;
-        int mActualViewHeight;
-        int mTextWrapWidth;
-        int mAnchorX;
-        int mAnchorY;
-        float mScale;
-        boolean mIgnoreHeight;
-    }
-
-    /**
-     * Compute unzoomed width and height, and if they differ from the last
-     * values we sent, send them to webkit (to be used as new viewport)
-     *
-     * @param force ensures that the message is sent to webkit even if the width
-     * or height has not changed since the last message
-     *
-     * @return true if new values were sent
-     */
-    boolean sendViewSizeZoom(boolean force) {
-        if (mBlockWebkitViewMessages) return false;
-        if (mZoomManager.isPreventingWebkitUpdates()) return false;
-
-        int viewWidth = getViewWidth();
-        int newWidth = Math.round(viewWidth * mZoomManager.getInvScale());
-        // This height could be fixed and be different from actual visible height.
-        int viewHeight = getViewHeightWithTitle() - getTitleHeight();
-        int newHeight = Math.round(viewHeight * mZoomManager.getInvScale());
-        // Make the ratio more accurate than (newHeight / newWidth), since the
-        // latter both are calculated and rounded.
-        float heightWidthRatio = (float) viewHeight / viewWidth;
-        /*
-         * Because the native side may have already done a layout before the
-         * View system was able to measure us, we have to send a height of 0 to
-         * remove excess whitespace when we grow our width. This will trigger a
-         * layout and a change in content size. This content size change will
-         * mean that contentSizeChanged will either call this method directly or
-         * indirectly from onSizeChanged.
-         */
-        if (newWidth > mLastWidthSent && mWrapContent) {
-            newHeight = 0;
-            heightWidthRatio = 0;
-        }
-        // Actual visible content height.
-        int actualViewHeight = Math.round(getViewHeight() * mZoomManager.getInvScale());
-        // Avoid sending another message if the dimensions have not changed.
-        if (newWidth != mLastWidthSent || newHeight != mLastHeightSent || force ||
-                actualViewHeight != mLastActualHeightSent) {
-            ViewSizeData data = new ViewSizeData();
-            data.mWidth = newWidth;
-            data.mHeight = newHeight;
-            data.mHeightWidthRatio = heightWidthRatio;
-            data.mActualViewHeight = actualViewHeight;
-            data.mTextWrapWidth = Math.round(viewWidth / mZoomManager.getTextWrapScale());
-            data.mScale = mZoomManager.getScale();
-            data.mIgnoreHeight = mZoomManager.isFixedLengthAnimationInProgress()
-                    && !mHeightCanMeasure;
-            data.mAnchorX = mZoomManager.getDocumentAnchorX();
-            data.mAnchorY = mZoomManager.getDocumentAnchorY();
-            mWebViewCore.sendMessage(EventHub.VIEW_SIZE_CHANGED, data);
-            mLastWidthSent = newWidth;
-            mLastHeightSent = newHeight;
-            mLastActualHeightSent = actualViewHeight;
-            mZoomManager.clearDocumentAnchor();
-            return true;
-        }
-        return false;
-    }
-
-    /**
-     * Update the double-tap zoom.
-     */
-    /* package */ void updateDoubleTapZoom(int doubleTapZoom) {
-        mZoomManager.updateDoubleTapZoom(doubleTapZoom);
-    }
-
-    private int computeRealHorizontalScrollRange() {
-        if (mDrawHistory) {
-            return mHistoryWidth;
-        } else {
-            // to avoid rounding error caused unnecessary scrollbar, use floor
-            return (int) Math.floor(mContentWidth * mZoomManager.getScale());
-        }
-    }
-
-    @Override
-    protected int computeHorizontalScrollRange() {
-        int range = computeRealHorizontalScrollRange();
-
-        // Adjust reported range if overscrolled to compress the scroll bars
-        final int scrollX = mScrollX;
-        final int overscrollRight = computeMaxScrollX();
-        if (scrollX < 0) {
-            range -= scrollX;
-        } else if (scrollX > overscrollRight) {
-            range += scrollX - overscrollRight;
-        }
-
-        return range;
-    }
-
-    @Override
-    protected int computeHorizontalScrollOffset() {
-        return Math.max(mScrollX, 0);
-    }
-
-    private int computeRealVerticalScrollRange() {
-        if (mDrawHistory) {
-            return mHistoryHeight;
-        } else {
-            // to avoid rounding error caused unnecessary scrollbar, use floor
-            return (int) Math.floor(mContentHeight * mZoomManager.getScale());
-        }
-    }
-
-    @Override
-    protected int computeVerticalScrollRange() {
-        int range = computeRealVerticalScrollRange();
-
-        // Adjust reported range if overscrolled to compress the scroll bars
-        final int scrollY = mScrollY;
-        final int overscrollBottom = computeMaxScrollY();
-        if (scrollY < 0) {
-            range -= scrollY;
-        } else if (scrollY > overscrollBottom) {
-            range += scrollY - overscrollBottom;
-        }
-
-        return range;
-    }
-
-    @Override
-    protected int computeVerticalScrollOffset() {
-        return Math.max(mScrollY - getTitleHeight(), 0);
-    }
-
-    @Override
-    protected int computeVerticalScrollExtent() {
-        return getViewHeight();
-    }
-
-    /** @hide */
-    @Override
-    protected void onDrawVerticalScrollBar(Canvas canvas,
-                                           Drawable scrollBar,
-                                           int l, int t, int r, int b) {
-        if (mScrollY < 0) {
-            t -= mScrollY;
-        }
-        scrollBar.setBounds(l, t + getVisibleTitleHeightImpl(), r, b);
-        scrollBar.draw(canvas);
-    }
-
-    @Override
-    protected void onOverScrolled(int scrollX, int scrollY, boolean clampedX,
-            boolean clampedY) {
-        // Special-case layer scrolling so that we do not trigger normal scroll
-        // updating.
-        if (mTouchMode == TOUCH_DRAG_LAYER_MODE) {
-            scrollLayerTo(scrollX, scrollY);
-            return;
-        }
-        mInOverScrollMode = false;
-        int maxX = computeMaxScrollX();
-        int maxY = computeMaxScrollY();
-        if (maxX == 0) {
-            // do not over scroll x if the page just fits the screen
-            scrollX = pinLocX(scrollX);
-        } else if (scrollX < 0 || scrollX > maxX) {
-            mInOverScrollMode = true;
-        }
-        if (scrollY < 0 || scrollY > maxY) {
-            mInOverScrollMode = true;
-        }
-
-        int oldX = mScrollX;
-        int oldY = mScrollY;
-
-        super.scrollTo(scrollX, scrollY);
-
-        if (mOverScrollGlow != null) {
-            mOverScrollGlow.pullGlow(mScrollX, mScrollY, oldX, oldY, maxX, maxY);
-        }
+        mProvider.requestImageRef(msg);
     }
 
     /**
@@ -3708,8 +1046,7 @@
      */
     public String getUrl() {
         checkThread();
-        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
-        return h != null ? h.getUrl() : null;
+        return mProvider.getUrl();
     }
 
     /**
@@ -3722,8 +1059,7 @@
      */
     public String getOriginalUrl() {
         checkThread();
-        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
-        return h != null ? h.getOriginalUrl() : null;
+        return mProvider.getOriginalUrl();
     }
 
     /**
@@ -3733,8 +1069,7 @@
      */
     public String getTitle() {
         checkThread();
-        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
-        return h != null ? h.getTitle() : null;
+        return mProvider.getTitle();
     }
 
     /**
@@ -3744,8 +1079,7 @@
      */
     public Bitmap getFavicon() {
         checkThread();
-        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
-        return h != null ? h.getFavicon() : null;
+        return mProvider.getFavicon();
     }
 
     /**
@@ -3755,8 +1089,7 @@
      * @hide
      */
     public String getTouchIconUrl() {
-        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
-        return h != null ? h.getTouchIconUrl() : null;
+        return mProvider.getTouchIconUrl();
     }
 
     /**
@@ -3765,7 +1098,7 @@
      */
     public int getProgress() {
         checkThread();
-        return mCallbackProxy.getProgress();
+        return mProvider.getProgress();
     }
 
     /**
@@ -3773,7 +1106,7 @@
      */
     public int getContentHeight() {
         checkThread();
-        return mContentHeight;
+        return mProvider.getContentHeight();
     }
 
     /**
@@ -3781,14 +1114,7 @@
      * @hide
      */
     public int getContentWidth() {
-        return mContentWidth;
-    }
-
-    /**
-     * @hide
-     */
-    public int getPageBackgroundColor() {
-        return nativeGetBackgroundColor();
+        return mProvider.getContentWidth();
     }
 
     /**
@@ -3798,7 +1124,7 @@
      */
     public void pauseTimers() {
         checkThread();
-        mWebViewCore.sendMessage(EventHub.PAUSE_TIMERS);
+        mProvider.pauseTimers();
     }
 
     /**
@@ -3807,7 +1133,7 @@
      */
     public void resumeTimers() {
         checkThread();
-        mWebViewCore.sendMessage(EventHub.RESUME_TIMERS);
+        mProvider.resumeTimers();
     }
 
     /**
@@ -3820,38 +1146,7 @@
      */
     public void onPause() {
         checkThread();
-        if (!mIsPaused) {
-            mIsPaused = true;
-            mWebViewCore.sendMessage(EventHub.ON_PAUSE);
-            // We want to pause the current playing video when switching out
-            // from the current WebView/tab.
-            if (mHTML5VideoViewProxy != null) {
-                mHTML5VideoViewProxy.pauseAndDispatch();
-            }
-            if (mNativeClass != 0) {
-                nativeSetPauseDrawing(mNativeClass, true);
-            }
-
-            cancelSelectDialog();
-            WebCoreThreadWatchdog.pause();
-        }
-    }
-
-    @Override
-    protected void onWindowVisibilityChanged(int visibility) {
-        super.onWindowVisibilityChanged(visibility);
-        updateDrawingState();
-    }
-
-    void updateDrawingState() {
-        if (mNativeClass == 0 || mIsPaused) return;
-        if (getWindowVisibility() != VISIBLE) {
-            nativeSetPauseDrawing(mNativeClass, true);
-        } else if (getVisibility() != VISIBLE) {
-            nativeSetPauseDrawing(mNativeClass, true);
-        } else {
-            nativeSetPauseDrawing(mNativeClass, false);
-        }
+        mProvider.onPause();
     }
 
     /**
@@ -3859,22 +1154,7 @@
      */
     public void onResume() {
         checkThread();
-        if (mIsPaused) {
-            mIsPaused = false;
-            mWebViewCore.sendMessage(EventHub.ON_RESUME);
-            if (mNativeClass != 0) {
-                nativeSetPauseDrawing(mNativeClass, false);
-            }
-        }
-        // Ensure that the watchdog has a currently valid Context to be able to display
-        // a prompt dialog. For example, if the Activity was finished whilst the WebCore
-        // thread was blocked and the Activity is started again, we may reuse the blocked
-        // thread, but we'll have a new Activity.
-        WebCoreThreadWatchdog.updateContext(mContext);
-        // We get a call to onResume for new WebViews (i.e. mIsPaused will be false). We need
-        // to ensure that the Watchdog thread is running for the new WebView, so call
-        // it outside the if block above.
-        WebCoreThreadWatchdog.resume();
+        mProvider.onResume();
     }
 
     /**
@@ -3883,7 +1163,7 @@
      * @hide
      */
     public boolean isPaused() {
-        return mIsPaused;
+        return mProvider.isPaused();
     }
 
     /**
@@ -3892,7 +1172,7 @@
      */
     public void freeMemory() {
         checkThread();
-        mWebViewCore.sendMessage(EventHub.FREE_MEMORY);
+        mProvider.freeMemory();
     }
 
     /**
@@ -3903,11 +1183,7 @@
      */
     public void clearCache(boolean includeDiskFiles) {
         checkThread();
-        // Note: this really needs to be a static method as it clears cache for all
-        // WebView. But we need mWebViewCore to send message to WebCore thread, so
-        // we can't make this static.
-        mWebViewCore.sendMessage(EventHub.CLEAR_CACHE,
-                includeDiskFiles ? 1 : 0, 0);
+        mProvider.clearCache(includeDiskFiles);
     }
 
     /**
@@ -3916,9 +1192,7 @@
      */
     public void clearFormData() {
         checkThread();
-        if (inEditingMode()) {
-            mWebTextView.setAdapterCustom(null);
-        }
+        mProvider.clearFormData();
     }
 
     /**
@@ -3926,8 +1200,7 @@
      */
     public void clearHistory() {
         checkThread();
-        mCallbackProxy.getBackForwardList().setClearPending();
-        mWebViewCore.sendMessage(EventHub.CLEAR_HISTORY);
+        mProvider.clearHistory();
     }
 
     /**
@@ -3936,7 +1209,7 @@
      */
     public void clearSslPreferences() {
         checkThread();
-        mWebViewCore.sendMessage(EventHub.CLEAR_SSL_PREF_TABLE);
+        mProvider.clearSslPreferences();
     }
 
     /**
@@ -3949,7 +1222,8 @@
      */
     public WebBackForwardList copyBackForwardList() {
         checkThread();
-        return mCallbackProxy.getBackForwardList().clone();
+        return mProvider.copyBackForwardList();
+
     }
 
     /*
@@ -3961,8 +1235,7 @@
      */
     public void findNext(boolean forward) {
         checkThread();
-        if (0 == mNativeClass) return; // client isn't initialized
-        mWebViewCore.sendMessage(EventHub.FIND_NEXT, forward ? 1 : 0);
+        mProvider.findNext(forward);
     }
 
     /*
@@ -3972,40 +1245,8 @@
      *              that were found.
      */
     public int findAll(String find) {
-        return findAllBody(find, false);
-    }
-
-    /**
-     * @hide
-     */
-    public void findAllAsync(String find) {
-        findAllBody(find, true);
-    }
-
-    private int findAllBody(String find, boolean isAsync) {
         checkThread();
-        if (0 == mNativeClass) return 0; // client isn't initialized
-        mLastFind = find;
-        mWebViewCore.removeMessages(EventHub.FIND_ALL);
-        WebViewCore.FindAllRequest request = new
-            WebViewCore.FindAllRequest(find);
-        if (isAsync) {
-            mWebViewCore.sendMessage(EventHub.FIND_ALL, request);
-            return 0; // no need to wait for response
-        }
-        synchronized(request) {
-            try {
-                mWebViewCore.sendMessageAtFrontOfQueue(EventHub.FIND_ALL,
-                    request);
-                while (request.mMatchCount == -1) {
-                    request.wait();
-                }
-            }
-            catch (InterruptedException e) {
-                return 0;
-            }
-        }
-        return request.mMatchCount;
+        return mProvider.findAll(find);
     }
 
     /**
@@ -4020,56 +1261,10 @@
      */
     public boolean showFindDialog(String text, boolean showIme) {
         checkThread();
-        FindActionModeCallback callback = new FindActionModeCallback(mContext);
-        if (getParent() == null || startActionMode(callback) == null) {
-            // Could not start the action mode, so end Find on page
-            return false;
-        }
-        mCachedOverlappingActionModeHeight = -1;
-        mFindCallback = callback;
-        setFindIsUp(true);
-        mFindCallback.setWebView(this);
-        if (showIme) {
-            mFindCallback.showSoftInput();
-        } else if (text != null) {
-            mFindCallback.setText(text);
-            mFindCallback.findAll();
-            return true;
-        }
-        if (text == null) {
-            text = mLastFind;
-        }
-        if (text != null) {
-            mFindCallback.setText(text);
-            mFindCallback.findAll();
-        }
-        return true;
+        return mProvider.showFindDialog(text, showIme);
     }
 
     /**
-     * Keep track of the find callback so that we can remove its titlebar if
-     * necessary.
-     */
-    private FindActionModeCallback mFindCallback;
-
-    /**
-     * Toggle whether the find dialog is showing, for both native and Java.
-     */
-    private void setFindIsUp(boolean isUp) {
-        mFindIsUp = isUp;
-        if (0 == mNativeClass) return; // client isn't initialized
-        nativeSetFindIsUp(isUp);
-    }
-
-    // Used to know whether the find dialog is open.  Affects whether
-    // or not we draw the highlights for matches.
-    private boolean mFindIsUp;
-
-    // Keep track of the last string sent, so we can search again when find is
-    // reopened.
-    private String mLastFind;
-
-    /**
      * Return the first substring consisting of the address of a physical
      * location. Currently, only addresses in the United States are detected,
      * and consist of:
@@ -4091,33 +1286,7 @@
      */
     public static String findAddress(String addr) {
         checkThread();
-        return findAddress(addr, false);
-    }
-
-    /**
-     * @hide
-     * Return the first substring consisting of the address of a physical
-     * location. Currently, only addresses in the United States are detected,
-     * and consist of:
-     * - a house number
-     * - a street name
-     * - a street type (Road, Circle, etc), either spelled out or abbreviated
-     * - a city name
-     * - a state or territory, either spelled out or two-letter abbr.
-     * - an optional 5 digit or 9 digit zip code.
-     *
-     * Names are optionally capitalized, and the zip code, if present,
-     * must be valid for the state. The street type must be a standard USPS
-     * spelling or abbreviation. The state or territory must also be spelled
-     * or abbreviated using USPS standards. The house number may not exceed
-     * five digits.
-     * @param addr The string to search for addresses.
-     * @param caseInsensitive addr Set to true to make search ignore case.
-     *
-     * @return the address, or if no address is found, return null.
-     */
-    public static String findAddress(String addr, boolean caseInsensitive) {
-        return WebViewCore.nativeFindAddress(addr, caseInsensitive);
+        return getFactory().getStatics().findAddress(addr);
     }
 
     /*
@@ -4125,28 +1294,7 @@
      */
     public void clearMatches() {
         checkThread();
-        if (mNativeClass == 0)
-            return;
-        mWebViewCore.removeMessages(EventHub.FIND_ALL);
-        mWebViewCore.sendMessage(EventHub.FIND_ALL, null);
-    }
-
-
-    /**
-     * Called when the find ActionMode ends.
-     */
-    void notifyFindDialogDismissed() {
-        mFindCallback = null;
-        mCachedOverlappingActionModeHeight = -1;
-        if (mWebViewCore == null) {
-            return;
-        }
-        clearMatches();
-        setFindIsUp(false);
-        // Now that the dialog has been removed, ensure that we scroll to a
-        // location that is not beyond the end of the page.
-        pinScrollTo(mScrollX, mScrollY, false, 0);
-        invalidate();
+        mProvider.clearMatches();
     }
 
     /**
@@ -4157,427 +1305,7 @@
      */
     public void documentHasImages(Message response) {
         checkThread();
-        if (response == null) {
-            return;
-        }
-        mWebViewCore.sendMessage(EventHub.DOC_HAS_IMAGES, response);
-    }
-
-    /**
-     * Request the scroller to abort any ongoing animation
-     *
-     * @hide
-     */
-    public void stopScroll() {
-        mScroller.forceFinished(true);
-        mLastVelocity = 0;
-    }
-
-    @Override
-    public void computeScroll() {
-        if (mScroller.computeScrollOffset()) {
-            int oldX = mScrollX;
-            int oldY = mScrollY;
-            int x = mScroller.getCurrX();
-            int y = mScroller.getCurrY();
-            invalidate();  // So we draw again
-
-            if (!mScroller.isFinished()) {
-                int rangeX = computeMaxScrollX();
-                int rangeY = computeMaxScrollY();
-                int overflingDistance = mOverflingDistance;
-
-                // Use the layer's scroll data if needed.
-                if (mTouchMode == TOUCH_DRAG_LAYER_MODE) {
-                    oldX = mScrollingLayerRect.left;
-                    oldY = mScrollingLayerRect.top;
-                    rangeX = mScrollingLayerRect.right;
-                    rangeY = mScrollingLayerRect.bottom;
-                    // No overscrolling for layers.
-                    overflingDistance = 0;
-                }
-
-                overScrollBy(x - oldX, y - oldY, oldX, oldY,
-                        rangeX, rangeY,
-                        overflingDistance, overflingDistance, false);
-
-                if (mOverScrollGlow != null) {
-                    mOverScrollGlow.absorbGlow(x, y, oldX, oldY, rangeX, rangeY);
-                }
-            } else {
-                if (mTouchMode != TOUCH_DRAG_LAYER_MODE) {
-                    mScrollX = x;
-                    mScrollY = y;
-                } else {
-                    // Update the layer position instead of WebView.
-                    scrollLayerTo(x, y);
-                }
-                abortAnimation();
-                nativeSetIsScrolling(false);
-                if (!mBlockWebkitViewMessages) {
-                    WebViewCore.resumePriority();
-                    if (!mSelectingText) {
-                        WebViewCore.resumeUpdatePicture(mWebViewCore);
-                    }
-                }
-                if (oldX != mScrollX || oldY != mScrollY) {
-                    sendOurVisibleRect();
-                }
-            }
-        } else {
-            super.computeScroll();
-        }
-    }
-
-    private void scrollLayerTo(int x, int y) {
-        if (x == mScrollingLayerRect.left && y == mScrollingLayerRect.top) {
-            return;
-        }
-        if (mSelectingText) {
-            int dx = mScrollingLayerRect.left - x;
-            int dy = mScrollingLayerRect.top - y;
-            if (mSelectCursorBaseLayerId == mCurrentScrollingLayerId) {
-                mSelectCursorBase.offset(dx, dy);
-            }
-            if (mSelectCursorExtentLayerId == mCurrentScrollingLayerId) {
-                mSelectCursorExtent.offset(dx, dy);
-            }
-        }
-        nativeScrollLayer(mCurrentScrollingLayerId, x, y);
-        mScrollingLayerRect.left = x;
-        mScrollingLayerRect.top = y;
-        mWebViewCore.sendMessage(WebViewCore.EventHub.SCROLL_LAYER, mCurrentScrollingLayerId,
-                mScrollingLayerRect);
-        onScrollChanged(mScrollX, mScrollY, mScrollX, mScrollY);
-        invalidate();
-    }
-
-    private static int computeDuration(int dx, int dy) {
-        int distance = Math.max(Math.abs(dx), Math.abs(dy));
-        int duration = distance * 1000 / STD_SPEED;
-        return Math.min(duration, MAX_DURATION);
-    }
-
-    // helper to pin the scrollBy parameters (already in view coordinates)
-    // returns true if the scroll was changed
-    private boolean pinScrollBy(int dx, int dy, boolean animate, int animationDuration) {
-        return pinScrollTo(mScrollX + dx, mScrollY + dy, animate, animationDuration);
-    }
-    // helper to pin the scrollTo parameters (already in view coordinates)
-    // returns true if the scroll was changed
-    private boolean pinScrollTo(int x, int y, boolean animate, int animationDuration) {
-        x = pinLocX(x);
-        y = pinLocY(y);
-        int dx = x - mScrollX;
-        int dy = y - mScrollY;
-
-        if ((dx | dy) == 0) {
-            return false;
-        }
-        abortAnimation();
-        if (animate) {
-            //        Log.d(LOGTAG, "startScroll: " + dx + " " + dy);
-            mScroller.startScroll(mScrollX, mScrollY, dx, dy,
-                    animationDuration > 0 ? animationDuration : computeDuration(dx, dy));
-            awakenScrollBars(mScroller.getDuration());
-            invalidate();
-        } else {
-            scrollTo(x, y);
-        }
-        return true;
-    }
-
-    // Scale from content to view coordinates, and pin.
-    // Also called by jni webview.cpp
-    private boolean setContentScrollBy(int cx, int cy, boolean animate) {
-        if (mDrawHistory) {
-            // disallow WebView to change the scroll position as History Picture
-            // is used in the view system.
-            // TODO: as we switchOutDrawHistory when trackball or navigation
-            // keys are hit, this should be safe. Right?
-            return false;
-        }
-        cx = contentToViewDimension(cx);
-        cy = contentToViewDimension(cy);
-        if (mHeightCanMeasure) {
-            // move our visible rect according to scroll request
-            if (cy != 0) {
-                Rect tempRect = new Rect();
-                calcOurVisibleRect(tempRect);
-                tempRect.offset(cx, cy);
-                requestRectangleOnScreen(tempRect);
-            }
-            // FIXME: We scroll horizontally no matter what because currently
-            // ScrollView and ListView will not scroll horizontally.
-            // FIXME: Why do we only scroll horizontally if there is no
-            // vertical scroll?
-//                Log.d(LOGTAG, "setContentScrollBy cy=" + cy);
-            return cy == 0 && cx != 0 && pinScrollBy(cx, 0, animate, 0);
-        } else {
-            return pinScrollBy(cx, cy, animate, 0);
-        }
-    }
-
-    /**
-     * Called by CallbackProxy when the page starts loading.
-     * @param url The URL of the page which has started loading.
-     */
-    /* package */ void onPageStarted(String url) {
-        // every time we start a new page, we want to reset the
-        // WebView certificate:  if the new site is secure, we
-        // will reload it and get a new certificate set;
-        // if the new site is not secure, the certificate must be
-        // null, and that will be the case
-        setCertificate(null);
-
-        // reset the flag since we set to true in if need after
-        // loading is see onPageFinished(Url)
-        mAccessibilityScriptInjected = false;
-    }
-
-    /**
-     * Called by CallbackProxy when the page finishes loading.
-     * @param url The URL of the page which has finished loading.
-     */
-    /* package */ void onPageFinished(String url) {
-        if (mPageThatNeedsToSlideTitleBarOffScreen != null) {
-            // If the user is now on a different page, or has scrolled the page
-            // past the point where the title bar is offscreen, ignore the
-            // scroll request.
-            if (mPageThatNeedsToSlideTitleBarOffScreen.equals(url)
-                    && mScrollX == 0 && mScrollY == 0) {
-                pinScrollTo(0, mYDistanceToSlideTitleOffScreen, true,
-                        SLIDE_TITLE_DURATION);
-            }
-            mPageThatNeedsToSlideTitleBarOffScreen = null;
-        }
-        mZoomManager.onPageFinished(url);
-        injectAccessibilityForUrl(url);
-    }
-
-    /**
-     * This method injects accessibility in the loaded document if accessibility
-     * is enabled. If JavaScript is enabled we try to inject a URL specific script.
-     * If no URL specific script is found or JavaScript is disabled we fallback to
-     * the default {@link AccessibilityInjector} implementation.
-     * </p>
-     * If the URL has the "axs" paramter set to 1 it has already done the
-     * script injection so we do nothing. If the parameter is set to 0
-     * the URL opts out accessibility script injection so we fall back to
-     * the default {@link AccessibilityInjector}.
-     * </p>
-     * Note: If the user has not opted-in the accessibility script injection no scripts
-     * are injected rather the default {@link AccessibilityInjector} implementation
-     * is used.
-     *
-     * @param url The URL loaded by this {@link WebView}.
-     */
-    private void injectAccessibilityForUrl(String url) {
-        if (mWebViewCore == null) {
-            return;
-        }
-        AccessibilityManager accessibilityManager = AccessibilityManager.getInstance(mContext);
-
-        if (!accessibilityManager.isEnabled()) {
-            // it is possible that accessibility was turned off between reloads
-            ensureAccessibilityScriptInjectorInstance(false);
-            return;
-        }
-
-        if (!getSettings().getJavaScriptEnabled()) {
-            // no JS so we fallback to the basic buil-in support
-            ensureAccessibilityScriptInjectorInstance(true);
-            return;
-        }
-
-        // check the URL "axs" parameter to choose appropriate action
-        int axsParameterValue = getAxsUrlParameterValue(url);
-        if (axsParameterValue == ACCESSIBILITY_SCRIPT_INJECTION_UNDEFINED) {
-            boolean onDeviceScriptInjectionEnabled = (Settings.Secure.getInt(mContext
-                    .getContentResolver(), Settings.Secure.ACCESSIBILITY_SCRIPT_INJECTION, 0) == 1);
-            if (onDeviceScriptInjectionEnabled) {
-                ensureAccessibilityScriptInjectorInstance(false);
-                // neither script injected nor script injection opted out => we inject
-                loadUrl(getScreenReaderInjectingJs());
-                // TODO: Set this flag after successfull script injection. Maybe upon injection
-                // the chooser should update the meta tag and we check it to declare success
-                mAccessibilityScriptInjected = true;
-            } else {
-                // injection disabled so we fallback to the basic built-in support
-                ensureAccessibilityScriptInjectorInstance(true);
-            }
-        } else if (axsParameterValue == ACCESSIBILITY_SCRIPT_INJECTION_OPTED_OUT) {
-            // injection opted out so we fallback to the basic buil-in support
-            ensureAccessibilityScriptInjectorInstance(true);
-        } else if (axsParameterValue == ACCESSIBILITY_SCRIPT_INJECTION_PROVIDED) {
-            ensureAccessibilityScriptInjectorInstance(false);
-            // the URL provides accessibility but we still need to add our generic script
-            loadUrl(getScreenReaderInjectingJs());
-        } else {
-            Log.e(LOGTAG, "Unknown URL value for the \"axs\" URL parameter: " + axsParameterValue);
-        }
-    }
-
-    /**
-     * Ensures the instance of the {@link AccessibilityInjector} to be present ot not.
-     *
-     * @param present True to ensure an insance, false to ensure no instance.
-     */
-    private void ensureAccessibilityScriptInjectorInstance(boolean present) {
-        if (present) {
-            if (mAccessibilityInjector == null) {
-                mAccessibilityInjector = new AccessibilityInjector(this);
-            }
-        } else {
-            mAccessibilityInjector = null;
-        }
-    }
-
-    /**
-     * Gets JavaScript that injects a screen-reader.
-     *
-     * @return The JavaScript snippet.
-     */
-    private String getScreenReaderInjectingJs() {
-        String screenReaderUrl = Settings.Secure.getString(mContext.getContentResolver(),
-                Settings.Secure.ACCESSIBILITY_SCREEN_READER_URL);
-        return String.format(ACCESSIBILITY_SCREEN_READER_JAVASCRIPT_TEMPLATE, screenReaderUrl);
-    }
-
-    /**
-     * Gets the "axs" URL parameter value.
-     *
-     * @param url A url to fetch the paramter from.
-     * @return The parameter value if such, -1 otherwise.
-     */
-    private int getAxsUrlParameterValue(String url) {
-        if (mMatchAxsUrlParameterPattern == null) {
-            mMatchAxsUrlParameterPattern = Pattern.compile(PATTERN_MATCH_AXS_URL_PARAMETER);
-        }
-        Matcher matcher = mMatchAxsUrlParameterPattern.matcher(url);
-        if (matcher.find()) {
-            String keyValuePair = url.substring(matcher.start(), matcher.end());
-            return Integer.parseInt(keyValuePair.split("=")[1]);
-        }
-        return -1;
-    }
-
-    /**
-     * The URL of a page that sent a message to scroll the title bar off screen.
-     *
-     * Many mobile sites tell the page to scroll to (0,1) in order to scroll the
-     * title bar off the screen.  Sometimes, the scroll position is set before
-     * the page finishes loading.  Rather than scrolling while the page is still
-     * loading, keep track of the URL and new scroll position so we can perform
-     * the scroll once the page finishes loading.
-     */
-    private String mPageThatNeedsToSlideTitleBarOffScreen;
-
-    /**
-     * The destination Y scroll position to be used when the page finishes
-     * loading.  See mPageThatNeedsToSlideTitleBarOffScreen.
-     */
-    private int mYDistanceToSlideTitleOffScreen;
-
-    // scale from content to view coordinates, and pin
-    // return true if pin caused the final x/y different than the request cx/cy,
-    // and a future scroll may reach the request cx/cy after our size has
-    // changed
-    // return false if the view scroll to the exact position as it is requested,
-    // where negative numbers are taken to mean 0
-    private boolean setContentScrollTo(int cx, int cy) {
-        if (mDrawHistory) {
-            // disallow WebView to change the scroll position as History Picture
-            // is used in the view system.
-            // One known case where this is called is that WebCore tries to
-            // restore the scroll position. As history Picture already uses the
-            // saved scroll position, it is ok to skip this.
-            return false;
-        }
-        int vx;
-        int vy;
-        if ((cx | cy) == 0) {
-            // If the page is being scrolled to (0,0), do not add in the title
-            // bar's height, and simply scroll to (0,0). (The only other work
-            // in contentToView_ is to multiply, so this would not change 0.)
-            vx = 0;
-            vy = 0;
-        } else {
-            vx = contentToViewX(cx);
-            vy = contentToViewY(cy);
-        }
-//        Log.d(LOGTAG, "content scrollTo [" + cx + " " + cy + "] view=[" +
-//                      vx + " " + vy + "]");
-        // Some mobile sites attempt to scroll the title bar off the page by
-        // scrolling to (0,1).  If we are at the top left corner of the
-        // page, assume this is an attempt to scroll off the title bar, and
-        // animate the title bar off screen slowly enough that the user can see
-        // it.
-        if (cx == 0 && cy == 1 && mScrollX == 0 && mScrollY == 0
-                && mTitleBar != null) {
-            // FIXME: 100 should be defined somewhere as our max progress.
-            if (getProgress() < 100) {
-                // Wait to scroll the title bar off screen until the page has
-                // finished loading.  Keep track of the URL and the destination
-                // Y position
-                mPageThatNeedsToSlideTitleBarOffScreen = getUrl();
-                mYDistanceToSlideTitleOffScreen = vy;
-            } else {
-                pinScrollTo(vx, vy, true, SLIDE_TITLE_DURATION);
-            }
-            // Since we are animating, we have not yet reached the desired
-            // scroll position.  Do not return true to request another attempt
-            return false;
-        }
-        pinScrollTo(vx, vy, false, 0);
-        // If the request was to scroll to a negative coordinate, treat it as if
-        // it was a request to scroll to 0
-        if ((mScrollX != vx && cx >= 0) || (mScrollY != vy && cy >= 0)) {
-            return true;
-        } else {
-            return false;
-        }
-    }
-
-    // scale from content to view coordinates, and pin
-    private void spawnContentScrollTo(int cx, int cy) {
-        if (mDrawHistory) {
-            // disallow WebView to change the scroll position as History Picture
-            // is used in the view system.
-            return;
-        }
-        int vx = contentToViewX(cx);
-        int vy = contentToViewY(cy);
-        pinScrollTo(vx, vy, true, 0);
-    }
-
-    /**
-     * These are from webkit, and are in content coordinate system (unzoomed)
-     */
-    private void contentSizeChanged(boolean updateLayout) {
-        // suppress 0,0 since we usually see real dimensions soon after
-        // this avoids drawing the prev content in a funny place. If we find a
-        // way to consolidate these notifications, this check may become
-        // obsolete
-        if ((mContentWidth | mContentHeight) == 0) {
-            return;
-        }
-
-        if (mHeightCanMeasure) {
-            if (getMeasuredHeight() != contentToViewDimension(mContentHeight)
-                    || updateLayout) {
-                requestLayout();
-            }
-        } else if (mWidthCanMeasure) {
-            if (getMeasuredWidth() != contentToViewDimension(mContentWidth)
-                    || updateLayout) {
-                requestLayout();
-            }
-        } else {
-            // If we don't request a layout, try to send our view size to the
-            // native side to ensure that WebCore has the correct dimensions.
-            sendViewSizeZoom(false);
-        }
+        mProvider.documentHasImages(response);
     }
 
     /**
@@ -4587,17 +1315,7 @@
      */
     public void setWebViewClient(WebViewClient client) {
         checkThread();
-        mCallbackProxy.setWebViewClient(client);
-    }
-
-    /**
-     * Gets the WebViewClient
-     * @return the current WebViewClient instance.
-     *
-     * @hide This is an implementation detail.
-     */
-    public WebViewClient getWebViewClient() {
-        return mCallbackProxy.getWebViewClient();
+        mProvider.setWebViewClient(client);
     }
 
     /**
@@ -4608,7 +1326,7 @@
      */
     public void setDownloadListener(DownloadListener listener) {
         checkThread();
-        mCallbackProxy.setDownloadListener(listener);
+        mProvider.setDownloadListener(listener);
     }
 
     /**
@@ -4619,36 +1337,7 @@
      */
     public void setWebChromeClient(WebChromeClient client) {
         checkThread();
-        mCallbackProxy.setWebChromeClient(client);
-    }
-
-    /**
-     * Gets the chrome handler.
-     * @return the current WebChromeClient instance.
-     *
-     * @hide This is an implementation detail.
-     */
-    public WebChromeClient getWebChromeClient() {
-        return mCallbackProxy.getWebChromeClient();
-    }
-
-    /**
-     * Set the back/forward list client. This is an implementation of
-     * WebBackForwardListClient for handling new items and changes in the
-     * history index.
-     * @param client An implementation of WebBackForwardListClient.
-     * {@hide}
-     */
-    public void setWebBackForwardListClient(WebBackForwardListClient client) {
-        mCallbackProxy.setWebBackForwardListClient(client);
-    }
-
-    /**
-     * Gets the WebBackForwardListClient.
-     * {@hide}
-     */
-    public WebBackForwardListClient getWebBackForwardListClient() {
-        return mCallbackProxy.getWebBackForwardListClient();
+        mProvider.setWebChromeClient(client);
     }
 
     /**
@@ -4660,23 +1349,7 @@
     @Deprecated
     public void setPictureListener(PictureListener listener) {
         checkThread();
-        mPictureListener = listener;
-    }
-
-    /**
-     * {@hide}
-     */
-    /* FIXME: Debug only! Remove for SDK! */
-    public void externalRepresentation(Message callback) {
-        mWebViewCore.sendMessage(EventHub.REQUEST_EXT_REPRESENTATION, callback);
-    }
-
-    /**
-     * {@hide}
-     */
-    /* FIXME: Debug only! Remove for SDK! */
-    public void documentAsText(Message callback) {
-        mWebViewCore.sendMessage(EventHub.REQUEST_DOC_AS_TEXT, callback);
+        mProvider.setPictureListener(listener);
     }
 
     /**
@@ -4707,13 +1380,7 @@
      */
     public void addJavascriptInterface(Object object, String name) {
         checkThread();
-        if (object == null) {
-            return;
-        }
-        WebViewCore.JSInterfaceData arg = new WebViewCore.JSInterfaceData();
-        arg.mObject = object;
-        arg.mInterfaceName = name;
-        mWebViewCore.sendMessage(EventHub.ADD_JS_INTERFACE, arg);
+        mProvider.addJavascriptInterface(object, name);
     }
 
     /**
@@ -4722,11 +1389,7 @@
      */
     public void removeJavascriptInterface(String interfaceName) {
         checkThread();
-        if (mWebViewCore != null) {
-            WebViewCore.JSInterfaceData arg = new WebViewCore.JSInterfaceData();
-            arg.mInterfaceName = interfaceName;
-            mWebViewCore.sendMessage(EventHub.REMOVE_JS_INTERFACE, arg);
-        }
+        mProvider.removeJavascriptInterface(interfaceName);
     }
 
     /**
@@ -4737,1410 +1400,31 @@
      */
     public WebSettings getSettings() {
         checkThread();
-        return (mWebViewCore != null) ? mWebViewCore.getSettings() : null;
+        return mProvider.getSettings();
     }
 
-   /**
-    * Return the list of currently loaded plugins.
-    * @return The list of currently loaded plugins.
-    *
-    * @hide
-    * @deprecated This was used for Gears, which has been deprecated.
-    */
+    /**
+     * Return the list of currently loaded plugins.
+     * @return The list of currently loaded plugins.
+     *
+     * @hide
+     * @deprecated This was used for Gears, which has been deprecated.
+     */
     @Deprecated
     public static synchronized PluginList getPluginList() {
         checkThread();
         return new PluginList();
     }
 
-   /**
-    * @hide
-    * @deprecated This was used for Gears, which has been deprecated.
-    */
+    /**
+     * @hide
+     * @deprecated This was used for Gears, which has been deprecated.
+     */
     @Deprecated
     public void refreshPlugins(boolean reloadOpenPages) {
         checkThread();
     }
 
-    //-------------------------------------------------------------------------
-    // Override View methods
-    //-------------------------------------------------------------------------
-
-    @Override
-    protected void finalize() throws Throwable {
-        try {
-            if (mNativeClass != 0) {
-                mPrivateHandler.post(new Runnable() {
-                    @Override
-                    public void run() {
-                        destroy();
-                    }
-                });
-            }
-        } finally {
-            super.finalize();
-        }
-    }
-
-    @Override
-    protected boolean drawChild(Canvas canvas, View child, long drawingTime) {
-        if (child == mTitleBar) {
-            // When drawing the title bar, move it horizontally to always show
-            // at the top of the WebView.
-            mTitleBar.offsetLeftAndRight(mScrollX - mTitleBar.getLeft());
-            int newTop = 0;
-            if (mTitleGravity == Gravity.NO_GRAVITY) {
-                newTop = Math.min(0, mScrollY);
-            } else if (mTitleGravity == Gravity.TOP) {
-                newTop = mScrollY;
-            }
-            mTitleBar.setBottom(newTop + mTitleBar.getHeight());
-            mTitleBar.setTop(newTop);
-        }
-        return super.drawChild(canvas, child, drawingTime);
-    }
-
-    private void drawContent(Canvas canvas, boolean drawRings) {
-        drawCoreAndCursorRing(canvas, mBackgroundColor,
-                mDrawCursorRing && drawRings);
-    }
-
-    /**
-     * Draw the background when beyond bounds
-     * @param canvas Canvas to draw into
-     */
-    private void drawOverScrollBackground(Canvas canvas) {
-        if (mOverScrollBackground == null) {
-            mOverScrollBackground = new Paint();
-            Bitmap bm = BitmapFactory.decodeResource(
-                    mContext.getResources(),
-                    com.android.internal.R.drawable.status_bar_background);
-            mOverScrollBackground.setShader(new BitmapShader(bm,
-                    Shader.TileMode.REPEAT, Shader.TileMode.REPEAT));
-            mOverScrollBorder = new Paint();
-            mOverScrollBorder.setStyle(Paint.Style.STROKE);
-            mOverScrollBorder.setStrokeWidth(0);
-            mOverScrollBorder.setColor(0xffbbbbbb);
-        }
-
-        int top = 0;
-        int right = computeRealHorizontalScrollRange();
-        int bottom = top + computeRealVerticalScrollRange();
-        // first draw the background and anchor to the top of the view
-        canvas.save();
-        canvas.translate(mScrollX, mScrollY);
-        canvas.clipRect(-mScrollX, top - mScrollY, right - mScrollX, bottom
-                - mScrollY, Region.Op.DIFFERENCE);
-        canvas.drawPaint(mOverScrollBackground);
-        canvas.restore();
-        // then draw the border
-        canvas.drawRect(-1, top - 1, right, bottom, mOverScrollBorder);
-        // next clip the region for the content
-        canvas.clipRect(0, top, right, bottom);
-    }
-
-    @Override
-    protected void onDraw(Canvas canvas) {
-        if (inFullScreenMode()) {
-            return; // no need to draw anything if we aren't visible.
-        }
-        // if mNativeClass is 0, the WebView is either destroyed or not
-        // initialized. In either case, just draw the background color and return
-        if (mNativeClass == 0) {
-            canvas.drawColor(mBackgroundColor);
-            return;
-        }
-
-        // if both mContentWidth and mContentHeight are 0, it means there is no
-        // valid Picture passed to WebView yet. This can happen when WebView
-        // just starts. Draw the background and return.
-        if ((mContentWidth | mContentHeight) == 0 && mHistoryPicture == null) {
-            canvas.drawColor(mBackgroundColor);
-            return;
-        }
-
-        if (canvas.isHardwareAccelerated()) {
-            mZoomManager.setHardwareAccelerated();
-        } else {
-            mWebViewCore.resumeWebKitDraw();
-        }
-
-        int saveCount = canvas.save();
-        if (mInOverScrollMode && !getSettings()
-                .getUseWebViewBackgroundForOverscrollBackground()) {
-            drawOverScrollBackground(canvas);
-        }
-        if (mTitleBar != null) {
-            canvas.translate(0, getTitleHeight());
-        }
-        boolean drawNativeRings = !sDisableNavcache;
-        drawContent(canvas, drawNativeRings);
-        canvas.restoreToCount(saveCount);
-
-        if (AUTO_REDRAW_HACK && mAutoRedraw) {
-            invalidate();
-        }
-        mWebViewCore.signalRepaintDone();
-
-        if (mOverScrollGlow != null && mOverScrollGlow.drawEdgeGlows(canvas)) {
-            invalidate();
-        }
-
-        if (mFocusTransition != null) {
-            mFocusTransition.draw(canvas);
-        } else if (shouldDrawHighlightRect()) {
-            RegionIterator iter = new RegionIterator(mTouchHighlightRegion);
-            Rect r = new Rect();
-            while (iter.next(r)) {
-                canvas.drawRect(r, mTouchHightlightPaint);
-            }
-        }
-        if (DEBUG_TOUCH_HIGHLIGHT) {
-            if (getSettings().getNavDump()) {
-                if ((mTouchHighlightX | mTouchHighlightY) != 0) {
-                    if (mTouchCrossHairColor == null) {
-                        mTouchCrossHairColor = new Paint();
-                        mTouchCrossHairColor.setColor(Color.RED);
-                    }
-                    canvas.drawLine(mTouchHighlightX - mNavSlop,
-                            mTouchHighlightY - mNavSlop, mTouchHighlightX
-                                    + mNavSlop + 1, mTouchHighlightY + mNavSlop
-                                    + 1, mTouchCrossHairColor);
-                    canvas.drawLine(mTouchHighlightX + mNavSlop + 1,
-                            mTouchHighlightY - mNavSlop, mTouchHighlightX
-                                    - mNavSlop,
-                            mTouchHighlightY + mNavSlop + 1,
-                            mTouchCrossHairColor);
-                }
-            }
-        }
-    }
-
-    private void removeTouchHighlight() {
-        mWebViewCore.removeMessages(EventHub.HIT_TEST);
-        mPrivateHandler.removeMessages(HIT_TEST_RESULT);
-        setTouchHighlightRects(null);
-    }
-
-    @Override
-    public void setLayoutParams(ViewGroup.LayoutParams params) {
-        if (params.height == LayoutParams.WRAP_CONTENT) {
-            mWrapContent = true;
-        }
-        super.setLayoutParams(params);
-    }
-
-    @Override
-    public boolean performLongClick() {
-        // performLongClick() is the result of a delayed message. If we switch
-        // to windows overview, the WebView will be temporarily removed from the
-        // view system. In that case, do nothing.
-        if (getParent() == null) return false;
-
-        // A multi-finger gesture can look like a long press; make sure we don't take
-        // long press actions if we're scaling.
-        final ScaleGestureDetector detector = mZoomManager.getMultiTouchGestureDetector();
-        if (detector != null && detector.isInProgress()) {
-            return false;
-        }
-
-        if (mNativeClass != 0 && nativeCursorIsTextInput()) {
-            // Send the click so that the textfield is in focus
-            centerKeyPressOnTextField();
-            rebuildWebTextView();
-        } else {
-            clearTextEntry();
-        }
-        if (inEditingMode()) {
-            // Since we just called rebuildWebTextView, the layout is not set
-            // properly.  Update it so it can correctly find the word to select.
-            mWebTextView.ensureLayout();
-            // Provide a touch down event to WebTextView, which will allow it
-            // to store the location to use in performLongClick.
-            AbsoluteLayout.LayoutParams params
-                    = (AbsoluteLayout.LayoutParams) mWebTextView.getLayoutParams();
-            MotionEvent fake = MotionEvent.obtain(mLastTouchTime,
-                    mLastTouchTime, MotionEvent.ACTION_DOWN,
-                    mLastTouchX - params.x + mScrollX,
-                    mLastTouchY - params.y + mScrollY, 0);
-            mWebTextView.dispatchTouchEvent(fake);
-            return mWebTextView.performLongClick();
-        }
-        if (mSelectingText) return false; // long click does nothing on selection
-        /* if long click brings up a context menu, the super function
-         * returns true and we're done. Otherwise, nothing happened when
-         * the user clicked. */
-        if (super.performLongClick()) {
-            return true;
-        }
-        /* In the case where the application hasn't already handled the long
-         * click action, look for a word under the  click. If one is found,
-         * animate the text selection into view.
-         * FIXME: no animation code yet */
-        final boolean isSelecting = selectText();
-        if (isSelecting) {
-            performHapticFeedback(HapticFeedbackConstants.LONG_PRESS);
-        } else if (focusCandidateIsEditableText()) {
-            mSelectCallback = new SelectActionModeCallback();
-            mSelectCallback.setWebView(this);
-            mSelectCallback.setTextSelected(false);
-            startActionMode(mSelectCallback);
-        }
-        return isSelecting;
-    }
-
-    /**
-     * Select the word at the last click point.
-     *
-     * @hide This is an implementation detail.
-     */
-    public boolean selectText() {
-        int x = viewToContentX(mLastTouchX + mScrollX);
-        int y = viewToContentY(mLastTouchY + mScrollY);
-        return selectText(x, y);
-    }
-
-    /**
-     * Select the word at the indicated content coordinates.
-     */
-    boolean selectText(int x, int y) {
-        mWebViewCore.sendMessage(EventHub.SELECT_WORD_AT, x, y);
-        return true;
-    }
-
-    private int mOrientation = Configuration.ORIENTATION_UNDEFINED;
-
-    @Override
-    protected void onConfigurationChanged(Configuration newConfig) {
-        mCachedOverlappingActionModeHeight = -1;
-        if (mSelectingText && mOrientation != newConfig.orientation) {
-            selectionDone();
-        }
-        mOrientation = newConfig.orientation;
-        if (mWebViewCore != null && !mBlockWebkitViewMessages) {
-            mWebViewCore.sendMessage(EventHub.CLEAR_CONTENT);
-        }
-    }
-
-    /**
-     * Keep track of the Callback so we can end its ActionMode or remove its
-     * titlebar.
-     */
-    private SelectActionModeCallback mSelectCallback;
-
-    // These values are possible options for didUpdateWebTextViewDimensions.
-    private static final int FULLY_ON_SCREEN = 0;
-    private static final int INTERSECTS_SCREEN = 1;
-    private static final int ANYWHERE = 2;
-
-    /**
-     * Check to see if the focused textfield/textarea is still on screen.  If it
-     * is, update the the dimensions and location of WebTextView.  Otherwise,
-     * remove the WebTextView.  Should be called when the zoom level changes.
-     * @param intersection How to determine whether the textfield/textarea is
-     *        still on screen.
-     * @return boolean True if the textfield/textarea is still on screen and the
-     *         dimensions/location of WebTextView have been updated.
-     */
-    private boolean didUpdateWebTextViewDimensions(int intersection) {
-        Rect contentBounds = nativeFocusCandidateNodeBounds();
-        Rect vBox = contentToViewRect(contentBounds);
-        Rect visibleRect = new Rect();
-        calcOurVisibleRect(visibleRect);
-        offsetByLayerScrollPosition(vBox);
-        // If the textfield is on screen, place the WebTextView in
-        // its new place, accounting for our new scroll/zoom values,
-        // and adjust its textsize.
-        boolean onScreen;
-        switch (intersection) {
-            case FULLY_ON_SCREEN:
-                onScreen = visibleRect.contains(vBox);
-                break;
-            case INTERSECTS_SCREEN:
-                onScreen = Rect.intersects(visibleRect, vBox);
-                break;
-            case ANYWHERE:
-                onScreen = true;
-                break;
-            default:
-                throw new AssertionError(
-                        "invalid parameter passed to didUpdateWebTextViewDimensions");
-        }
-        if (onScreen) {
-            mWebTextView.setRect(vBox.left, vBox.top, vBox.width(),
-                    vBox.height());
-            mWebTextView.updateTextSize();
-            updateWebTextViewPadding();
-            return true;
-        } else {
-            // The textfield is now off screen.  The user probably
-            // was not zooming to see the textfield better.  Remove
-            // the WebTextView.  If the user types a key, and the
-            // textfield is still in focus, we will reconstruct
-            // the WebTextView and scroll it back on screen.
-            mWebTextView.remove();
-            return false;
-        }
-    }
-
-    private void offsetByLayerScrollPosition(Rect box) {
-        if ((mCurrentScrollingLayerId != 0)
-                && (mCurrentScrollingLayerId == nativeFocusCandidateLayerId())) {
-            box.offsetTo(box.left - mScrollingLayerRect.left,
-                    box.top - mScrollingLayerRect.top);
-        }
-    }
-
-    void setBaseLayer(int layer, Region invalRegion, boolean showVisualIndicator,
-            boolean isPictureAfterFirstLayout) {
-        if (mNativeClass == 0)
-            return;
-        boolean queueFull;
-        queueFull = nativeSetBaseLayer(mNativeClass, layer, invalRegion,
-                                       showVisualIndicator, isPictureAfterFirstLayout);
-
-        if (layer == 0 || isPictureAfterFirstLayout) {
-            mWebViewCore.resumeWebKitDraw();
-        } else if (queueFull) {
-            // temporarily disable webkit draw throttling
-            // TODO: re-enable
-            // mWebViewCore.pauseWebKitDraw();
-        }
-
-        if (mHTML5VideoViewProxy != null) {
-            mHTML5VideoViewProxy.setBaseLayer(layer);
-        }
-    }
-
-    int getBaseLayer() {
-        if (mNativeClass == 0) {
-            return 0;
-        }
-        return nativeGetBaseLayer();
-    }
-
-    private void onZoomAnimationStart() {
-        // If it is in password mode, turn it off so it does not draw misplaced.
-        if (inEditingMode()) {
-            mWebTextView.setVisibility(INVISIBLE);
-        }
-    }
-
-    private void onZoomAnimationEnd() {
-        // adjust the edit text view if needed
-        if (inEditingMode()
-                && didUpdateWebTextViewDimensions(FULLY_ON_SCREEN)) {
-            // If it is a password field, start drawing the WebTextView once
-            // again.
-            mWebTextView.setVisibility(VISIBLE);
-        }
-    }
-
-    void onFixedLengthZoomAnimationStart() {
-        WebViewCore.pauseUpdatePicture(getWebViewCore());
-        onZoomAnimationStart();
-    }
-
-    void onFixedLengthZoomAnimationEnd() {
-        if (!mBlockWebkitViewMessages && !mSelectingText) {
-            WebViewCore.resumeUpdatePicture(mWebViewCore);
-        }
-        onZoomAnimationEnd();
-    }
-
-    private static final int ZOOM_BITS = Paint.FILTER_BITMAP_FLAG |
-                                         Paint.DITHER_FLAG |
-                                         Paint.SUBPIXEL_TEXT_FLAG;
-    private static final int SCROLL_BITS = Paint.FILTER_BITMAP_FLAG |
-                                           Paint.DITHER_FLAG;
-
-    private final DrawFilter mZoomFilter =
-            new PaintFlagsDrawFilter(ZOOM_BITS, Paint.LINEAR_TEXT_FLAG);
-    // If we need to trade better quality for speed, set mScrollFilter to null
-    private final DrawFilter mScrollFilter =
-            new PaintFlagsDrawFilter(SCROLL_BITS, 0);
-
-    private void drawCoreAndCursorRing(Canvas canvas, int color,
-        boolean drawCursorRing) {
-        if (mDrawHistory) {
-            canvas.scale(mZoomManager.getScale(), mZoomManager.getScale());
-            canvas.drawPicture(mHistoryPicture);
-            return;
-        }
-        if (mNativeClass == 0) return;
-
-        boolean animateZoom = mZoomManager.isFixedLengthAnimationInProgress();
-        boolean animateScroll = ((!mScroller.isFinished()
-                || mVelocityTracker != null)
-                && (mTouchMode != TOUCH_DRAG_MODE ||
-                mHeldMotionless != MOTIONLESS_TRUE))
-                || mDeferTouchMode == TOUCH_DRAG_MODE;
-        if (mTouchMode == TOUCH_DRAG_MODE) {
-            if (mHeldMotionless == MOTIONLESS_PENDING) {
-                mPrivateHandler.removeMessages(DRAG_HELD_MOTIONLESS);
-                mPrivateHandler.removeMessages(AWAKEN_SCROLL_BARS);
-                mHeldMotionless = MOTIONLESS_FALSE;
-            }
-            if (mHeldMotionless == MOTIONLESS_FALSE) {
-                mPrivateHandler.sendMessageDelayed(mPrivateHandler
-                        .obtainMessage(DRAG_HELD_MOTIONLESS), MOTIONLESS_TIME);
-                mPrivateHandler.sendMessageDelayed(mPrivateHandler
-                        .obtainMessage(AWAKEN_SCROLL_BARS),
-                            ViewConfiguration.getScrollDefaultDelay());
-                mHeldMotionless = MOTIONLESS_PENDING;
-            }
-        }
-        int saveCount = canvas.save();
-        if (animateZoom) {
-            mZoomManager.animateZoom(canvas);
-        } else if (!canvas.isHardwareAccelerated()) {
-            canvas.scale(mZoomManager.getScale(), mZoomManager.getScale());
-        }
-
-        boolean UIAnimationsRunning = false;
-        // Currently for each draw we compute the animation values;
-        // We may in the future decide to do that independently.
-        if (mNativeClass != 0 && !canvas.isHardwareAccelerated()
-                && nativeEvaluateLayersAnimations(mNativeClass)) {
-            UIAnimationsRunning = true;
-            // If we have unfinished (or unstarted) animations,
-            // we ask for a repaint. We only need to do this in software
-            // rendering (with hardware rendering we already have a different
-            // method of requesting a repaint)
-            mWebViewCore.sendMessage(EventHub.NOTIFY_ANIMATION_STARTED);
-            invalidate();
-        }
-
-        // decide which adornments to draw
-        int extras = DRAW_EXTRAS_NONE;
-        if (!mFindIsUp) {
-            if (mSelectingText) {
-                extras = DRAW_EXTRAS_SELECTION;
-            } else if (drawCursorRing) {
-                extras = DRAW_EXTRAS_CURSOR_RING;
-            }
-        }
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "mFindIsUp=" + mFindIsUp
-                    + " mSelectingText=" + mSelectingText
-                    + " nativePageShouldHandleShiftAndArrows()="
-                    + nativePageShouldHandleShiftAndArrows()
-                    + " animateZoom=" + animateZoom
-                    + " extras=" + extras);
-        }
-
-        calcOurContentVisibleRectF(mVisibleContentRect);
-        if (canvas.isHardwareAccelerated()) {
-            Rect glRectViewport = mGLViewportEmpty ? null : mGLRectViewport;
-            Rect viewRectViewport = mGLViewportEmpty ? null : mViewRectViewport;
-
-            int functor = nativeGetDrawGLFunction(mNativeClass, glRectViewport,
-                    viewRectViewport, mVisibleContentRect, getScale(), extras);
-            ((HardwareCanvas) canvas).callDrawGLFunction(functor);
-            if (mHardwareAccelSkia != getSettings().getHardwareAccelSkiaEnabled()) {
-                mHardwareAccelSkia = getSettings().getHardwareAccelSkiaEnabled();
-                nativeUseHardwareAccelSkia(mHardwareAccelSkia);
-            }
-
-        } else {
-            DrawFilter df = null;
-            if (mZoomManager.isZoomAnimating() || UIAnimationsRunning) {
-                df = mZoomFilter;
-            } else if (animateScroll) {
-                df = mScrollFilter;
-            }
-            canvas.setDrawFilter(df);
-            // XXX: Revisit splitting content.  Right now it causes a
-            // synchronization problem with layers.
-            int content = nativeDraw(canvas, mVisibleContentRect, color,
-                    extras, false);
-            canvas.setDrawFilter(null);
-            if (!mBlockWebkitViewMessages && content != 0) {
-                mWebViewCore.sendMessage(EventHub.SPLIT_PICTURE_SET, content, 0);
-            }
-        }
-
-        canvas.restoreToCount(saveCount);
-        if (mSelectingText) {
-            drawTextSelectionHandles(canvas);
-        }
-
-        if (extras == DRAW_EXTRAS_CURSOR_RING) {
-            if (mTouchMode == TOUCH_SHORTPRESS_START_MODE) {
-                mTouchMode = TOUCH_SHORTPRESS_MODE;
-            }
-        }
-        if (mFocusSizeChanged) {
-            mFocusSizeChanged = false;
-            // If we are zooming, this will get handled above, when the zoom
-            // finishes.  We also do not need to do this unless the WebTextView
-            // is showing. With hardware acceleration, the pageSwapCallback()
-            // updates the WebTextView position in sync with page swapping
-            if (!canvas.isHardwareAccelerated() && !animateZoom && inEditingMode()) {
-                didUpdateWebTextViewDimensions(ANYWHERE);
-            }
-        }
-    }
-
-    private void drawTextSelectionHandles(Canvas canvas) {
-        int[] handles = new int[4];
-        getSelectionHandles(handles);
-        int start_x = contentToViewDimension(handles[0]);
-        int start_y = contentToViewDimension(handles[1]);
-        int end_x = contentToViewDimension(handles[2]);
-        int end_y = contentToViewDimension(handles[3]);
-
-        if (mIsCaretSelection) {
-            if (mSelectHandleCenter == null) {
-                mSelectHandleCenter = mContext.getResources().getDrawable(
-                        com.android.internal.R.drawable.text_select_handle_middle);
-            }
-            // Caret handle is centered
-            start_x -= (mSelectHandleCenter.getIntrinsicWidth() / 2);
-            mSelectHandleCenter.setBounds(start_x, start_y,
-                    start_x + mSelectHandleCenter.getIntrinsicWidth(),
-                    start_y + mSelectHandleCenter.getIntrinsicHeight());
-            mSelectHandleCenter.draw(canvas);
-        } else {
-            if (mSelectHandleLeft == null) {
-                mSelectHandleLeft = mContext.getResources().getDrawable(
-                        com.android.internal.R.drawable.text_select_handle_left);
-            }
-            // Magic formula copied from TextView
-            start_x -= (mSelectHandleLeft.getIntrinsicWidth() * 3) / 4;
-            mSelectHandleLeft.setBounds(start_x, start_y,
-                    start_x + mSelectHandleLeft.getIntrinsicWidth(),
-                    start_y + mSelectHandleLeft.getIntrinsicHeight());
-            if (mSelectHandleRight == null) {
-                mSelectHandleRight = mContext.getResources().getDrawable(
-                        com.android.internal.R.drawable.text_select_handle_right);
-            }
-            end_x -= mSelectHandleRight.getIntrinsicWidth() / 4;
-            mSelectHandleRight.setBounds(end_x, end_y,
-                    end_x + mSelectHandleRight.getIntrinsicWidth(),
-                    end_y + mSelectHandleRight.getIntrinsicHeight());
-            mSelectHandleLeft.draw(canvas);
-            mSelectHandleRight.draw(canvas);
-        }
-    }
-
-    /**
-     * Takes an int[4] array as an output param with the values being
-     * startX, startY, endX, endY
-     */
-    private void getSelectionHandles(int[] handles) {
-        handles[0] = mSelectCursorBase.right;
-        handles[1] = mSelectCursorBase.bottom -
-                (mSelectCursorBase.height() / 4);
-        handles[2] = mSelectCursorExtent.left;
-        handles[3] = mSelectCursorExtent.bottom
-                - (mSelectCursorExtent.height() / 4);
-        if (!nativeIsBaseFirst(mNativeClass)) {
-            int swap = handles[0];
-            handles[0] = handles[2];
-            handles[2] = swap;
-            swap = handles[1];
-            handles[1] = handles[3];
-            handles[3] = swap;
-        }
-    }
-
-    // draw history
-    private boolean mDrawHistory = false;
-    private Picture mHistoryPicture = null;
-    private int mHistoryWidth = 0;
-    private int mHistoryHeight = 0;
-
-    // Only check the flag, can be called from WebCore thread
-    boolean drawHistory() {
-        return mDrawHistory;
-    }
-
-    int getHistoryPictureWidth() {
-        return (mHistoryPicture != null) ? mHistoryPicture.getWidth() : 0;
-    }
-
-    // Should only be called in UI thread
-    void switchOutDrawHistory() {
-        if (null == mWebViewCore) return; // CallbackProxy may trigger this
-        if (mDrawHistory && (getProgress() == 100 || nativeHasContent())) {
-            mDrawHistory = false;
-            mHistoryPicture = null;
-            invalidate();
-            int oldScrollX = mScrollX;
-            int oldScrollY = mScrollY;
-            mScrollX = pinLocX(mScrollX);
-            mScrollY = pinLocY(mScrollY);
-            if (oldScrollX != mScrollX || oldScrollY != mScrollY) {
-                onScrollChanged(mScrollX, mScrollY, oldScrollX, oldScrollY);
-            } else {
-                sendOurVisibleRect();
-            }
-        }
-    }
-
-    // TODO: Remove this
-    WebViewCore.CursorData cursorData() {
-        if (sDisableNavcache) {
-            return new WebViewCore.CursorData(0, 0, 0, 0);
-        }
-        WebViewCore.CursorData result = cursorDataNoPosition();
-        Point position = nativeCursorPosition();
-        result.mX = position.x;
-        result.mY = position.y;
-        return result;
-    }
-
-    WebViewCore.CursorData cursorDataNoPosition() {
-        WebViewCore.CursorData result = new WebViewCore.CursorData();
-        result.mMoveGeneration = nativeMoveGeneration();
-        result.mFrame = nativeCursorFramePointer();
-        return result;
-    }
-
-    /**
-     *  Delete text from start to end in the focused textfield. If there is no
-     *  focus, or if start == end, silently fail.  If start and end are out of
-     *  order, swap them.
-     *  @param  start   Beginning of selection to delete.
-     *  @param  end     End of selection to delete.
-     */
-    /* package */ void deleteSelection(int start, int end) {
-        mTextGeneration++;
-        WebViewCore.TextSelectionData data
-                = new WebViewCore.TextSelectionData(start, end, 0);
-        mWebViewCore.sendMessage(EventHub.DELETE_SELECTION, mTextGeneration, 0,
-                data);
-    }
-
-    /**
-     *  Set the selection to (start, end) in the focused textfield. If start and
-     *  end are out of order, swap them.
-     *  @param  start   Beginning of selection.
-     *  @param  end     End of selection.
-     */
-    /* package */ void setSelection(int start, int end) {
-        if (mWebViewCore != null) {
-            mWebViewCore.sendMessage(EventHub.SET_SELECTION, start, end);
-        }
-    }
-
-    @Override
-    public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
-        if (mInputConnection == null) {
-            mInputConnection = new WebViewInputConnection();
-        }
-        mInputConnection.setupEditorInfo(outAttrs);
-        return mInputConnection;
-    }
-
-    /**
-     * Called in response to a message from webkit telling us that the soft
-     * keyboard should be launched.
-     */
-    private void displaySoftKeyboard(boolean isTextView) {
-        InputMethodManager imm = (InputMethodManager)
-                getContext().getSystemService(Context.INPUT_METHOD_SERVICE);
-
-        // bring it back to the default level scale so that user can enter text
-        boolean zoom = mZoomManager.getScale() < mZoomManager.getDefaultScale();
-        if (zoom) {
-            mZoomManager.setZoomCenter(mLastTouchX, mLastTouchY);
-            mZoomManager.setZoomScale(mZoomManager.getDefaultScale(), false);
-        }
-        if (isTextView) {
-            rebuildWebTextView();
-            if (inEditingMode()) {
-                imm.showSoftInput(mWebTextView, 0, mWebTextView.getResultReceiver());
-                if (zoom) {
-                    didUpdateWebTextViewDimensions(INTERSECTS_SCREEN);
-                }
-                return;
-            }
-        }
-        // Used by plugins and contentEditable.
-        // Also used if the navigation cache is out of date, and
-        // does not recognize that a textfield is in focus.  In that
-        // case, use WebView as the targeted view.
-        // see http://b/issue?id=2457459
-        imm.showSoftInput(this, 0);
-    }
-
-    // Called by WebKit to instruct the UI to hide the keyboard
-    private void hideSoftKeyboard() {
-        InputMethodManager imm = InputMethodManager.peekInstance();
-        if (imm != null && (imm.isActive(this)
-                || (inEditingMode() && imm.isActive(mWebTextView)))) {
-            imm.hideSoftInputFromWindow(this.getWindowToken(), 0);
-        }
-    }
-
-    /*
-     * This method checks the current focus and cursor and potentially rebuilds
-     * mWebTextView to have the appropriate properties, such as password,
-     * multiline, and what text it contains.  It also removes it if necessary.
-     */
-    /* package */ void rebuildWebTextView() {
-        if (!sEnableWebTextView) {
-            return; // always use WebKit's text entry
-        }
-        // If the WebView does not have focus, do nothing until it gains focus.
-        if (!hasFocus() && (null == mWebTextView || !mWebTextView.hasFocus())) {
-            return;
-        }
-        boolean alreadyThere = inEditingMode();
-        // inEditingMode can only return true if mWebTextView is non-null,
-        // so we can safely call remove() if (alreadyThere)
-        if (0 == mNativeClass || !nativeFocusCandidateIsTextInput()) {
-            if (alreadyThere) {
-                mWebTextView.remove();
-            }
-            return;
-        }
-        // At this point, we know we have found an input field, so go ahead
-        // and create the WebTextView if necessary.
-        if (mWebTextView == null) {
-            mWebTextView = new WebTextView(mContext, WebView.this, mAutoFillData.getQueryId());
-            // Initialize our generation number.
-            mTextGeneration = 0;
-        }
-        mWebTextView.updateTextSize();
-        updateWebTextViewPosition();
-        String text = nativeFocusCandidateText();
-        int nodePointer = nativeFocusCandidatePointer();
-        // This needs to be called before setType, which may call
-        // requestFormData, and it needs to have the correct nodePointer.
-        mWebTextView.setNodePointer(nodePointer);
-        mWebTextView.setType(nativeFocusCandidateType());
-        // Gravity needs to be set after setType
-        mWebTextView.setGravityForRtl(nativeFocusCandidateIsRtlText());
-        if (null == text) {
-            if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "rebuildWebTextView null == text");
-            }
-            text = "";
-        }
-        mWebTextView.setTextAndKeepSelection(text);
-        InputMethodManager imm = InputMethodManager.peekInstance();
-        if (imm != null && imm.isActive(mWebTextView)) {
-            imm.restartInput(mWebTextView);
-            mWebTextView.clearComposingText();
-        }
-        if (isFocused()) {
-            mWebTextView.requestFocus();
-        }
-    }
-
-    private void updateWebTextViewPosition() {
-        Rect visibleRect = new Rect();
-        calcOurContentVisibleRect(visibleRect);
-        // Note that sendOurVisibleRect calls viewToContent, so the coordinates
-        // should be in content coordinates.
-        Rect bounds = nativeFocusCandidateNodeBounds();
-        Rect vBox = contentToViewRect(bounds);
-        offsetByLayerScrollPosition(vBox);
-        mWebTextView.setRect(vBox.left, vBox.top, vBox.width(), vBox.height());
-        if (!Rect.intersects(bounds, visibleRect)) {
-            revealSelection();
-        }
-        updateWebTextViewPadding();
-    }
-
-    /**
-     * Update the padding of mWebTextView based on the native textfield/textarea
-     */
-    void updateWebTextViewPadding() {
-        Rect paddingRect = nativeFocusCandidatePaddingRect();
-        if (paddingRect != null) {
-            // Use contentToViewDimension since these are the dimensions of
-            // the padding.
-            mWebTextView.setPadding(
-                    contentToViewDimension(paddingRect.left),
-                    contentToViewDimension(paddingRect.top),
-                    contentToViewDimension(paddingRect.right),
-                    contentToViewDimension(paddingRect.bottom));
-        }
-    }
-
-    /**
-     * Tell webkit to put the cursor on screen.
-     */
-    /* package */ void revealSelection() {
-        if (mWebViewCore != null) {
-            mWebViewCore.sendMessage(EventHub.REVEAL_SELECTION);
-        }
-    }
-
-    /**
-     * Called by WebTextView to find saved form data associated with the
-     * textfield
-     * @param name Name of the textfield.
-     * @param nodePointer Pointer to the node of the textfield, so it can be
-     *          compared to the currently focused textfield when the data is
-     *          retrieved.
-     * @param autoFillable true if WebKit has determined this field is part of
-     *          a form that can be auto filled.
-     * @param autoComplete true if the attribute "autocomplete" is set to true
-     *          on the textfield.
-     */
-    /* package */ void requestFormData(String name, int nodePointer,
-            boolean autoFillable, boolean autoComplete) {
-        if (mWebViewCore.getSettings().getSaveFormData()) {
-            Message update = mPrivateHandler.obtainMessage(REQUEST_FORM_DATA);
-            update.arg1 = nodePointer;
-            RequestFormData updater = new RequestFormData(name, getUrl(),
-                    update, autoFillable, autoComplete);
-            Thread t = new Thread(updater);
-            t.start();
-        }
-    }
-
-    /**
-     * Pass a message to find out the <label> associated with the <input>
-     * identified by nodePointer
-     * @param framePointer Pointer to the frame containing the <input> node
-     * @param nodePointer Pointer to the node for which a <label> is desired.
-     */
-    /* package */ void requestLabel(int framePointer, int nodePointer) {
-        mWebViewCore.sendMessage(EventHub.REQUEST_LABEL, framePointer,
-                nodePointer);
-    }
-
-    /*
-     * This class requests an Adapter for the WebTextView which shows past
-     * entries stored in the database.  It is a Runnable so that it can be done
-     * in its own thread, without slowing down the UI.
-     */
-    private class RequestFormData implements Runnable {
-        private String mName;
-        private String mUrl;
-        private Message mUpdateMessage;
-        private boolean mAutoFillable;
-        private boolean mAutoComplete;
-        private WebSettings mWebSettings;
-
-        public RequestFormData(String name, String url, Message msg,
-                boolean autoFillable, boolean autoComplete) {
-            mName = name;
-            mUrl = WebTextView.urlForAutoCompleteData(url);
-            mUpdateMessage = msg;
-            mAutoFillable = autoFillable;
-            mAutoComplete = autoComplete;
-            mWebSettings = getSettings();
-        }
-
-        @Override
-        public void run() {
-            ArrayList<String> pastEntries = new ArrayList<String>();
-
-            if (mAutoFillable) {
-                // Note that code inside the adapter click handler in WebTextView depends
-                // on the AutoFill item being at the top of the drop down list. If you change
-                // the order, make sure to do it there too!
-                if (mWebSettings != null && mWebSettings.getAutoFillProfile() != null) {
-                    pastEntries.add(getResources().getText(
-                            com.android.internal.R.string.autofill_this_form).toString() +
-                            " " +
-                            mAutoFillData.getPreviewString());
-                    mWebTextView.setAutoFillProfileIsSet(true);
-                } else {
-                    // There is no autofill profile set up yet, so add an option that
-                    // will invite the user to set their profile up.
-                    pastEntries.add(getResources().getText(
-                            com.android.internal.R.string.setup_autofill).toString());
-                    mWebTextView.setAutoFillProfileIsSet(false);
-                }
-            }
-
-            if (mAutoComplete) {
-                pastEntries.addAll(mDatabase.getFormData(mUrl, mName));
-            }
-
-            if (pastEntries.size() > 0) {
-                AutoCompleteAdapter adapter = new
-                        AutoCompleteAdapter(mContext, pastEntries);
-                mUpdateMessage.obj = adapter;
-                mUpdateMessage.sendToTarget();
-            }
-        }
-    }
-
-    /**
-     * Dump the display tree to "/sdcard/displayTree.txt"
-     *
-     * @hide debug only
-     */
-    public void dumpDisplayTree() {
-        nativeDumpDisplayTree(getUrl());
-    }
-
-    /**
-     * Dump the dom tree to adb shell if "toFile" is False, otherwise dump it to
-     * "/sdcard/domTree.txt"
-     *
-     * @hide debug only
-     */
-    public void dumpDomTree(boolean toFile) {
-        mWebViewCore.sendMessage(EventHub.DUMP_DOMTREE, toFile ? 1 : 0, 0);
-    }
-
-    /**
-     * Dump the render tree to adb shell if "toFile" is False, otherwise dump it
-     * to "/sdcard/renderTree.txt"
-     *
-     * @hide debug only
-     */
-    public void dumpRenderTree(boolean toFile) {
-        mWebViewCore.sendMessage(EventHub.DUMP_RENDERTREE, toFile ? 1 : 0, 0);
-    }
-
-    /**
-     * Called by DRT on UI thread, need to proxy to WebCore thread.
-     *
-     * @hide debug only
-     */
-    public void useMockDeviceOrientation() {
-        mWebViewCore.sendMessage(EventHub.USE_MOCK_DEVICE_ORIENTATION);
-    }
-
-    /**
-     * Called by DRT on WebCore thread.
-     *
-     * @hide debug only
-     */
-    public void setMockDeviceOrientation(boolean canProvideAlpha, double alpha,
-            boolean canProvideBeta, double beta, boolean canProvideGamma, double gamma) {
-        mWebViewCore.setMockDeviceOrientation(canProvideAlpha, alpha, canProvideBeta, beta,
-                canProvideGamma, gamma);
-    }
-
-    // This is used to determine long press with the center key.  Does not
-    // affect long press with the trackball/touch.
-    private boolean mGotCenterDown = false;
-
-    @Override
-    public boolean onKeyMultiple(int keyCode, int repeatCount, KeyEvent event) {
-        if (mBlockWebkitViewMessages) {
-            return false;
-        }
-        // send complex characters to webkit for use by JS and plugins
-        if (keyCode == KeyEvent.KEYCODE_UNKNOWN && event.getCharacters() != null) {
-            // pass the key to DOM
-            mWebViewCore.sendMessage(EventHub.KEY_DOWN, event);
-            mWebViewCore.sendMessage(EventHub.KEY_UP, event);
-            // return true as DOM handles the key
-            return true;
-        }
-        return false;
-    }
-
-    private boolean isEnterActionKey(int keyCode) {
-        return keyCode == KeyEvent.KEYCODE_DPAD_CENTER
-                || keyCode == KeyEvent.KEYCODE_ENTER
-                || keyCode == KeyEvent.KEYCODE_NUMPAD_ENTER;
-    }
-
-    @Override
-    public boolean onKeyDown(int keyCode, KeyEvent event) {
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "keyDown at " + System.currentTimeMillis()
-                    + "keyCode=" + keyCode
-                    + ", " + event + ", unicode=" + event.getUnicodeChar());
-        }
-        if (mIsCaretSelection) {
-            selectionDone();
-        }
-        if (mBlockWebkitViewMessages) {
-            return false;
-        }
-
-        // don't implement accelerator keys here; defer to host application
-        if (event.isCtrlPressed()) {
-            return false;
-        }
-
-        if (mNativeClass == 0) {
-            return false;
-        }
-
-        // do this hack up front, so it always works, regardless of touch-mode
-        if (AUTO_REDRAW_HACK && (keyCode == KeyEvent.KEYCODE_CALL)) {
-            mAutoRedraw = !mAutoRedraw;
-            if (mAutoRedraw) {
-                invalidate();
-            }
-            return true;
-        }
-
-        // Bubble up the key event if
-        // 1. it is a system key; or
-        // 2. the host application wants to handle it;
-        if (event.isSystem()
-                || mCallbackProxy.uiOverrideKeyEvent(event)) {
-            return false;
-        }
-
-        // accessibility support
-        if (accessibilityScriptInjected()) {
-            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
-                // if an accessibility script is injected we delegate to it the key handling.
-                // this script is a screen reader which is a fully fledged solution for blind
-                // users to navigate in and interact with web pages.
-                mWebViewCore.sendMessage(EventHub.KEY_DOWN, event);
-                return true;
-            } else {
-                // Clean up if accessibility was disabled after loading the current URL.
-                mAccessibilityScriptInjected = false;
-            }
-        } else if (mAccessibilityInjector != null) {
-            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
-                if (mAccessibilityInjector.onKeyEvent(event)) {
-                    // if an accessibility injector is present (no JavaScript enabled or the site
-                    // opts out injecting our JavaScript screen reader) we let it decide whether
-                    // to act on and consume the event.
-                    return true;
-                }
-            } else {
-                // Clean up if accessibility was disabled after loading the current URL.
-                mAccessibilityInjector = null;
-            }
-        }
-
-        if (keyCode == KeyEvent.KEYCODE_PAGE_UP) {
-            if (event.hasNoModifiers()) {
-                pageUp(false);
-                return true;
-            } else if (event.hasModifiers(KeyEvent.META_ALT_ON)) {
-                pageUp(true);
-                return true;
-            }
-        }
-
-        if (keyCode == KeyEvent.KEYCODE_PAGE_DOWN) {
-            if (event.hasNoModifiers()) {
-                pageDown(false);
-                return true;
-            } else if (event.hasModifiers(KeyEvent.META_ALT_ON)) {
-                pageDown(true);
-                return true;
-            }
-        }
-
-        if (keyCode == KeyEvent.KEYCODE_MOVE_HOME && event.hasNoModifiers()) {
-            pageUp(true);
-            return true;
-        }
-
-        if (keyCode == KeyEvent.KEYCODE_MOVE_END && event.hasNoModifiers()) {
-            pageDown(true);
-            return true;
-        }
-
-        if (keyCode >= KeyEvent.KEYCODE_DPAD_UP
-                && keyCode <= KeyEvent.KEYCODE_DPAD_RIGHT) {
-            switchOutDrawHistory();
-            if (nativePageShouldHandleShiftAndArrows()) {
-                letPageHandleNavKey(keyCode, event.getEventTime(), true, event.getMetaState());
-                return true;
-            }
-            if (event.hasModifiers(KeyEvent.META_ALT_ON)) {
-                switch (keyCode) {
-                    case KeyEvent.KEYCODE_DPAD_UP:
-                        pageUp(true);
-                        return true;
-                    case KeyEvent.KEYCODE_DPAD_DOWN:
-                        pageDown(true);
-                        return true;
-                    case KeyEvent.KEYCODE_DPAD_LEFT:
-                        nativeClearCursor(); // start next trackball movement from page edge
-                        return pinScrollTo(0, mScrollY, true, 0);
-                    case KeyEvent.KEYCODE_DPAD_RIGHT:
-                        nativeClearCursor(); // start next trackball movement from page edge
-                        return pinScrollTo(mContentWidth, mScrollY, true, 0);
-                }
-            }
-            if (navHandledKey(keyCode, 1, false, event.getEventTime())) {
-                playSoundEffect(keyCodeToSoundsEffect(keyCode));
-                return true;
-            }
-            // Bubble up the key event as WebView doesn't handle it
-            return false;
-        }
-
-        if (isEnterActionKey(keyCode)) {
-            switchOutDrawHistory();
-            boolean wantsKeyEvents = nativeCursorNodePointer() == 0
-                || nativeCursorWantsKeyEvents();
-            if (event.getRepeatCount() == 0) {
-                if (mSelectingText) {
-                    return true; // discard press if copy in progress
-                }
-                mGotCenterDown = true;
-                mPrivateHandler.sendMessageDelayed(mPrivateHandler
-                        .obtainMessage(LONG_PRESS_CENTER), LONG_PRESS_TIMEOUT);
-                if (!wantsKeyEvents) return true;
-            }
-            // Bubble up the key event as WebView doesn't handle it
-            if (!wantsKeyEvents) return false;
-        }
-
-        if (getSettings().getNavDump()) {
-            switch (keyCode) {
-                case KeyEvent.KEYCODE_4:
-                    dumpDisplayTree();
-                    break;
-                case KeyEvent.KEYCODE_5:
-                case KeyEvent.KEYCODE_6:
-                    dumpDomTree(keyCode == KeyEvent.KEYCODE_5);
-                    break;
-                case KeyEvent.KEYCODE_7:
-                case KeyEvent.KEYCODE_8:
-                    dumpRenderTree(keyCode == KeyEvent.KEYCODE_7);
-                    break;
-            }
-        }
-
-        if (nativeCursorIsTextInput()) {
-            // This message will put the node in focus, for the DOM's notion
-            // of focus.
-            mWebViewCore.sendMessage(EventHub.FAKE_CLICK, nativeCursorFramePointer(),
-                    nativeCursorNodePointer());
-            // This will bring up the WebTextView and put it in focus, for
-            // our view system's notion of focus
-            rebuildWebTextView();
-            // Now we need to pass the event to it
-            if (inEditingMode()) {
-                mWebTextView.setDefaultSelection();
-                return mWebTextView.dispatchKeyEvent(event);
-            }
-        } else if (nativeHasFocusNode()) {
-            // In this case, the cursor is not on a text input, but the focus
-            // might be.  Check it, and if so, hand over to the WebTextView.
-            rebuildWebTextView();
-            if (inEditingMode()) {
-                mWebTextView.setDefaultSelection();
-                return mWebTextView.dispatchKeyEvent(event);
-            }
-        }
-
-        // TODO: should we pass all the keys to DOM or check the meta tag
-        if (nativeCursorWantsKeyEvents() || true) {
-            // pass the key to DOM
-            mWebViewCore.sendMessage(EventHub.KEY_DOWN, event);
-            // return true as DOM handles the key
-            return true;
-        }
-
-        // Bubble up the key event as WebView doesn't handle it
-        return false;
-    }
-
-    @Override
-    public boolean onKeyUp(int keyCode, KeyEvent event) {
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "keyUp at " + System.currentTimeMillis()
-                    + ", " + event + ", unicode=" + event.getUnicodeChar());
-        }
-        if (mBlockWebkitViewMessages) {
-            return false;
-        }
-
-        if (mNativeClass == 0) {
-            return false;
-        }
-
-        // special CALL handling when cursor node's href is "tel:XXX"
-        if (keyCode == KeyEvent.KEYCODE_CALL && nativeHasCursorNode()) {
-            String text = nativeCursorText();
-            if (!nativeCursorIsTextInput() && text != null
-                    && text.startsWith(SCHEME_TEL)) {
-                Intent intent = new Intent(Intent.ACTION_DIAL, Uri.parse(text));
-                getContext().startActivity(intent);
-                return true;
-            }
-        }
-
-        // Bubble up the key event if
-        // 1. it is a system key; or
-        // 2. the host application wants to handle it;
-        if (event.isSystem()
-                || mCallbackProxy.uiOverrideKeyEvent(event)) {
-            return false;
-        }
-
-        // accessibility support
-        if (accessibilityScriptInjected()) {
-            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
-                // if an accessibility script is injected we delegate to it the key handling.
-                // this script is a screen reader which is a fully fledged solution for blind
-                // users to navigate in and interact with web pages.
-                mWebViewCore.sendMessage(EventHub.KEY_UP, event);
-                return true;
-            } else {
-                // Clean up if accessibility was disabled after loading the current URL.
-                mAccessibilityScriptInjected = false;
-            }
-        } else if (mAccessibilityInjector != null) {
-            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
-                if (mAccessibilityInjector.onKeyEvent(event)) {
-                    // if an accessibility injector is present (no JavaScript enabled or the site
-                    // opts out injecting our JavaScript screen reader) we let it decide whether to
-                    // act on and consume the event.
-                    return true;
-                }
-            } else {
-                // Clean up if accessibility was disabled after loading the current URL.
-                mAccessibilityInjector = null;
-            }
-        }
-
-        if (keyCode >= KeyEvent.KEYCODE_DPAD_UP
-                && keyCode <= KeyEvent.KEYCODE_DPAD_RIGHT) {
-            if (nativePageShouldHandleShiftAndArrows()) {
-                letPageHandleNavKey(keyCode, event.getEventTime(), false, event.getMetaState());
-                return true;
-            }
-            // always handle the navigation keys in the UI thread
-            // Bubble up the key event as WebView doesn't handle it
-            return false;
-        }
-
-        if (isEnterActionKey(keyCode)) {
-            // remove the long press message first
-            mPrivateHandler.removeMessages(LONG_PRESS_CENTER);
-            mGotCenterDown = false;
-
-            if (mSelectingText) {
-                copySelection();
-                selectionDone();
-                return true; // discard press if copy in progress
-            }
-
-            if (!sDisableNavcache) {
-                // perform the single click
-                Rect visibleRect = sendOurVisibleRect();
-                // Note that sendOurVisibleRect calls viewToContent, so the
-                // coordinates should be in content coordinates.
-                if (!nativeCursorIntersects(visibleRect)) {
-                    return false;
-                }
-                WebViewCore.CursorData data = cursorData();
-                mWebViewCore.sendMessage(EventHub.SET_MOVE_MOUSE, data);
-                playSoundEffect(SoundEffectConstants.CLICK);
-                if (nativeCursorIsTextInput()) {
-                    rebuildWebTextView();
-                    centerKeyPressOnTextField();
-                    if (inEditingMode()) {
-                        mWebTextView.setDefaultSelection();
-                    }
-                    return true;
-                }
-                clearTextEntry();
-                nativeShowCursorTimed();
-                if (mCallbackProxy.uiOverrideUrlLoading(nativeCursorText())) {
-                    return true;
-                }
-                if (nativeCursorNodePointer() != 0 && !nativeCursorWantsKeyEvents()) {
-                    mWebViewCore.sendMessage(EventHub.CLICK, data.mFrame,
-                            nativeCursorNodePointer());
-                    return true;
-                }
-            }
-        }
-
-        // TODO: should we pass all the keys to DOM or check the meta tag
-        if (nativeCursorWantsKeyEvents() || true) {
-            // pass the key to DOM
-            mWebViewCore.sendMessage(EventHub.KEY_UP, event);
-            // return true as DOM handles the key
-            return true;
-        }
-
-        // Bubble up the key event as WebView doesn't handle it
-        return false;
-    }
-
-    private boolean startSelectActionMode() {
-        mSelectCallback = new SelectActionModeCallback();
-        mSelectCallback.setTextSelected(!mIsCaretSelection);
-        mSelectCallback.setWebView(this);
-        if (startActionMode(mSelectCallback) == null) {
-            // There is no ActionMode, so do not allow the user to modify a
-            // selection.
-            selectionDone();
-            return false;
-        }
-        performHapticFeedback(HapticFeedbackConstants.LONG_PRESS);
-        return true;
-    }
-
-    private void showPasteWindow() {
-        ClipboardManager cm = (ClipboardManager)(mContext
-                .getSystemService(Context.CLIPBOARD_SERVICE));
-        if (cm.hasPrimaryClip()) {
-            Rect cursorRect = contentToViewRect(mSelectCursorBase);
-            int[] location = new int[2];
-            getLocationInWindow(location);
-            cursorRect.offset(location[0] - mScrollX, location[1] - mScrollY);
-            if (mPasteWindow == null) {
-                mPasteWindow = new PastePopupWindow();
-            }
-            mPasteWindow.show(cursorRect, location[0], location[1]);
-        }
-    }
-
-    private void hidePasteButton() {
-        if (mPasteWindow != null) {
-            mPasteWindow.hide();
-        }
-    }
-
-    private void syncSelectionCursors() {
-        mSelectCursorBaseLayerId =
-                nativeGetHandleLayerId(mNativeClass, HANDLE_ID_BASE, mSelectCursorBase);
-        mSelectCursorExtentLayerId =
-                nativeGetHandleLayerId(mNativeClass, HANDLE_ID_EXTENT, mSelectCursorExtent);
-    }
-
-    private boolean setupWebkitSelect() {
-        syncSelectionCursors();
-        if (mIsCaretSelection) {
-            showPasteWindow();
-        } else if (!startSelectActionMode()) {
-            selectionDone();
-            return false;
-        }
-        mSelectingText = true;
-        mTouchMode = TOUCH_DRAG_MODE;
-        return true;
-    }
-
-    private void updateWebkitSelection() {
-        int[] handles = null;
-        if (mIsCaretSelection) {
-            mSelectCursorExtent.set(mSelectCursorBase);
-        }
-        if (mSelectingText) {
-            handles = new int[4];
-            handles[0] = mSelectCursorBase.centerX();
-            handles[1] = mSelectCursorBase.centerY();
-            handles[2] = mSelectCursorExtent.centerX();
-            handles[3] = mSelectCursorExtent.centerY();
-        } else {
-            nativeSetTextSelection(mNativeClass, 0);
-        }
-        mWebViewCore.removeMessages(EventHub.SELECT_TEXT);
-        mWebViewCore.sendMessageAtFrontOfQueue(EventHub.SELECT_TEXT, handles);
-    }
-
-    private void resetCaretTimer() {
-        mPrivateHandler.removeMessages(CLEAR_CARET_HANDLE);
-        if (!mSelectionStarted) {
-            mPrivateHandler.sendEmptyMessageDelayed(CLEAR_CARET_HANDLE,
-                    CARET_HANDLE_STAMINA_MS);
-        }
-    }
-
     /**
      * Use this method to put the WebView into text selection mode.
      * Do not rely on this functionality; it will be deprecated in the future.
@@ -6149,165 +1433,7 @@
     @Deprecated
     public void emulateShiftHeld() {
         checkThread();
-    }
-
-    /**
-     * Select all of the text in this WebView.
-     *
-     * @hide This is an implementation detail.
-     */
-    public void selectAll() {
-        mWebViewCore.sendMessage(EventHub.SELECT_ALL);
-    }
-
-    /**
-     * Called when the selection has been removed.
-     */
-    void selectionDone() {
-        if (mSelectingText) {
-            hidePasteButton();
-            mSelectingText = false;
-            // finish is idempotent, so this is fine even if selectionDone was
-            // called by mSelectCallback.onDestroyActionMode
-            if (mSelectCallback != null) {
-                mSelectCallback.finish();
-                mSelectCallback = null;
-            }
-            if (!mIsCaretSelection) {
-                updateWebkitSelection();
-            }
-            mIsCaretSelection = false;
-            invalidate(); // redraw without selection
-            mAutoScrollX = 0;
-            mAutoScrollY = 0;
-            mSentAutoScrollMessage = false;
-        }
-    }
-
-    /**
-     * Copy the selection to the clipboard
-     *
-     * @hide This is an implementation detail.
-     */
-    public boolean copySelection() {
-        boolean copiedSomething = false;
-        String selection = getSelection();
-        if (selection != null && selection != "") {
-            if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "copySelection \"" + selection + "\"");
-            }
-            Toast.makeText(mContext
-                    , com.android.internal.R.string.text_copied
-                    , Toast.LENGTH_SHORT).show();
-            copiedSomething = true;
-            ClipboardManager cm = (ClipboardManager)getContext()
-                    .getSystemService(Context.CLIPBOARD_SERVICE);
-            cm.setText(selection);
-            int[] handles = new int[4];
-            getSelectionHandles(handles);
-            mWebViewCore.sendMessage(EventHub.COPY_TEXT, handles);
-        }
-        invalidate(); // remove selection region and pointer
-        return copiedSomething;
-    }
-
-    /**
-     * Cut the selected text into the clipboard
-     *
-     * @hide This is an implementation detail
-     */
-    public void cutSelection() {
-        copySelection();
-        int[] handles = new int[4];
-        getSelectionHandles(handles);
-        mWebViewCore.sendMessage(EventHub.DELETE_TEXT, handles);
-    }
-
-    /**
-     * Paste text from the clipboard to the cursor position.
-     *
-     * @hide This is an implementation detail
-     */
-    public void pasteFromClipboard() {
-        ClipboardManager cm = (ClipboardManager)getContext()
-                .getSystemService(Context.CLIPBOARD_SERVICE);
-        ClipData clipData = cm.getPrimaryClip();
-        if (clipData != null) {
-            ClipData.Item clipItem = clipData.getItemAt(0);
-            CharSequence pasteText = clipItem.getText();
-            if (mInputConnection != null) {
-                mInputConnection.replaceSelection(pasteText);
-            }
-        }
-    }
-
-    /**
-     * @hide This is an implementation detail.
-     */
-    public SearchBox getSearchBox() {
-        if ((mWebViewCore == null) || (mWebViewCore.getBrowserFrame() == null)) {
-            return null;
-        }
-        return mWebViewCore.getBrowserFrame().getSearchBox();
-    }
-
-    /**
-     * Returns the currently highlighted text as a string.
-     */
-    String getSelection() {
-        if (mNativeClass == 0) return "";
-        return nativeGetSelection();
-    }
-
-    @Override
-    protected void onAttachedToWindow() {
-        super.onAttachedToWindow();
-        if (hasWindowFocus()) setActive(true);
-        final ViewTreeObserver treeObserver = getViewTreeObserver();
-        if (mGlobalLayoutListener == null) {
-            mGlobalLayoutListener = new InnerGlobalLayoutListener();
-            treeObserver.addOnGlobalLayoutListener(mGlobalLayoutListener);
-        }
-        if (mScrollChangedListener == null) {
-            mScrollChangedListener = new InnerScrollChangedListener();
-            treeObserver.addOnScrollChangedListener(mScrollChangedListener);
-        }
-
-        addAccessibilityApisToJavaScript();
-
-        mTouchEventQueue.reset();
-    }
-
-    @Override
-    protected void onDetachedFromWindow() {
-        clearHelpers();
-        mZoomManager.dismissZoomPicker();
-        if (hasWindowFocus()) setActive(false);
-
-        final ViewTreeObserver treeObserver = getViewTreeObserver();
-        if (mGlobalLayoutListener != null) {
-            treeObserver.removeGlobalOnLayoutListener(mGlobalLayoutListener);
-            mGlobalLayoutListener = null;
-        }
-        if (mScrollChangedListener != null) {
-            treeObserver.removeOnScrollChangedListener(mScrollChangedListener);
-            mScrollChangedListener = null;
-        }
-
-        removeAccessibilityApisFromJavaScript();
-
-        super.onDetachedFromWindow();
-    }
-
-    @Override
-    protected void onVisibilityChanged(View changedView, int visibility) {
-        super.onVisibilityChanged(changedView, visibility);
-        // The zoomManager may be null if the webview is created from XML that
-        // specifies the view's visibility param as not visible (see http://b/2794841)
-        if (visibility != View.VISIBLE && mZoomManager != null) {
-            mZoomManager.dismissZoomPicker();
-        }
-        updateDrawingState();
+        mProvider.emulateShiftHeld();
     }
 
     /**
@@ -6338,1571 +1464,15 @@
     public void onGlobalFocusChanged(View oldFocus, View newFocus) {
     }
 
-    void setActive(boolean active) {
-        if (active) {
-            if (hasFocus()) {
-                // If our window regained focus, and we have focus, then begin
-                // drawing the cursor ring
-                mDrawCursorRing = !inEditingMode();
-                setFocusControllerActive(true);
-            } else {
-                mDrawCursorRing = false;
-                if (!inEditingMode()) {
-                    // If our window gained focus, but we do not have it, do not
-                    // draw the cursor ring.
-                    setFocusControllerActive(false);
-                }
-                // We do not call recordButtons here because we assume
-                // that when we lost focus, or window focus, it got called with
-                // false for the first parameter
-            }
-        } else {
-            if (!mZoomManager.isZoomPickerVisible()) {
-                /*
-                 * The external zoom controls come in their own window, so our
-                 * window loses focus. Our policy is to not draw the cursor ring
-                 * if our window is not focused, but this is an exception since
-                 * the user can still navigate the web page with the zoom
-                 * controls showing.
-                 */
-                mDrawCursorRing = false;
-            }
-            mKeysPressed.clear();
-            mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-            mTouchMode = TOUCH_DONE_MODE;
-            setFocusControllerActive(false);
-        }
-        invalidate();
-    }
-
-    // To avoid drawing the cursor ring, and remove the TextView when our window
-    // loses focus.
-    @Override
-    public void onWindowFocusChanged(boolean hasWindowFocus) {
-        setActive(hasWindowFocus);
-        if (hasWindowFocus) {
-            JWebCoreJavaBridge.setActiveWebView(this);
-            if (mPictureUpdatePausedForFocusChange) {
-                WebViewCore.resumeUpdatePicture(mWebViewCore);
-                mPictureUpdatePausedForFocusChange = false;
-            }
-        } else {
-            JWebCoreJavaBridge.removeActiveWebView(this);
-            final WebSettings settings = getSettings();
-            if (settings != null && settings.enableSmoothTransition() &&
-                    mWebViewCore != null && !WebViewCore.isUpdatePicturePaused(mWebViewCore)) {
-                WebViewCore.pauseUpdatePicture(mWebViewCore);
-                mPictureUpdatePausedForFocusChange = true;
-            }
-        }
-        super.onWindowFocusChanged(hasWindowFocus);
-    }
-
-    /*
-     * Pass a message to WebCore Thread, telling the WebCore::Page's
-     * FocusController to be  "inactive" so that it will
-     * not draw the blinking cursor.  It gets set to "active" to draw the cursor
-     * in WebViewCore.cpp, when the WebCore thread receives key events/clicks.
-     */
-    /* package */ void setFocusControllerActive(boolean active) {
-        if (mWebViewCore == null) return;
-        mWebViewCore.sendMessage(EventHub.SET_ACTIVE, active ? 1 : 0, 0);
-        // Need to send this message after the document regains focus.
-        if (active && mListBoxMessage != null) {
-            mWebViewCore.sendMessage(mListBoxMessage);
-            mListBoxMessage = null;
-        }
-    }
-
-    @Override
-    protected void onFocusChanged(boolean focused, int direction,
-            Rect previouslyFocusedRect) {
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "MT focusChanged " + focused + ", " + direction);
-        }
-        if (focused) {
-            // When we regain focus, if we have window focus, resume drawing
-            // the cursor ring
-            if (hasWindowFocus()) {
-                mDrawCursorRing = !inEditingMode();
-                setFocusControllerActive(true);
-            //} else {
-                // The WebView has gained focus while we do not have
-                // windowfocus.  When our window lost focus, we should have
-                // called recordButtons(false...)
-            }
-        } else {
-            // When we lost focus, unless focus went to the TextView (which is
-            // true if we are in editing mode), stop drawing the cursor ring.
-            mDrawCursorRing = false;
-            if (!inEditingMode()) {
-                setFocusControllerActive(false);
-            }
-            mKeysPressed.clear();
-        }
-
-        super.onFocusChanged(focused, direction, previouslyFocusedRect);
-    }
-
-    void setGLRectViewport() {
-        // Use the getGlobalVisibleRect() to get the intersection among the parents
-        // visible == false means we're clipped - send a null rect down to indicate that
-        // we should not draw
-        boolean visible = getGlobalVisibleRect(mGLRectViewport);
-        if (visible) {
-            // Then need to invert the Y axis, just for GL
-            View rootView = getRootView();
-            int rootViewHeight = rootView.getHeight();
-            mViewRectViewport.set(mGLRectViewport);
-            int savedWebViewBottom = mGLRectViewport.bottom;
-            mGLRectViewport.bottom = rootViewHeight - mGLRectViewport.top - getVisibleTitleHeightImpl();
-            mGLRectViewport.top = rootViewHeight - savedWebViewBottom;
-            mGLViewportEmpty = false;
-        } else {
-            mGLViewportEmpty = true;
-        }
-        calcOurContentVisibleRectF(mVisibleContentRect);
-        nativeUpdateDrawGLFunction(mGLViewportEmpty ? null : mGLRectViewport,
-                mGLViewportEmpty ? null : mViewRectViewport,
-                mVisibleContentRect, getScale());
-    }
-
-    /**
-     * @hide
-     */
-    @Override
-    protected boolean setFrame(int left, int top, int right, int bottom) {
-        boolean changed = super.setFrame(left, top, right, bottom);
-        if (!changed && mHeightCanMeasure) {
-            // When mHeightCanMeasure is true, we will set mLastHeightSent to 0
-            // in WebViewCore after we get the first layout. We do call
-            // requestLayout() when we get contentSizeChanged(). But the View
-            // system won't call onSizeChanged if the dimension is not changed.
-            // In this case, we need to call sendViewSizeZoom() explicitly to
-            // notify the WebKit about the new dimensions.
-            sendViewSizeZoom(false);
-        }
-        setGLRectViewport();
-        return changed;
-    }
-
-    @Override
-    protected void onSizeChanged(int w, int h, int ow, int oh) {
-        super.onSizeChanged(w, h, ow, oh);
-
-        // adjust the max viewport width depending on the view dimensions. This
-        // is to ensure the scaling is not going insane. So do not shrink it if
-        // the view size is temporarily smaller, e.g. when soft keyboard is up.
-        int newMaxViewportWidth = (int) (Math.max(w, h) / mZoomManager.getDefaultMinZoomScale());
-        if (newMaxViewportWidth > sMaxViewportWidth) {
-            sMaxViewportWidth = newMaxViewportWidth;
-        }
-
-        mZoomManager.onSizeChanged(w, h, ow, oh);
-
-        if (mLoadedPicture != null && mDelaySetPicture == null) {
-            // Size changes normally result in a new picture
-            // Re-set the loaded picture to simulate that
-            // However, do not update the base layer as that hasn't changed
-            setNewPicture(mLoadedPicture, false);
-        }
-    }
-
-    @Override
-    protected void onScrollChanged(int l, int t, int oldl, int oldt) {
-        super.onScrollChanged(l, t, oldl, oldt);
-        if (!mInOverScrollMode) {
-            sendOurVisibleRect();
-            // update WebKit if visible title bar height changed. The logic is same
-            // as getVisibleTitleHeightImpl.
-            int titleHeight = getTitleHeight();
-            if (Math.max(titleHeight - t, 0) != Math.max(titleHeight - oldt, 0)) {
-                sendViewSizeZoom(false);
-            }
-        }
-    }
-
-    @Override
-    public boolean dispatchKeyEvent(KeyEvent event) {
-        switch (event.getAction()) {
-            case KeyEvent.ACTION_DOWN:
-                mKeysPressed.add(Integer.valueOf(event.getKeyCode()));
-                break;
-            case KeyEvent.ACTION_MULTIPLE:
-                // Always accept the action.
-                break;
-            case KeyEvent.ACTION_UP:
-                int location = mKeysPressed.indexOf(Integer.valueOf(event.getKeyCode()));
-                if (location == -1) {
-                    // We did not receive the key down for this key, so do not
-                    // handle the key up.
-                    return false;
-                } else {
-                    // We did receive the key down.  Handle the key up, and
-                    // remove it from our pressed keys.
-                    mKeysPressed.remove(location);
-                }
-                break;
-            default:
-                // Accept the action.  This should not happen, unless a new
-                // action is added to KeyEvent.
-                break;
-        }
-        if (inEditingMode() && mWebTextView.isFocused()) {
-            // Ensure that the WebTextView gets the event, even if it does
-            // not currently have a bounds.
-            return mWebTextView.dispatchKeyEvent(event);
-        } else {
-            return super.dispatchKeyEvent(event);
-        }
-    }
-
-    /*
-     * Here is the snap align logic:
-     * 1. If it starts nearly horizontally or vertically, snap align;
-     * 2. If there is a dramitic direction change, let it go;
-     *
-     * Adjustable parameters. Angle is the radians on a unit circle, limited
-     * to quadrant 1. Values range from 0f (horizontal) to PI/2 (vertical)
-     */
-    private static final float HSLOPE_TO_START_SNAP = .25f;
-    private static final float HSLOPE_TO_BREAK_SNAP = .4f;
-    private static final float VSLOPE_TO_START_SNAP = 1.25f;
-    private static final float VSLOPE_TO_BREAK_SNAP = .95f;
-    /*
-     *  These values are used to influence the average angle when entering
-     *  snap mode. If is is the first movement entering snap, we set the average
-     *  to the appropriate ideal. If the user is entering into snap after the
-     *  first movement, then we average the average angle with these values.
-     */
-    private static final float ANGLE_VERT = 2f;
-    private static final float ANGLE_HORIZ = 0f;
-    /*
-     *  The modified moving average weight.
-     *  Formula: MAV[t]=MAV[t-1] + (P[t]-MAV[t-1])/n
-     */
-    private static final float MMA_WEIGHT_N = 5;
-
-    private boolean hitFocusedPlugin(int contentX, int contentY) {
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "nativeFocusIsPlugin()=" + nativeFocusIsPlugin());
-            Rect r = nativeFocusNodeBounds();
-            Log.v(LOGTAG, "nativeFocusNodeBounds()=(" + r.left + ", " + r.top
-                    + ", " + r.right + ", " + r.bottom + ")");
-        }
-        return nativeFocusIsPlugin()
-                && nativeFocusNodeBounds().contains(contentX, contentY);
-    }
-
-    private boolean shouldForwardTouchEvent() {
-        if (mFullScreenHolder != null) return true;
-        if (mBlockWebkitViewMessages) return false;
-        return mForwardTouchEvents
-                && !mSelectingText
-                && mPreventDefault != PREVENT_DEFAULT_IGNORE
-                && mPreventDefault != PREVENT_DEFAULT_NO;
-    }
-
-    private boolean inFullScreenMode() {
-        return mFullScreenHolder != null;
-    }
-
-    private void dismissFullScreenMode() {
-        if (inFullScreenMode()) {
-            mFullScreenHolder.hide();
-            mFullScreenHolder = null;
-            invalidate();
-        }
-    }
-
-    void onPinchToZoomAnimationStart() {
-        // cancel the single touch handling
-        cancelTouch();
-        onZoomAnimationStart();
-    }
-
-    void onPinchToZoomAnimationEnd(ScaleGestureDetector detector) {
-        onZoomAnimationEnd();
-        // start a drag, TOUCH_PINCH_DRAG, can't use TOUCH_INIT_MODE as
-        // it may trigger the unwanted click, can't use TOUCH_DRAG_MODE
-        // as it may trigger the unwanted fling.
-        mTouchMode = TOUCH_PINCH_DRAG;
-        mConfirmMove = true;
-        startTouch(detector.getFocusX(), detector.getFocusY(), mLastTouchTime);
-    }
-
-    // See if there is a layer at x, y and switch to TOUCH_DRAG_LAYER_MODE if a
-    // layer is found.
-    private void startScrollingLayer(float x, float y) {
-        int contentX = viewToContentX((int) x + mScrollX);
-        int contentY = viewToContentY((int) y + mScrollY);
-        mCurrentScrollingLayerId = nativeScrollableLayer(contentX, contentY,
-                mScrollingLayerRect, mScrollingLayerBounds);
-        if (mCurrentScrollingLayerId != 0) {
-            mTouchMode = TOUCH_DRAG_LAYER_MODE;
-        }
-    }
-
-    // 1/(density * density) used to compute the distance between points.
-    // Computed in init().
-    private float DRAG_LAYER_INVERSE_DENSITY_SQUARED;
-
-    // The distance between two points reported in onTouchEvent scaled by the
-    // density of the screen.
-    private static final int DRAG_LAYER_FINGER_DISTANCE = 20000;
-
-    @Override
-    public boolean onHoverEvent(MotionEvent event) {
-        if (mNativeClass == 0) {
-            return false;
-        }
-        WebViewCore.CursorData data = cursorDataNoPosition();
-        data.mX = viewToContentX((int) event.getX() + mScrollX);
-        data.mY = viewToContentY((int) event.getY() + mScrollY);
-        mWebViewCore.sendMessage(EventHub.SET_MOVE_MOUSE, data);
-        return true;
-    }
-
-    @Override
-    public boolean onTouchEvent(MotionEvent ev) {
-        if (mNativeClass == 0 || (!isClickable() && !isLongClickable())) {
-            return false;
-        }
-
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, ev + " at " + ev.getEventTime()
-                + " mTouchMode=" + mTouchMode
-                + " numPointers=" + ev.getPointerCount());
-        }
-
-        // If WebKit wasn't interested in this multitouch gesture, enqueue
-        // the event for handling directly rather than making the round trip
-        // to WebKit and back.
-        if (ev.getPointerCount() > 1 && mPreventDefault != PREVENT_DEFAULT_NO) {
-            passMultiTouchToWebKit(ev, mTouchEventQueue.nextTouchSequence());
-        } else {
-            mTouchEventQueue.enqueueTouchEvent(ev);
-        }
-
-        // Since all events are handled asynchronously, we always want the gesture stream.
-        return true;
-    }
-
-    private float calculateDragAngle(int dx, int dy) {
-        dx = Math.abs(dx);
-        dy = Math.abs(dy);
-        return (float) Math.atan2(dy, dx);
-    }
-
-    /*
-     * Common code for single touch and multi-touch.
-     * (x, y) denotes current focus point, which is the touch point for single touch
-     * and the middle point for multi-touch.
-     */
-    private boolean handleTouchEventCommon(MotionEvent ev, int action, int x, int y) {
-        long eventTime = ev.getEventTime();
-
-        // Due to the touch screen edge effect, a touch closer to the edge
-        // always snapped to the edge. As getViewWidth() can be different from
-        // getWidth() due to the scrollbar, adjusting the point to match
-        // getViewWidth(). Same applied to the height.
-        x = Math.min(x, getViewWidth() - 1);
-        y = Math.min(y, getViewHeightWithTitle() - 1);
-
-        int deltaX = mLastTouchX - x;
-        int deltaY = mLastTouchY - y;
-        int contentX = viewToContentX(x + mScrollX);
-        int contentY = viewToContentY(y + mScrollY);
-
-        switch (action) {
-            case MotionEvent.ACTION_DOWN: {
-                mPreventDefault = PREVENT_DEFAULT_NO;
-                mConfirmMove = false;
-                mInitialHitTestResult = null;
-                if (!mScroller.isFinished()) {
-                    // stop the current scroll animation, but if this is
-                    // the start of a fling, allow it to add to the current
-                    // fling's velocity
-                    mScroller.abortAnimation();
-                    mTouchMode = TOUCH_DRAG_START_MODE;
-                    mConfirmMove = true;
-                    nativeSetIsScrolling(false);
-                } else if (mPrivateHandler.hasMessages(RELEASE_SINGLE_TAP)) {
-                    mPrivateHandler.removeMessages(RELEASE_SINGLE_TAP);
-                    if (sDisableNavcache) {
-                        removeTouchHighlight();
-                    }
-                    if (deltaX * deltaX + deltaY * deltaY < mDoubleTapSlopSquare) {
-                        mTouchMode = TOUCH_DOUBLE_TAP_MODE;
-                    } else {
-                        // commit the short press action for the previous tap
-                        doShortPress();
-                        mTouchMode = TOUCH_INIT_MODE;
-                        mDeferTouchProcess = !mBlockWebkitViewMessages
-                                && (!inFullScreenMode() && mForwardTouchEvents)
-                                ? hitFocusedPlugin(contentX, contentY)
-                                : false;
-                    }
-                } else { // the normal case
-                    mTouchMode = TOUCH_INIT_MODE;
-                    mDeferTouchProcess = !mBlockWebkitViewMessages
-                            && (!inFullScreenMode() && mForwardTouchEvents)
-                            ? hitFocusedPlugin(contentX, contentY)
-                            : false;
-                    if (!mBlockWebkitViewMessages) {
-                        mWebViewCore.sendMessage(
-                                EventHub.UPDATE_FRAME_CACHE_IF_LOADING);
-                    }
-                    if (sDisableNavcache) {
-                        TouchHighlightData data = new TouchHighlightData();
-                        data.mX = contentX;
-                        data.mY = contentY;
-                        data.mNativeLayerRect = new Rect();
-                        data.mNativeLayer = nativeScrollableLayer(
-                                contentX, contentY, data.mNativeLayerRect, null);
-                        data.mSlop = viewToContentDimension(mNavSlop);
-                        mTouchHighlightRegion.setEmpty();
-                        if (!mBlockWebkitViewMessages) {
-                            mTouchHighlightRequested = System.currentTimeMillis();
-                            mWebViewCore.sendMessageAtFrontOfQueue(
-                                    EventHub.HIT_TEST, data);
-                        }
-                        if (DEBUG_TOUCH_HIGHLIGHT) {
-                            if (getSettings().getNavDump()) {
-                                mTouchHighlightX = x + mScrollX;
-                                mTouchHighlightY = y + mScrollY;
-                                mPrivateHandler.postDelayed(new Runnable() {
-                                    @Override
-                                    public void run() {
-                                        mTouchHighlightX = mTouchHighlightY = 0;
-                                        invalidate();
-                                    }
-                                }, TOUCH_HIGHLIGHT_ELAPSE_TIME);
-                            }
-                        }
-                    }
-                    if (mLogEvent && eventTime - mLastTouchUpTime < 1000) {
-                        EventLog.writeEvent(EventLogTags.BROWSER_DOUBLE_TAP_DURATION,
-                                (eventTime - mLastTouchUpTime), eventTime);
-                    }
-                    mSelectionStarted = false;
-                    if (mSelectingText) {
-                        int shiftedY = y - getTitleHeight() + mScrollY;
-                        int shiftedX = x + mScrollX;
-                        if (mSelectHandleCenter != null && mSelectHandleCenter.getBounds()
-                                .contains(shiftedX, shiftedY)) {
-                            mSelectionStarted = true;
-                            mSelectDraggingCursor = mSelectCursorBase;
-                            mPrivateHandler.removeMessages(CLEAR_CARET_HANDLE);
-                            hidePasteButton();
-                        } else if (mSelectHandleLeft != null
-                                && mSelectHandleLeft.getBounds()
-                                    .contains(shiftedX, shiftedY)) {
-                                mSelectionStarted = true;
-                                mSelectDraggingCursor = mSelectCursorBase;
-                        } else if (mSelectHandleRight != null
-                                && mSelectHandleRight.getBounds()
-                                .contains(shiftedX, shiftedY)) {
-                            mSelectionStarted = true;
-                            mSelectDraggingCursor = mSelectCursorExtent;
-                        } else if (mIsCaretSelection) {
-                            selectionDone();
-                        }
-                        if (mSelectDraggingCursor != null) {
-                            mSelectDraggingOffset.set(
-                                    mSelectDraggingCursor.left - contentX,
-                                    mSelectDraggingCursor.top - contentY);
-                        }
-                        if (DebugFlags.WEB_VIEW) {
-                            Log.v(LOGTAG, "select=" + contentX + "," + contentY);
-                        }
-                    }
-                }
-                // Trigger the link
-                if (!mSelectingText && (mTouchMode == TOUCH_INIT_MODE
-                        || mTouchMode == TOUCH_DOUBLE_TAP_MODE)) {
-                    mPrivateHandler.sendEmptyMessageDelayed(
-                            SWITCH_TO_SHORTPRESS, TAP_TIMEOUT);
-                    mPrivateHandler.sendEmptyMessageDelayed(
-                            SWITCH_TO_LONGPRESS, LONG_PRESS_TIMEOUT);
-                    if (inFullScreenMode() || mDeferTouchProcess) {
-                        mPreventDefault = PREVENT_DEFAULT_YES;
-                    } else if (!mBlockWebkitViewMessages && mForwardTouchEvents) {
-                        mPreventDefault = PREVENT_DEFAULT_MAYBE_YES;
-                    } else {
-                        mPreventDefault = PREVENT_DEFAULT_NO;
-                    }
-                    // pass the touch events from UI thread to WebCore thread
-                    if (shouldForwardTouchEvent()) {
-                        TouchEventData ted = new TouchEventData();
-                        ted.mAction = action;
-                        ted.mIds = new int[1];
-                        ted.mIds[0] = ev.getPointerId(0);
-                        ted.mPoints = new Point[1];
-                        ted.mPoints[0] = new Point(contentX, contentY);
-                        ted.mPointsInView = new Point[1];
-                        ted.mPointsInView[0] = new Point(x, y);
-                        ted.mMetaState = ev.getMetaState();
-                        ted.mReprocess = mDeferTouchProcess;
-                        ted.mNativeLayer = nativeScrollableLayer(
-                                contentX, contentY, ted.mNativeLayerRect, null);
-                        ted.mSequence = mTouchEventQueue.nextTouchSequence();
-                        mTouchEventQueue.preQueueTouchEventData(ted);
-                        mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
-                        if (mDeferTouchProcess) {
-                            // still needs to set them for compute deltaX/Y
-                            mLastTouchX = x;
-                            mLastTouchY = y;
-                            break;
-                        }
-                        if (!inFullScreenMode()) {
-                            mPrivateHandler.removeMessages(PREVENT_DEFAULT_TIMEOUT);
-                            mPrivateHandler.sendMessageDelayed(mPrivateHandler
-                                    .obtainMessage(PREVENT_DEFAULT_TIMEOUT,
-                                            action, 0), TAP_TIMEOUT);
-                        }
-                    }
-                }
-                startTouch(x, y, eventTime);
-                break;
-            }
-            case MotionEvent.ACTION_MOVE: {
-                boolean firstMove = false;
-                if (!mConfirmMove && (deltaX * deltaX + deltaY * deltaY)
-                        >= mTouchSlopSquare) {
-                    mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
-                    mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-                    mConfirmMove = true;
-                    firstMove = true;
-                    if (mTouchMode == TOUCH_DOUBLE_TAP_MODE) {
-                        mTouchMode = TOUCH_INIT_MODE;
-                    }
-                    if (sDisableNavcache) {
-                        removeTouchHighlight();
-                    }
-                }
-                if (mSelectingText && mSelectionStarted) {
-                    if (DebugFlags.WEB_VIEW) {
-                        Log.v(LOGTAG, "extend=" + contentX + "," + contentY);
-                    }
-                    ViewParent parent = getParent();
-                    if (parent != null) {
-                        parent.requestDisallowInterceptTouchEvent(true);
-                    }
-                    if (deltaX != 0 || deltaY != 0) {
-                        mSelectDraggingCursor.offsetTo(
-                                contentX + mSelectDraggingOffset.x,
-                                contentY + mSelectDraggingOffset.y);
-                        updateWebkitSelection();
-                        mLastTouchX = x;
-                        mLastTouchY = y;
-                        invalidate();
-                    }
-                    break;
-                }
-
-                // pass the touch events from UI thread to WebCore thread
-                if (shouldForwardTouchEvent() && mConfirmMove && (firstMove
-                        || eventTime - mLastSentTouchTime > mCurrentTouchInterval)) {
-                    TouchEventData ted = new TouchEventData();
-                    ted.mAction = action;
-                    ted.mIds = new int[1];
-                    ted.mIds[0] = ev.getPointerId(0);
-                    ted.mPoints = new Point[1];
-                    ted.mPoints[0] = new Point(contentX, contentY);
-                    ted.mPointsInView = new Point[1];
-                    ted.mPointsInView[0] = new Point(x, y);
-                    ted.mMetaState = ev.getMetaState();
-                    ted.mReprocess = mDeferTouchProcess;
-                    ted.mNativeLayer = mCurrentScrollingLayerId;
-                    ted.mNativeLayerRect.set(mScrollingLayerRect);
-                    ted.mSequence = mTouchEventQueue.nextTouchSequence();
-                    mTouchEventQueue.preQueueTouchEventData(ted);
-                    mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
-                    mLastSentTouchTime = eventTime;
-                    if (mDeferTouchProcess) {
-                        break;
-                    }
-                    if (firstMove && !inFullScreenMode()) {
-                        mPrivateHandler.sendMessageDelayed(mPrivateHandler
-                                .obtainMessage(PREVENT_DEFAULT_TIMEOUT,
-                                        action, 0), TAP_TIMEOUT);
-                    }
-                }
-                if (mTouchMode == TOUCH_DONE_MODE
-                        || mPreventDefault == PREVENT_DEFAULT_YES) {
-                    // no dragging during scroll zoom animation, or when prevent
-                    // default is yes
-                    break;
-                }
-                if (mVelocityTracker == null) {
-                    Log.e(LOGTAG, "Got null mVelocityTracker when "
-                            + "mPreventDefault = " + mPreventDefault
-                            + " mDeferTouchProcess = " + mDeferTouchProcess
-                            + " mTouchMode = " + mTouchMode);
-                } else {
-                    mVelocityTracker.addMovement(ev);
-                }
-
-                if (mTouchMode != TOUCH_DRAG_MODE &&
-                        mTouchMode != TOUCH_DRAG_LAYER_MODE) {
-
-                    if (!mConfirmMove) {
-                        break;
-                    }
-
-                    if (mPreventDefault == PREVENT_DEFAULT_MAYBE_YES
-                            || mPreventDefault == PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN) {
-                        // track mLastTouchTime as we may need to do fling at
-                        // ACTION_UP
-                        mLastTouchTime = eventTime;
-                        break;
-                    }
-
-                    // Only lock dragging to one axis if we don't have a scale in progress.
-                    // Scaling implies free-roaming movement. Note this is only ever a question
-                    // if mZoomManager.supportsPanDuringZoom() is true.
-                    final ScaleGestureDetector detector =
-                      mZoomManager.getMultiTouchGestureDetector();
-                    mAverageAngle = calculateDragAngle(deltaX, deltaY);
-                    if (detector == null || !detector.isInProgress()) {
-                        // if it starts nearly horizontal or vertical, enforce it
-                        if (mAverageAngle < HSLOPE_TO_START_SNAP) {
-                            mSnapScrollMode = SNAP_X;
-                            mSnapPositive = deltaX > 0;
-                            mAverageAngle = ANGLE_HORIZ;
-                        } else if (mAverageAngle > VSLOPE_TO_START_SNAP) {
-                            mSnapScrollMode = SNAP_Y;
-                            mSnapPositive = deltaY > 0;
-                            mAverageAngle = ANGLE_VERT;
-                        }
-                    }
-
-                    mTouchMode = TOUCH_DRAG_MODE;
-                    mLastTouchX = x;
-                    mLastTouchY = y;
-                    deltaX = 0;
-                    deltaY = 0;
-
-                    startScrollingLayer(x, y);
-                    startDrag();
-                }
-
-                // do pan
-                boolean done = false;
-                boolean keepScrollBarsVisible = false;
-                if (deltaX == 0 && deltaY == 0) {
-                    keepScrollBarsVisible = done = true;
-                } else {
-                    mAverageAngle +=
-                        (calculateDragAngle(deltaX, deltaY) - mAverageAngle)
-                        / MMA_WEIGHT_N;
-                    if (mSnapScrollMode != SNAP_NONE) {
-                        if (mSnapScrollMode == SNAP_Y) {
-                            // radical change means getting out of snap mode
-                            if (mAverageAngle < VSLOPE_TO_BREAK_SNAP) {
-                                mSnapScrollMode = SNAP_NONE;
-                            }
-                        }
-                        if (mSnapScrollMode == SNAP_X) {
-                            // radical change means getting out of snap mode
-                            if (mAverageAngle > HSLOPE_TO_BREAK_SNAP) {
-                                mSnapScrollMode = SNAP_NONE;
-                            }
-                        }
-                    } else {
-                        if (mAverageAngle < HSLOPE_TO_START_SNAP) {
-                            mSnapScrollMode = SNAP_X;
-                            mSnapPositive = deltaX > 0;
-                            mAverageAngle = (mAverageAngle + ANGLE_HORIZ) / 2;
-                        } else if (mAverageAngle > VSLOPE_TO_START_SNAP) {
-                            mSnapScrollMode = SNAP_Y;
-                            mSnapPositive = deltaY > 0;
-                            mAverageAngle = (mAverageAngle + ANGLE_VERT) / 2;
-                        }
-                    }
-                    if (mSnapScrollMode != SNAP_NONE) {
-                        if ((mSnapScrollMode & SNAP_X) == SNAP_X) {
-                            deltaY = 0;
-                        } else {
-                            deltaX = 0;
-                        }
-                    }
-                    mLastTouchX = x;
-                    mLastTouchY = y;
-
-                    if (deltaX * deltaX + deltaY * deltaY > mTouchSlopSquare) {
-                        mHeldMotionless = MOTIONLESS_FALSE;
-                        nativeSetIsScrolling(true);
-                    } else {
-                        mHeldMotionless = MOTIONLESS_TRUE;
-                        nativeSetIsScrolling(false);
-                        keepScrollBarsVisible = true;
-                    }
-
-                    mLastTouchTime = eventTime;
-                }
-
-                doDrag(deltaX, deltaY);
-
-                // Turn off scrollbars when dragging a layer.
-                if (keepScrollBarsVisible &&
-                        mTouchMode != TOUCH_DRAG_LAYER_MODE) {
-                    if (mHeldMotionless != MOTIONLESS_TRUE) {
-                        mHeldMotionless = MOTIONLESS_TRUE;
-                        invalidate();
-                    }
-                    // keep the scrollbar on the screen even there is no scroll
-                    awakenScrollBars(ViewConfiguration.getScrollDefaultDelay(),
-                            false);
-                    // Post a message so that we'll keep them alive while we're not scrolling.
-                    mPrivateHandler.sendMessageDelayed(mPrivateHandler
-                            .obtainMessage(AWAKEN_SCROLL_BARS),
-                            ViewConfiguration.getScrollDefaultDelay());
-                    // return false to indicate that we can't pan out of the
-                    // view space
-                    return !done;
-                } else {
-                    mPrivateHandler.removeMessages(AWAKEN_SCROLL_BARS);
-                }
-                break;
-            }
-            case MotionEvent.ACTION_UP: {
-                if (!isFocused()) requestFocus();
-                // pass the touch events from UI thread to WebCore thread
-                if (shouldForwardTouchEvent()) {
-                    TouchEventData ted = new TouchEventData();
-                    ted.mIds = new int[1];
-                    ted.mIds[0] = ev.getPointerId(0);
-                    ted.mAction = action;
-                    ted.mPoints = new Point[1];
-                    ted.mPoints[0] = new Point(contentX, contentY);
-                    ted.mPointsInView = new Point[1];
-                    ted.mPointsInView[0] = new Point(x, y);
-                    ted.mMetaState = ev.getMetaState();
-                    ted.mReprocess = mDeferTouchProcess;
-                    ted.mNativeLayer = mCurrentScrollingLayerId;
-                    ted.mNativeLayerRect.set(mScrollingLayerRect);
-                    ted.mSequence = mTouchEventQueue.nextTouchSequence();
-                    mTouchEventQueue.preQueueTouchEventData(ted);
-                    mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
-                }
-                mLastTouchUpTime = eventTime;
-                if (mSentAutoScrollMessage) {
-                    mAutoScrollX = mAutoScrollY = 0;
-                }
-                switch (mTouchMode) {
-                    case TOUCH_DOUBLE_TAP_MODE: // double tap
-                        mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
-                        mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-                        if (inFullScreenMode() || mDeferTouchProcess) {
-                            TouchEventData ted = new TouchEventData();
-                            ted.mIds = new int[1];
-                            ted.mIds[0] = ev.getPointerId(0);
-                            ted.mAction = WebViewCore.ACTION_DOUBLETAP;
-                            ted.mPoints = new Point[1];
-                            ted.mPoints[0] = new Point(contentX, contentY);
-                            ted.mPointsInView = new Point[1];
-                            ted.mPointsInView[0] = new Point(x, y);
-                            ted.mMetaState = ev.getMetaState();
-                            ted.mReprocess = mDeferTouchProcess;
-                            ted.mNativeLayer = nativeScrollableLayer(
-                                    contentX, contentY,
-                                    ted.mNativeLayerRect, null);
-                            ted.mSequence = mTouchEventQueue.nextTouchSequence();
-                            mTouchEventQueue.preQueueTouchEventData(ted);
-                            mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
-                        } else if (mPreventDefault != PREVENT_DEFAULT_YES){
-                            mZoomManager.handleDoubleTap(mLastTouchX, mLastTouchY);
-                            mTouchMode = TOUCH_DONE_MODE;
-                        }
-                        break;
-                    case TOUCH_INIT_MODE: // tap
-                    case TOUCH_SHORTPRESS_START_MODE:
-                    case TOUCH_SHORTPRESS_MODE:
-                        mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
-                        mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-                        if (mConfirmMove) {
-                            Log.w(LOGTAG, "Miss a drag as we are waiting for" +
-                                    " WebCore's response for touch down.");
-                            if (mPreventDefault != PREVENT_DEFAULT_YES
-                                    && (computeMaxScrollX() > 0
-                                            || computeMaxScrollY() > 0)) {
-                                // If the user has performed a very quick touch
-                                // sequence it is possible that we may get here
-                                // before WebCore has had a chance to process the events.
-                                // In this case, any call to preventDefault in the
-                                // JS touch handler will not have been executed yet.
-                                // Hence we will see both the UI (now) and WebCore
-                                // (when context switches) handling the event,
-                                // regardless of whether the web developer actually
-                                // doeses preventDefault in their touch handler. This
-                                // is the nature of our asynchronous touch model.
-
-                                // we will not rewrite drag code here, but we
-                                // will try fling if it applies.
-                                WebViewCore.reducePriority();
-                                // to get better performance, pause updating the
-                                // picture
-                                WebViewCore.pauseUpdatePicture(mWebViewCore);
-                                // fall through to TOUCH_DRAG_MODE
-                            } else {
-                                // WebKit may consume the touch event and modify
-                                // DOM. drawContentPicture() will be called with
-                                // animateSroll as true for better performance.
-                                // Force redraw in high-quality.
-                                invalidate();
-                                break;
-                            }
-                        } else {
-                            if (mSelectingText) {
-                                // tapping on selection or controls does nothing
-                                if (!mSelectionStarted) {
-                                    selectionDone();
-                                }
-                                break;
-                            }
-                            // only trigger double tap if the WebView is
-                            // scalable
-                            if (mTouchMode == TOUCH_INIT_MODE
-                                    && (canZoomIn() || canZoomOut())) {
-                                mPrivateHandler.sendEmptyMessageDelayed(
-                                        RELEASE_SINGLE_TAP, ViewConfiguration
-                                                .getDoubleTapTimeout());
-                            } else {
-                                doShortPress();
-                            }
-                            break;
-                        }
-                    case TOUCH_DRAG_MODE:
-                    case TOUCH_DRAG_LAYER_MODE:
-                        mPrivateHandler.removeMessages(DRAG_HELD_MOTIONLESS);
-                        mPrivateHandler.removeMessages(AWAKEN_SCROLL_BARS);
-                        // if the user waits a while w/o moving before the
-                        // up, we don't want to do a fling
-                        if (eventTime - mLastTouchTime <= MIN_FLING_TIME) {
-                            if (mVelocityTracker == null) {
-                                Log.e(LOGTAG, "Got null mVelocityTracker when "
-                                        + "mPreventDefault = "
-                                        + mPreventDefault
-                                        + " mDeferTouchProcess = "
-                                        + mDeferTouchProcess);
-                            } else {
-                                mVelocityTracker.addMovement(ev);
-                            }
-                            // set to MOTIONLESS_IGNORE so that it won't keep
-                            // removing and sending message in
-                            // drawCoreAndCursorRing()
-                            mHeldMotionless = MOTIONLESS_IGNORE;
-                            doFling();
-                            break;
-                        } else {
-                            if (mScroller.springBack(mScrollX, mScrollY, 0,
-                                    computeMaxScrollX(), 0,
-                                    computeMaxScrollY())) {
-                                invalidate();
-                            }
-                        }
-                        // redraw in high-quality, as we're done dragging
-                        mHeldMotionless = MOTIONLESS_TRUE;
-                        invalidate();
-                        // fall through
-                    case TOUCH_DRAG_START_MODE:
-                        // TOUCH_DRAG_START_MODE should not happen for the real
-                        // device as we almost certain will get a MOVE. But this
-                        // is possible on emulator.
-                        mLastVelocity = 0;
-                        WebViewCore.resumePriority();
-                        if (!mSelectingText) {
-                            WebViewCore.resumeUpdatePicture(mWebViewCore);
-                        }
-                        break;
-                }
-                stopTouch();
-                break;
-            }
-            case MotionEvent.ACTION_CANCEL: {
-                if (mTouchMode == TOUCH_DRAG_MODE) {
-                    mScroller.springBack(mScrollX, mScrollY, 0,
-                            computeMaxScrollX(), 0, computeMaxScrollY());
-                    invalidate();
-                }
-                cancelWebCoreTouchEvent(contentX, contentY, false);
-                cancelTouch();
-                break;
-            }
-        }
-        return true;
-    }
-
-    private void passMultiTouchToWebKit(MotionEvent ev, long sequence) {
-        TouchEventData ted = new TouchEventData();
-        ted.mAction = ev.getActionMasked();
-        final int count = ev.getPointerCount();
-        ted.mIds = new int[count];
-        ted.mPoints = new Point[count];
-        ted.mPointsInView = new Point[count];
-        for (int c = 0; c < count; c++) {
-            ted.mIds[c] = ev.getPointerId(c);
-            int x = viewToContentX((int) ev.getX(c) + mScrollX);
-            int y = viewToContentY((int) ev.getY(c) + mScrollY);
-            ted.mPoints[c] = new Point(x, y);
-            ted.mPointsInView[c] = new Point((int) ev.getX(c), (int) ev.getY(c));
-        }
-        if (ted.mAction == MotionEvent.ACTION_POINTER_DOWN
-            || ted.mAction == MotionEvent.ACTION_POINTER_UP) {
-            ted.mActionIndex = ev.getActionIndex();
-        }
-        ted.mMetaState = ev.getMetaState();
-        ted.mReprocess = true;
-        ted.mMotionEvent = MotionEvent.obtain(ev);
-        ted.mSequence = sequence;
-        mTouchEventQueue.preQueueTouchEventData(ted);
-        mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
-        cancelLongPress();
-        mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-    }
-
-    void handleMultiTouchInWebView(MotionEvent ev) {
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "multi-touch: " + ev + " at " + ev.getEventTime()
-                + " mTouchMode=" + mTouchMode
-                + " numPointers=" + ev.getPointerCount()
-                + " scrolloffset=(" + mScrollX + "," + mScrollY + ")");
-        }
-
-        final ScaleGestureDetector detector =
-            mZoomManager.getMultiTouchGestureDetector();
-
-        // A few apps use WebView but don't instantiate gesture detector.
-        // We don't need to support multi touch for them.
-        if (detector == null) return;
-
-        float x = ev.getX();
-        float y = ev.getY();
-
-        if (mPreventDefault != PREVENT_DEFAULT_YES) {
-            detector.onTouchEvent(ev);
-
-            if (detector.isInProgress()) {
-                if (DebugFlags.WEB_VIEW) {
-                    Log.v(LOGTAG, "detector is in progress");
-                }
-                mLastTouchTime = ev.getEventTime();
-                x = detector.getFocusX();
-                y = detector.getFocusY();
-
-                cancelLongPress();
-                mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-                if (!mZoomManager.supportsPanDuringZoom()) {
-                    return;
-                }
-                mTouchMode = TOUCH_DRAG_MODE;
-                if (mVelocityTracker == null) {
-                    mVelocityTracker = VelocityTracker.obtain();
-                }
-            }
-        }
-
-        int action = ev.getActionMasked();
-        if (action == MotionEvent.ACTION_POINTER_DOWN) {
-            cancelTouch();
-            action = MotionEvent.ACTION_DOWN;
-        } else if (action == MotionEvent.ACTION_POINTER_UP && ev.getPointerCount() >= 2) {
-            // set mLastTouchX/Y to the remaining points for multi-touch.
-            mLastTouchX = Math.round(x);
-            mLastTouchY = Math.round(y);
-        } else if (action == MotionEvent.ACTION_MOVE) {
-            // negative x or y indicate it is on the edge, skip it.
-            if (x < 0 || y < 0) {
-                return;
-            }
-        }
-
-        handleTouchEventCommon(ev, action, Math.round(x), Math.round(y));
-    }
-
-    private void cancelWebCoreTouchEvent(int x, int y, boolean removeEvents) {
-        if (shouldForwardTouchEvent()) {
-            if (removeEvents) {
-                mWebViewCore.removeMessages(EventHub.TOUCH_EVENT);
-            }
-            TouchEventData ted = new TouchEventData();
-            ted.mIds = new int[1];
-            ted.mIds[0] = 0;
-            ted.mPoints = new Point[1];
-            ted.mPoints[0] = new Point(x, y);
-            ted.mPointsInView = new Point[1];
-            int viewX = contentToViewX(x) - mScrollX;
-            int viewY = contentToViewY(y) - mScrollY;
-            ted.mPointsInView[0] = new Point(viewX, viewY);
-            ted.mAction = MotionEvent.ACTION_CANCEL;
-            ted.mNativeLayer = nativeScrollableLayer(
-                    x, y, ted.mNativeLayerRect, null);
-            ted.mSequence = mTouchEventQueue.nextTouchSequence();
-            mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
-            mPreventDefault = PREVENT_DEFAULT_IGNORE;
-
-            if (removeEvents) {
-                // Mark this after sending the message above; we should
-                // be willing to ignore the cancel event that we just sent.
-                mTouchEventQueue.ignoreCurrentlyMissingEvents();
-            }
-        }
-    }
-
-    private void startTouch(float x, float y, long eventTime) {
-        // Remember where the motion event started
-        mStartTouchX = mLastTouchX = Math.round(x);
-        mStartTouchY = mLastTouchY = Math.round(y);
-        mLastTouchTime = eventTime;
-        mVelocityTracker = VelocityTracker.obtain();
-        mSnapScrollMode = SNAP_NONE;
-        mPrivateHandler.sendEmptyMessageDelayed(UPDATE_SELECTION,
-                ViewConfiguration.getTapTimeout());
-    }
-
-    private void startDrag() {
-        WebViewCore.reducePriority();
-        // to get better performance, pause updating the picture
-        WebViewCore.pauseUpdatePicture(mWebViewCore);
-        nativeSetIsScrolling(true);
-
-        if (!mDragFromTextInput) {
-            nativeHideCursor();
-        }
-
-        if (mHorizontalScrollBarMode != SCROLLBAR_ALWAYSOFF
-                || mVerticalScrollBarMode != SCROLLBAR_ALWAYSOFF) {
-            mZoomManager.invokeZoomPicker();
-        }
-    }
-
-    private void doDrag(int deltaX, int deltaY) {
-        if ((deltaX | deltaY) != 0) {
-            int oldX = mScrollX;
-            int oldY = mScrollY;
-            int rangeX = computeMaxScrollX();
-            int rangeY = computeMaxScrollY();
-            // Check for the original scrolling layer in case we change
-            // directions.  mTouchMode might be TOUCH_DRAG_MODE if we have
-            // reached the edge of a layer but mScrollingLayer will be non-zero
-            // if we initiated the drag on a layer.
-            if (mCurrentScrollingLayerId != 0) {
-                final int contentX = viewToContentDimension(deltaX);
-                final int contentY = viewToContentDimension(deltaY);
-
-                // Check the scrolling bounds to see if we will actually do any
-                // scrolling.  The rectangle is in document coordinates.
-                final int maxX = mScrollingLayerRect.right;
-                final int maxY = mScrollingLayerRect.bottom;
-                final int resultX = Math.max(0,
-                        Math.min(mScrollingLayerRect.left + contentX, maxX));
-                final int resultY = Math.max(0,
-                        Math.min(mScrollingLayerRect.top + contentY, maxY));
-
-                if (resultX != mScrollingLayerRect.left ||
-                        resultY != mScrollingLayerRect.top) {
-                    // In case we switched to dragging the page.
-                    mTouchMode = TOUCH_DRAG_LAYER_MODE;
-                    deltaX = contentX;
-                    deltaY = contentY;
-                    oldX = mScrollingLayerRect.left;
-                    oldY = mScrollingLayerRect.top;
-                    rangeX = maxX;
-                    rangeY = maxY;
-                } else {
-                    // Scroll the main page if we are not going to scroll the
-                    // layer.  This does not reset mScrollingLayer in case the
-                    // user changes directions and the layer can scroll the
-                    // other way.
-                    mTouchMode = TOUCH_DRAG_MODE;
-                }
-            }
-
-            if (mOverScrollGlow != null) {
-                mOverScrollGlow.setOverScrollDeltas(deltaX, deltaY);
-            }
-
-            overScrollBy(deltaX, deltaY, oldX, oldY,
-                    rangeX, rangeY,
-                    mOverscrollDistance, mOverscrollDistance, true);
-            if (mOverScrollGlow != null && mOverScrollGlow.isAnimating()) {
-                invalidate();
-            }
-        }
-        mZoomManager.keepZoomPickerVisible();
-    }
-
-    private void stopTouch() {
-        if (mScroller.isFinished() && !mSelectingText
-                && (mTouchMode == TOUCH_DRAG_MODE || mTouchMode == TOUCH_DRAG_LAYER_MODE)) {
-            WebViewCore.resumePriority();
-            WebViewCore.resumeUpdatePicture(mWebViewCore);
-            nativeSetIsScrolling(false);
-        }
-
-        // we also use mVelocityTracker == null to tell us that we are
-        // not "moving around", so we can take the slower/prettier
-        // mode in the drawing code
-        if (mVelocityTracker != null) {
-            mVelocityTracker.recycle();
-            mVelocityTracker = null;
-        }
-
-        // Release any pulled glows
-        if (mOverScrollGlow != null) {
-            mOverScrollGlow.releaseAll();
-        }
-
-        if (mSelectingText) {
-            mSelectionStarted = false;
-            syncSelectionCursors();
-            if (mIsCaretSelection) {
-                resetCaretTimer();
-                showPasteWindow();
-            }
-            invalidate();
-        }
-    }
-
-    private void cancelTouch() {
-        // we also use mVelocityTracker == null to tell us that we are
-        // not "moving around", so we can take the slower/prettier
-        // mode in the drawing code
-        if (mVelocityTracker != null) {
-            mVelocityTracker.recycle();
-            mVelocityTracker = null;
-        }
-
-        if ((mTouchMode == TOUCH_DRAG_MODE
-                || mTouchMode == TOUCH_DRAG_LAYER_MODE) && !mSelectingText) {
-            WebViewCore.resumePriority();
-            WebViewCore.resumeUpdatePicture(mWebViewCore);
-            nativeSetIsScrolling(false);
-        }
-        mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
-        mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-        mPrivateHandler.removeMessages(DRAG_HELD_MOTIONLESS);
-        mPrivateHandler.removeMessages(AWAKEN_SCROLL_BARS);
-        if (sDisableNavcache) {
-            removeTouchHighlight();
-        }
-        mHeldMotionless = MOTIONLESS_TRUE;
-        mTouchMode = TOUCH_DONE_MODE;
-        nativeHideCursor();
-    }
-
-    @Override
-    public boolean onGenericMotionEvent(MotionEvent event) {
-        if ((event.getSource() & InputDevice.SOURCE_CLASS_POINTER) != 0) {
-            switch (event.getAction()) {
-                case MotionEvent.ACTION_SCROLL: {
-                    final float vscroll;
-                    final float hscroll;
-                    if ((event.getMetaState() & KeyEvent.META_SHIFT_ON) != 0) {
-                        vscroll = 0;
-                        hscroll = event.getAxisValue(MotionEvent.AXIS_VSCROLL);
-                    } else {
-                        vscroll = -event.getAxisValue(MotionEvent.AXIS_VSCROLL);
-                        hscroll = event.getAxisValue(MotionEvent.AXIS_HSCROLL);
-                    }
-                    if (hscroll != 0 || vscroll != 0) {
-                        final int vdelta = (int) (vscroll * getVerticalScrollFactor());
-                        final int hdelta = (int) (hscroll * getHorizontalScrollFactor());
-                        if (pinScrollBy(hdelta, vdelta, false, 0)) {
-                            return true;
-                        }
-                    }
-                }
-            }
-        }
-        return super.onGenericMotionEvent(event);
-    }
-
-    private long mTrackballFirstTime = 0;
-    private long mTrackballLastTime = 0;
-    private float mTrackballRemainsX = 0.0f;
-    private float mTrackballRemainsY = 0.0f;
-    private int mTrackballXMove = 0;
-    private int mTrackballYMove = 0;
-    private boolean mSelectingText = false;
-    private boolean mSelectionStarted = false;
-    private static final int TRACKBALL_KEY_TIMEOUT = 1000;
-    private static final int TRACKBALL_TIMEOUT = 200;
-    private static final int TRACKBALL_WAIT = 100;
-    private static final int TRACKBALL_SCALE = 400;
-    private static final int TRACKBALL_SCROLL_COUNT = 5;
-    private static final int TRACKBALL_MOVE_COUNT = 10;
-    private static final int TRACKBALL_MULTIPLIER = 3;
-    private static final int SELECT_CURSOR_OFFSET = 16;
-    private static final int SELECT_SCROLL = 5;
-    private int mSelectX = 0;
-    private int mSelectY = 0;
-    private boolean mFocusSizeChanged = false;
-    private boolean mTrackballDown = false;
-    private long mTrackballUpTime = 0;
-    private long mLastCursorTime = 0;
-    private Rect mLastCursorBounds;
-
-    // Set by default; BrowserActivity clears to interpret trackball data
-    // directly for movement. Currently, the framework only passes
-    // arrow key events, not trackball events, from one child to the next
-    private boolean mMapTrackballToArrowKeys = true;
-
-    private DrawData mDelaySetPicture;
-    private DrawData mLoadedPicture;
-
     public void setMapTrackballToArrowKeys(boolean setMap) {
         checkThread();
-        mMapTrackballToArrowKeys = setMap;
+        mProvider.setMapTrackballToArrowKeys(setMap);
     }
 
-    void resetTrackballTime() {
-        mTrackballLastTime = 0;
-    }
-
-    @Override
-    public boolean onTrackballEvent(MotionEvent ev) {
-        long time = ev.getEventTime();
-        if ((ev.getMetaState() & KeyEvent.META_ALT_ON) != 0) {
-            if (ev.getY() > 0) pageDown(true);
-            if (ev.getY() < 0) pageUp(true);
-            return true;
-        }
-        if (ev.getAction() == MotionEvent.ACTION_DOWN) {
-            if (mSelectingText) {
-                return true; // discard press if copy in progress
-            }
-            mTrackballDown = true;
-            if (mNativeClass == 0) {
-                return false;
-            }
-            if (time - mLastCursorTime <= TRACKBALL_TIMEOUT
-                    && !mLastCursorBounds.equals(cursorRingBounds())) {
-                nativeSelectBestAt(mLastCursorBounds);
-            }
-            if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "onTrackballEvent down ev=" + ev
-                        + " time=" + time
-                        + " mLastCursorTime=" + mLastCursorTime);
-            }
-            if (isInTouchMode()) requestFocusFromTouch();
-            return false; // let common code in onKeyDown at it
-        }
-        if (ev.getAction() == MotionEvent.ACTION_UP) {
-            // LONG_PRESS_CENTER is set in common onKeyDown
-            mPrivateHandler.removeMessages(LONG_PRESS_CENTER);
-            mTrackballDown = false;
-            mTrackballUpTime = time;
-            if (mSelectingText) {
-                copySelection();
-                selectionDone();
-                return true; // discard press if copy in progress
-            }
-            if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "onTrackballEvent up ev=" + ev
-                        + " time=" + time
-                );
-            }
-            return false; // let common code in onKeyUp at it
-        }
-        if ((mMapTrackballToArrowKeys && (ev.getMetaState() & KeyEvent.META_SHIFT_ON) == 0) ||
-                AccessibilityManager.getInstance(mContext).isEnabled()) {
-            if (DebugFlags.WEB_VIEW) Log.v(LOGTAG, "onTrackballEvent gmail quit");
-            return false;
-        }
-        if (mTrackballDown) {
-            if (DebugFlags.WEB_VIEW) Log.v(LOGTAG, "onTrackballEvent down quit");
-            return true; // discard move if trackball is down
-        }
-        if (time - mTrackballUpTime < TRACKBALL_TIMEOUT) {
-            if (DebugFlags.WEB_VIEW) Log.v(LOGTAG, "onTrackballEvent up timeout quit");
-            return true;
-        }
-        // TODO: alternatively we can do panning as touch does
-        switchOutDrawHistory();
-        if (time - mTrackballLastTime > TRACKBALL_TIMEOUT) {
-            if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "onTrackballEvent time="
-                        + time + " last=" + mTrackballLastTime);
-            }
-            mTrackballFirstTime = time;
-            mTrackballXMove = mTrackballYMove = 0;
-        }
-        mTrackballLastTime = time;
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "onTrackballEvent ev=" + ev + " time=" + time);
-        }
-        mTrackballRemainsX += ev.getX();
-        mTrackballRemainsY += ev.getY();
-        doTrackball(time, ev.getMetaState());
-        return true;
-    }
-
-    private int scaleTrackballX(float xRate, int width) {
-        int xMove = (int) (xRate / TRACKBALL_SCALE * width);
-        int nextXMove = xMove;
-        if (xMove > 0) {
-            if (xMove > mTrackballXMove) {
-                xMove -= mTrackballXMove;
-            }
-        } else if (xMove < mTrackballXMove) {
-            xMove -= mTrackballXMove;
-        }
-        mTrackballXMove = nextXMove;
-        return xMove;
-    }
-
-    private int scaleTrackballY(float yRate, int height) {
-        int yMove = (int) (yRate / TRACKBALL_SCALE * height);
-        int nextYMove = yMove;
-        if (yMove > 0) {
-            if (yMove > mTrackballYMove) {
-                yMove -= mTrackballYMove;
-            }
-        } else if (yMove < mTrackballYMove) {
-            yMove -= mTrackballYMove;
-        }
-        mTrackballYMove = nextYMove;
-        return yMove;
-    }
-
-    private int keyCodeToSoundsEffect(int keyCode) {
-        switch(keyCode) {
-            case KeyEvent.KEYCODE_DPAD_UP:
-                return SoundEffectConstants.NAVIGATION_UP;
-            case KeyEvent.KEYCODE_DPAD_RIGHT:
-                return SoundEffectConstants.NAVIGATION_RIGHT;
-            case KeyEvent.KEYCODE_DPAD_DOWN:
-                return SoundEffectConstants.NAVIGATION_DOWN;
-            case KeyEvent.KEYCODE_DPAD_LEFT:
-                return SoundEffectConstants.NAVIGATION_LEFT;
-        }
-        throw new IllegalArgumentException("keyCode must be one of " +
-                "{KEYCODE_DPAD_UP, KEYCODE_DPAD_RIGHT, KEYCODE_DPAD_DOWN, " +
-                "KEYCODE_DPAD_LEFT}.");
-    }
-
-    private void doTrackball(long time, int metaState) {
-        int elapsed = (int) (mTrackballLastTime - mTrackballFirstTime);
-        if (elapsed == 0) {
-            elapsed = TRACKBALL_TIMEOUT;
-        }
-        float xRate = mTrackballRemainsX * 1000 / elapsed;
-        float yRate = mTrackballRemainsY * 1000 / elapsed;
-        int viewWidth = getViewWidth();
-        int viewHeight = getViewHeight();
-        float ax = Math.abs(xRate);
-        float ay = Math.abs(yRate);
-        float maxA = Math.max(ax, ay);
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "doTrackball elapsed=" + elapsed
-                    + " xRate=" + xRate
-                    + " yRate=" + yRate
-                    + " mTrackballRemainsX=" + mTrackballRemainsX
-                    + " mTrackballRemainsY=" + mTrackballRemainsY);
-        }
-        int width = mContentWidth - viewWidth;
-        int height = mContentHeight - viewHeight;
-        if (width < 0) width = 0;
-        if (height < 0) height = 0;
-        ax = Math.abs(mTrackballRemainsX * TRACKBALL_MULTIPLIER);
-        ay = Math.abs(mTrackballRemainsY * TRACKBALL_MULTIPLIER);
-        maxA = Math.max(ax, ay);
-        int count = Math.max(0, (int) maxA);
-        int oldScrollX = mScrollX;
-        int oldScrollY = mScrollY;
-        if (count > 0) {
-            int selectKeyCode = ax < ay ? mTrackballRemainsY < 0 ?
-                    KeyEvent.KEYCODE_DPAD_UP : KeyEvent.KEYCODE_DPAD_DOWN :
-                    mTrackballRemainsX < 0 ? KeyEvent.KEYCODE_DPAD_LEFT :
-                    KeyEvent.KEYCODE_DPAD_RIGHT;
-            count = Math.min(count, TRACKBALL_MOVE_COUNT);
-            if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "doTrackball keyCode=" + selectKeyCode
-                        + " count=" + count
-                        + " mTrackballRemainsX=" + mTrackballRemainsX
-                        + " mTrackballRemainsY=" + mTrackballRemainsY);
-            }
-            if (mNativeClass != 0 && nativePageShouldHandleShiftAndArrows()) {
-                for (int i = 0; i < count; i++) {
-                    letPageHandleNavKey(selectKeyCode, time, true, metaState);
-                }
-                letPageHandleNavKey(selectKeyCode, time, false, metaState);
-            } else if (navHandledKey(selectKeyCode, count, false, time)) {
-                playSoundEffect(keyCodeToSoundsEffect(selectKeyCode));
-            }
-            mTrackballRemainsX = mTrackballRemainsY = 0;
-        }
-        if (count >= TRACKBALL_SCROLL_COUNT) {
-            int xMove = scaleTrackballX(xRate, width);
-            int yMove = scaleTrackballY(yRate, height);
-            if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "doTrackball pinScrollBy"
-                        + " count=" + count
-                        + " xMove=" + xMove + " yMove=" + yMove
-                        + " mScrollX-oldScrollX=" + (mScrollX-oldScrollX)
-                        + " mScrollY-oldScrollY=" + (mScrollY-oldScrollY)
-                        );
-            }
-            if (Math.abs(mScrollX - oldScrollX) > Math.abs(xMove)) {
-                xMove = 0;
-            }
-            if (Math.abs(mScrollY - oldScrollY) > Math.abs(yMove)) {
-                yMove = 0;
-            }
-            if (xMove != 0 || yMove != 0) {
-                pinScrollBy(xMove, yMove, true, 0);
-            }
-        }
-    }
-
-    /**
-     * Compute the maximum horizontal scroll position. Used by {@link OverScrollGlow}.
-     * @return Maximum horizontal scroll position within real content
-     */
-    int computeMaxScrollX() {
-        return Math.max(computeRealHorizontalScrollRange() - getViewWidth(), 0);
-    }
-
-    /**
-     * Compute the maximum vertical scroll position. Used by {@link OverScrollGlow}.
-     * @return Maximum vertical scroll position within real content
-     */
-    int computeMaxScrollY() {
-        return Math.max(computeRealVerticalScrollRange() + getTitleHeight()
-                - getViewHeightWithTitle(), 0);
-    }
-
-    boolean updateScrollCoordinates(int x, int y) {
-        int oldX = mScrollX;
-        int oldY = mScrollY;
-        mScrollX = x;
-        mScrollY = y;
-        if (oldX != mScrollX || oldY != mScrollY) {
-            onScrollChanged(mScrollX, mScrollY, oldX, oldY);
-            return true;
-        } else {
-            return false;
-        }
-    }
 
     public void flingScroll(int vx, int vy) {
         checkThread();
-        mScroller.fling(mScrollX, mScrollY, vx, vy, 0, computeMaxScrollX(), 0,
-                computeMaxScrollY(), mOverflingDistance, mOverflingDistance);
-        invalidate();
-    }
-
-    private void doFling() {
-        if (mVelocityTracker == null) {
-            return;
-        }
-        int maxX = computeMaxScrollX();
-        int maxY = computeMaxScrollY();
-
-        mVelocityTracker.computeCurrentVelocity(1000, mMaximumFling);
-        int vx = (int) mVelocityTracker.getXVelocity();
-        int vy = (int) mVelocityTracker.getYVelocity();
-
-        int scrollX = mScrollX;
-        int scrollY = mScrollY;
-        int overscrollDistance = mOverscrollDistance;
-        int overflingDistance = mOverflingDistance;
-
-        // Use the layer's scroll data if applicable.
-        if (mTouchMode == TOUCH_DRAG_LAYER_MODE) {
-            scrollX = mScrollingLayerRect.left;
-            scrollY = mScrollingLayerRect.top;
-            maxX = mScrollingLayerRect.right;
-            maxY = mScrollingLayerRect.bottom;
-            // No overscrolling for layers.
-            overscrollDistance = overflingDistance = 0;
-        }
-
-        if (mSnapScrollMode != SNAP_NONE) {
-            if ((mSnapScrollMode & SNAP_X) == SNAP_X) {
-                vy = 0;
-            } else {
-                vx = 0;
-            }
-        }
-        if ((maxX == 0 && vy == 0) || (maxY == 0 && vx == 0)) {
-            WebViewCore.resumePriority();
-            if (!mSelectingText) {
-                WebViewCore.resumeUpdatePicture(mWebViewCore);
-            }
-            if (mScroller.springBack(scrollX, scrollY, 0, maxX, 0, maxY)) {
-                invalidate();
-            }
-            return;
-        }
-        float currentVelocity = mScroller.getCurrVelocity();
-        float velocity = (float) Math.hypot(vx, vy);
-        if (mLastVelocity > 0 && currentVelocity > 0 && velocity
-                > mLastVelocity * MINIMUM_VELOCITY_RATIO_FOR_ACCELERATION) {
-            float deltaR = (float) (Math.abs(Math.atan2(mLastVelY, mLastVelX)
-                    - Math.atan2(vy, vx)));
-            final float circle = (float) (Math.PI) * 2.0f;
-            if (deltaR > circle * 0.9f || deltaR < circle * 0.1f) {
-                vx += currentVelocity * mLastVelX / mLastVelocity;
-                vy += currentVelocity * mLastVelY / mLastVelocity;
-                velocity = (float) Math.hypot(vx, vy);
-                if (DebugFlags.WEB_VIEW) {
-                    Log.v(LOGTAG, "doFling vx= " + vx + " vy=" + vy);
-                }
-            } else if (DebugFlags.WEB_VIEW) {
-                Log.v(LOGTAG, "doFling missed " + deltaR / circle);
-            }
-        } else if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "doFling start last=" + mLastVelocity
-                    + " current=" + currentVelocity
-                    + " vx=" + vx + " vy=" + vy
-                    + " maxX=" + maxX + " maxY=" + maxY
-                    + " scrollX=" + scrollX + " scrollY=" + scrollY
-                    + " layer=" + mCurrentScrollingLayerId);
-        }
-
-        // Allow sloppy flings without overscrolling at the edges.
-        if ((scrollX == 0 || scrollX == maxX) && Math.abs(vx) < Math.abs(vy)) {
-            vx = 0;
-        }
-        if ((scrollY == 0 || scrollY == maxY) && Math.abs(vy) < Math.abs(vx)) {
-            vy = 0;
-        }
-
-        if (overscrollDistance < overflingDistance) {
-            if ((vx > 0 && scrollX == -overscrollDistance) ||
-                    (vx < 0 && scrollX == maxX + overscrollDistance)) {
-                vx = 0;
-            }
-            if ((vy > 0 && scrollY == -overscrollDistance) ||
-                    (vy < 0 && scrollY == maxY + overscrollDistance)) {
-                vy = 0;
-            }
-        }
-
-        mLastVelX = vx;
-        mLastVelY = vy;
-        mLastVelocity = velocity;
-
-        // no horizontal overscroll if the content just fits
-        mScroller.fling(scrollX, scrollY, -vx, -vy, 0, maxX, 0, maxY,
-                maxX == 0 ? 0 : overflingDistance, overflingDistance);
-        // Duration is calculated based on velocity. With range boundaries and overscroll
-        // we may not know how long the final animation will take. (Hence the deprecation
-        // warning on the call below.) It's not a big deal for scroll bars but if webcore
-        // resumes during this effect we will take a performance hit. See computeScroll;
-        // we resume webcore there when the animation is finished.
-        final int time = mScroller.getDuration();
-
-        // Suppress scrollbars for layer scrolling.
-        if (mTouchMode != TOUCH_DRAG_LAYER_MODE) {
-            awakenScrollBars(time);
-        }
-
-        invalidate();
+        mProvider.flingScroll(vx, vy);
     }
 
     /**
@@ -7921,27 +1491,7 @@
     @Deprecated
     public View getZoomControls() {
         checkThread();
-        if (!getSettings().supportZoom()) {
-            Log.w(LOGTAG, "This WebView doesn't support zoom.");
-            return null;
-        }
-        return mZoomManager.getExternalZoomPicker();
-    }
-
-    void dismissZoomControl() {
-        mZoomManager.dismissZoomPicker();
-    }
-
-    float getDefaultZoomScale() {
-        return mZoomManager.getDefaultScale();
-    }
-
-    /**
-     * Return the overview scale of the WebView
-     * @return The overview scale.
-     */
-    float getZoomOverviewScale() {
-        return mZoomManager.getZoomOverviewScale();
+        return mProvider.getZoomControls();
     }
 
     /**
@@ -7949,7 +1499,7 @@
      */
     public boolean canZoomIn() {
         checkThread();
-        return mZoomManager.canZoomIn();
+        return mProvider.canZoomIn();
     }
 
     /**
@@ -7957,7 +1507,7 @@
      */
     public boolean canZoomOut() {
         checkThread();
-        return mZoomManager.canZoomOut();
+        return mProvider.canZoomOut();
     }
 
     /**
@@ -7966,7 +1516,7 @@
      */
     public boolean zoomIn() {
         checkThread();
-        return mZoomManager.zoomIn();
+        return mProvider.zoomIn();
     }
 
     /**
@@ -7975,2262 +1525,7 @@
      */
     public boolean zoomOut() {
         checkThread();
-        return mZoomManager.zoomOut();
-    }
-
-    /**
-     * This selects the best clickable target at mLastTouchX and mLastTouchY
-     * and calls showCursorTimed on the native side
-     */
-    private void updateSelection() {
-        if (mNativeClass == 0 || sDisableNavcache) {
-            return;
-        }
-        mPrivateHandler.removeMessages(UPDATE_SELECTION);
-        // mLastTouchX and mLastTouchY are the point in the current viewport
-        int contentX = viewToContentX(mLastTouchX + mScrollX);
-        int contentY = viewToContentY(mLastTouchY + mScrollY);
-        int slop = viewToContentDimension(mNavSlop);
-        Rect rect = new Rect(contentX - slop, contentY - slop,
-                contentX + slop, contentY + slop);
-        nativeSelectBestAt(rect);
-        mInitialHitTestResult = hitTestResult(null);
-    }
-
-    /**
-     * Scroll the focused text field to match the WebTextView
-     * @param xPercent New x position of the WebTextView from 0 to 1.
-     */
-    /*package*/ void scrollFocusedTextInputX(float xPercent) {
-        if (!inEditingMode() || mWebViewCore == null) {
-            return;
-        }
-        mWebViewCore.sendMessage(EventHub.SCROLL_TEXT_INPUT, 0,
-                new Float(xPercent));
-    }
-
-    /**
-     * Scroll the focused textarea vertically to match the WebTextView
-     * @param y New y position of the WebTextView in view coordinates
-     */
-    /* package */ void scrollFocusedTextInputY(int y) {
-        if (!inEditingMode() || mWebViewCore == null) {
-            return;
-        }
-        mWebViewCore.sendMessage(EventHub.SCROLL_TEXT_INPUT, 0, viewToContentDimension(y));
-    }
-
-    /**
-     * Set our starting point and time for a drag from the WebTextView.
-     */
-    /*package*/ void initiateTextFieldDrag(float x, float y, long eventTime) {
-        if (!inEditingMode()) {
-            return;
-        }
-        mLastTouchX = Math.round(x + mWebTextView.getLeft() - mScrollX);
-        mLastTouchY = Math.round(y + mWebTextView.getTop() - mScrollY);
-        mLastTouchTime = eventTime;
-        if (!mScroller.isFinished()) {
-            abortAnimation();
-        }
-        mSnapScrollMode = SNAP_NONE;
-        mVelocityTracker = VelocityTracker.obtain();
-        mTouchMode = TOUCH_DRAG_START_MODE;
-    }
-
-    /**
-     * Given a motion event from the WebTextView, set its location to our
-     * coordinates, and handle the event.
-     */
-    /*package*/ boolean textFieldDrag(MotionEvent event) {
-        if (!inEditingMode()) {
-            return false;
-        }
-        mDragFromTextInput = true;
-        event.offsetLocation((mWebTextView.getLeft() - mScrollX),
-                (mWebTextView.getTop() - mScrollY));
-        boolean result = onTouchEvent(event);
-        mDragFromTextInput = false;
-        return result;
-    }
-
-    /**
-     * Due a touch up from a WebTextView.  This will be handled by webkit to
-     * change the selection.
-     * @param event MotionEvent in the WebTextView's coordinates.
-     */
-    /*package*/ void touchUpOnTextField(MotionEvent event) {
-        if (!inEditingMode()) {
-            return;
-        }
-        int x = viewToContentX((int) event.getX() + mWebTextView.getLeft());
-        int y = viewToContentY((int) event.getY() + mWebTextView.getTop());
-        int slop = viewToContentDimension(mNavSlop);
-        nativeMotionUp(x, y, slop);
-    }
-
-    /**
-     * Called when pressing the center key or trackball on a textfield.
-     */
-    /*package*/ void centerKeyPressOnTextField() {
-        mWebViewCore.sendMessage(EventHub.CLICK, nativeCursorFramePointer(),
-                    nativeCursorNodePointer());
-    }
-
-    private void doShortPress() {
-        if (mNativeClass == 0) {
-            return;
-        }
-        if (mPreventDefault == PREVENT_DEFAULT_YES) {
-            return;
-        }
-        mTouchMode = TOUCH_DONE_MODE;
-        updateSelection();
-        switchOutDrawHistory();
-        // mLastTouchX and mLastTouchY are the point in the current viewport
-        int contentX = viewToContentX(mLastTouchX + mScrollX);
-        int contentY = viewToContentY(mLastTouchY + mScrollY);
-        int slop = viewToContentDimension(mNavSlop);
-        if (sDisableNavcache && !mTouchHighlightRegion.isEmpty()) {
-            // set mTouchHighlightRequested to 0 to cause an immediate
-            // drawing of the touch rings
-            mTouchHighlightRequested = 0;
-            invalidate(mTouchHighlightRegion.getBounds());
-            mPrivateHandler.postDelayed(new Runnable() {
-                @Override
-                public void run() {
-                    removeTouchHighlight();
-                }
-            }, ViewConfiguration.getPressedStateDuration());
-        }
-        if (mFocusedNode != null && mFocusedNode.mIntentUrl != null) {
-            playSoundEffect(SoundEffectConstants.CLICK);
-            overrideLoading(mFocusedNode.mIntentUrl);
-        } else if (sDisableNavcache) {
-            WebViewCore.TouchUpData touchUpData = new WebViewCore.TouchUpData();
-            // use "0" as generation id to inform WebKit to use the same x/y as
-            // it used when processing GET_TOUCH_HIGHLIGHT_RECTS
-            touchUpData.mMoveGeneration = 0;
-            mWebViewCore.sendMessage(EventHub.TOUCH_UP, touchUpData);
-        } else if (nativePointInNavCache(contentX, contentY, slop)) {
-            WebViewCore.MotionUpData motionUpData = new WebViewCore
-                    .MotionUpData();
-            motionUpData.mFrame = nativeCacheHitFramePointer();
-            motionUpData.mNode = nativeCacheHitNodePointer();
-            motionUpData.mBounds = nativeCacheHitNodeBounds();
-            motionUpData.mX = contentX;
-            motionUpData.mY = contentY;
-            mWebViewCore.sendMessageAtFrontOfQueue(EventHub.VALID_NODE_BOUNDS,
-                    motionUpData);
-        } else {
-            doMotionUp(contentX, contentY);
-        }
-    }
-
-    private void doMotionUp(int contentX, int contentY) {
-        int slop = viewToContentDimension(mNavSlop);
-        if (nativeMotionUp(contentX, contentY, slop) && mLogEvent) {
-            EventLog.writeEvent(EventLogTags.BROWSER_SNAP_CENTER);
-        }
-        if (nativeHasCursorNode() && !nativeCursorIsTextInput()) {
-            playSoundEffect(SoundEffectConstants.CLICK);
-        }
-    }
-
-    void sendPluginDrawMsg() {
-        mWebViewCore.sendMessage(EventHub.PLUGIN_SURFACE_READY);
-    }
-
-    /**
-     * Returns plugin bounds if x/y in content coordinates corresponds to a
-     * plugin. Otherwise a NULL rectangle is returned.
-     */
-    Rect getPluginBounds(int x, int y) {
-        int slop = viewToContentDimension(mNavSlop);
-        if (nativePointInNavCache(x, y, slop) && nativeCacheHitIsPlugin()) {
-            return nativeCacheHitNodeBounds();
-        } else {
-            return null;
-        }
-    }
-
-    /*
-     * Return true if the rect (e.g. plugin) is fully visible and maximized
-     * inside the WebView.
-     */
-    boolean isRectFitOnScreen(Rect rect) {
-        final int rectWidth = rect.width();
-        final int rectHeight = rect.height();
-        final int viewWidth = getViewWidth();
-        final int viewHeight = getViewHeightWithTitle();
-        float scale = Math.min((float) viewWidth / rectWidth, (float) viewHeight / rectHeight);
-        scale = mZoomManager.computeScaleWithLimits(scale);
-        return !mZoomManager.willScaleTriggerZoom(scale)
-                && contentToViewX(rect.left) >= mScrollX
-                && contentToViewX(rect.right) <= mScrollX + viewWidth
-                && contentToViewY(rect.top) >= mScrollY
-                && contentToViewY(rect.bottom) <= mScrollY + viewHeight;
-    }
-
-    /*
-     * Maximize and center the rectangle, specified in the document coordinate
-     * space, inside the WebView. If the zoom doesn't need to be changed, do an
-     * animated scroll to center it. If the zoom needs to be changed, find the
-     * zoom center and do a smooth zoom transition. The rect is in document
-     * coordinates
-     */
-    void centerFitRect(Rect rect) {
-        final int rectWidth = rect.width();
-        final int rectHeight = rect.height();
-        final int viewWidth = getViewWidth();
-        final int viewHeight = getViewHeightWithTitle();
-        float scale = Math.min((float) viewWidth / rectWidth, (float) viewHeight
-                / rectHeight);
-        scale = mZoomManager.computeScaleWithLimits(scale);
-        if (!mZoomManager.willScaleTriggerZoom(scale)) {
-            pinScrollTo(contentToViewX(rect.left + rectWidth / 2) - viewWidth / 2,
-                    contentToViewY(rect.top + rectHeight / 2) - viewHeight / 2,
-                    true, 0);
-        } else {
-            float actualScale = mZoomManager.getScale();
-            float oldScreenX = rect.left * actualScale - mScrollX;
-            float rectViewX = rect.left * scale;
-            float rectViewWidth = rectWidth * scale;
-            float newMaxWidth = mContentWidth * scale;
-            float newScreenX = (viewWidth - rectViewWidth) / 2;
-            // pin the newX to the WebView
-            if (newScreenX > rectViewX) {
-                newScreenX = rectViewX;
-            } else if (newScreenX > (newMaxWidth - rectViewX - rectViewWidth)) {
-                newScreenX = viewWidth - (newMaxWidth - rectViewX);
-            }
-            float zoomCenterX = (oldScreenX * scale - newScreenX * actualScale)
-                    / (scale - actualScale);
-            float oldScreenY = rect.top * actualScale + getTitleHeight()
-                    - mScrollY;
-            float rectViewY = rect.top * scale + getTitleHeight();
-            float rectViewHeight = rectHeight * scale;
-            float newMaxHeight = mContentHeight * scale + getTitleHeight();
-            float newScreenY = (viewHeight - rectViewHeight) / 2;
-            // pin the newY to the WebView
-            if (newScreenY > rectViewY) {
-                newScreenY = rectViewY;
-            } else if (newScreenY > (newMaxHeight - rectViewY - rectViewHeight)) {
-                newScreenY = viewHeight - (newMaxHeight - rectViewY);
-            }
-            float zoomCenterY = (oldScreenY * scale - newScreenY * actualScale)
-                    / (scale - actualScale);
-            mZoomManager.setZoomCenter(zoomCenterX, zoomCenterY);
-            mZoomManager.startZoomAnimation(scale, false);
-        }
-    }
-
-    // Called by JNI to handle a touch on a node representing an email address,
-    // address, or phone number
-    private void overrideLoading(String url) {
-        mCallbackProxy.uiOverrideUrlLoading(url);
-    }
-
-    @Override
-    public boolean requestFocus(int direction, Rect previouslyFocusedRect) {
-        // FIXME: If a subwindow is showing find, and the user touches the
-        // background window, it can steal focus.
-        if (mFindIsUp) return false;
-        boolean result = false;
-        if (inEditingMode()) {
-            result = mWebTextView.requestFocus(direction,
-                    previouslyFocusedRect);
-        } else {
-            result = super.requestFocus(direction, previouslyFocusedRect);
-            if (mWebViewCore.getSettings().getNeedInitialFocus() && !isInTouchMode()) {
-                // For cases such as GMail, where we gain focus from a direction,
-                // we want to move to the first available link.
-                // FIXME: If there are no visible links, we may not want to
-                int fakeKeyDirection = 0;
-                switch(direction) {
-                    case View.FOCUS_UP:
-                        fakeKeyDirection = KeyEvent.KEYCODE_DPAD_UP;
-                        break;
-                    case View.FOCUS_DOWN:
-                        fakeKeyDirection = KeyEvent.KEYCODE_DPAD_DOWN;
-                        break;
-                    case View.FOCUS_LEFT:
-                        fakeKeyDirection = KeyEvent.KEYCODE_DPAD_LEFT;
-                        break;
-                    case View.FOCUS_RIGHT:
-                        fakeKeyDirection = KeyEvent.KEYCODE_DPAD_RIGHT;
-                        break;
-                    default:
-                        return result;
-                }
-                if (mNativeClass != 0 && !nativeHasCursorNode()) {
-                    navHandledKey(fakeKeyDirection, 1, true, 0);
-                }
-            }
-        }
-        return result;
-    }
-
-    @Override
-    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
-        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
-
-        int heightMode = MeasureSpec.getMode(heightMeasureSpec);
-        int heightSize = MeasureSpec.getSize(heightMeasureSpec);
-        int widthMode = MeasureSpec.getMode(widthMeasureSpec);
-        int widthSize = MeasureSpec.getSize(widthMeasureSpec);
-
-        int measuredHeight = heightSize;
-        int measuredWidth = widthSize;
-
-        // Grab the content size from WebViewCore.
-        int contentHeight = contentToViewDimension(mContentHeight);
-        int contentWidth = contentToViewDimension(mContentWidth);
-
-//        Log.d(LOGTAG, "------- measure " + heightMode);
-
-        if (heightMode != MeasureSpec.EXACTLY) {
-            mHeightCanMeasure = true;
-            measuredHeight = contentHeight;
-            if (heightMode == MeasureSpec.AT_MOST) {
-                // If we are larger than the AT_MOST height, then our height can
-                // no longer be measured and we should scroll internally.
-                if (measuredHeight > heightSize) {
-                    measuredHeight = heightSize;
-                    mHeightCanMeasure = false;
-                    measuredHeight |= MEASURED_STATE_TOO_SMALL;
-                }
-            }
-        } else {
-            mHeightCanMeasure = false;
-        }
-        if (mNativeClass != 0) {
-            nativeSetHeightCanMeasure(mHeightCanMeasure);
-        }
-        // For the width, always use the given size unless unspecified.
-        if (widthMode == MeasureSpec.UNSPECIFIED) {
-            mWidthCanMeasure = true;
-            measuredWidth = contentWidth;
-        } else {
-            if (measuredWidth < contentWidth) {
-                measuredWidth |= MEASURED_STATE_TOO_SMALL;
-            }
-            mWidthCanMeasure = false;
-        }
-
-        synchronized (this) {
-            setMeasuredDimension(measuredWidth, measuredHeight);
-        }
-    }
-
-    @Override
-    public boolean requestChildRectangleOnScreen(View child,
-                                                 Rect rect,
-                                                 boolean immediate) {
-        if (mNativeClass == 0) {
-            return false;
-        }
-        // don't scroll while in zoom animation. When it is done, we will adjust
-        // the necessary components (e.g., WebTextView if it is in editing mode)
-        if (mZoomManager.isFixedLengthAnimationInProgress()) {
-            return false;
-        }
-
-        rect.offset(child.getLeft() - child.getScrollX(),
-                child.getTop() - child.getScrollY());
-
-        Rect content = new Rect(viewToContentX(mScrollX),
-                viewToContentY(mScrollY),
-                viewToContentX(mScrollX + getWidth()
-                - getVerticalScrollbarWidth()),
-                viewToContentY(mScrollY + getViewHeightWithTitle()));
-        content = nativeSubtractLayers(content);
-        int screenTop = contentToViewY(content.top);
-        int screenBottom = contentToViewY(content.bottom);
-        int height = screenBottom - screenTop;
-        int scrollYDelta = 0;
-
-        if (rect.bottom > screenBottom) {
-            int oneThirdOfScreenHeight = height / 3;
-            if (rect.height() > 2 * oneThirdOfScreenHeight) {
-                // If the rectangle is too tall to fit in the bottom two thirds
-                // of the screen, place it at the top.
-                scrollYDelta = rect.top - screenTop;
-            } else {
-                // If the rectangle will still fit on screen, we want its
-                // top to be in the top third of the screen.
-                scrollYDelta = rect.top - (screenTop + oneThirdOfScreenHeight);
-            }
-        } else if (rect.top < screenTop) {
-            scrollYDelta = rect.top - screenTop;
-        }
-
-        int screenLeft = contentToViewX(content.left);
-        int screenRight = contentToViewX(content.right);
-        int width = screenRight - screenLeft;
-        int scrollXDelta = 0;
-
-        if (rect.right > screenRight && rect.left > screenLeft) {
-            if (rect.width() > width) {
-                scrollXDelta += (rect.left - screenLeft);
-            } else {
-                scrollXDelta += (rect.right - screenRight);
-            }
-        } else if (rect.left < screenLeft) {
-            scrollXDelta -= (screenLeft - rect.left);
-        }
-
-        if ((scrollYDelta | scrollXDelta) != 0) {
-            return pinScrollBy(scrollXDelta, scrollYDelta, !immediate, 0);
-        }
-
-        return false;
-    }
-
-    /* package */ void replaceTextfieldText(int oldStart, int oldEnd,
-            String replace, int newStart, int newEnd) {
-        WebViewCore.ReplaceTextData arg = new WebViewCore.ReplaceTextData();
-        arg.mReplace = replace;
-        arg.mNewStart = newStart;
-        arg.mNewEnd = newEnd;
-        mTextGeneration++;
-        arg.mTextGeneration = mTextGeneration;
-        mWebViewCore.sendMessage(EventHub.REPLACE_TEXT, oldStart, oldEnd, arg);
-    }
-
-    /* package */ void passToJavaScript(String currentText, KeyEvent event) {
-        // check if mWebViewCore has been destroyed
-        if (mWebViewCore == null) {
-            return;
-        }
-        WebViewCore.JSKeyData arg = new WebViewCore.JSKeyData();
-        arg.mEvent = event;
-        arg.mCurrentText = currentText;
-        // Increase our text generation number, and pass it to webcore thread
-        mTextGeneration++;
-        mWebViewCore.sendMessage(EventHub.PASS_TO_JS, mTextGeneration, 0, arg);
-        // WebKit's document state is not saved until about to leave the page.
-        // To make sure the host application, like Browser, has the up to date
-        // document state when it goes to background, we force to save the
-        // document state.
-        mWebViewCore.removeMessages(EventHub.SAVE_DOCUMENT_STATE);
-        mWebViewCore.sendMessageDelayed(EventHub.SAVE_DOCUMENT_STATE,
-                cursorData(), 1000);
-    }
-
-    /**
-     * @hide
-     */
-    public synchronized WebViewCore getWebViewCore() {
-        return mWebViewCore;
-    }
-
-    /**
-     * Used only by TouchEventQueue to store pending touch events.
-     */
-    private static class QueuedTouch {
-        long mSequence;
-        MotionEvent mEvent; // Optional
-        TouchEventData mTed; // Optional
-
-        QueuedTouch mNext;
-
-        public QueuedTouch set(TouchEventData ted) {
-            mSequence = ted.mSequence;
-            mTed = ted;
-            mEvent = null;
-            mNext = null;
-            return this;
-        }
-
-        public QueuedTouch set(MotionEvent ev, long sequence) {
-            mEvent = MotionEvent.obtain(ev);
-            mSequence = sequence;
-            mTed = null;
-            mNext = null;
-            return this;
-        }
-
-        public QueuedTouch add(QueuedTouch other) {
-            if (other.mSequence < mSequence) {
-                other.mNext = this;
-                return other;
-            }
-
-            QueuedTouch insertAt = this;
-            while (insertAt.mNext != null && insertAt.mNext.mSequence < other.mSequence) {
-                insertAt = insertAt.mNext;
-            }
-            other.mNext = insertAt.mNext;
-            insertAt.mNext = other;
-            return this;
-        }
-    }
-
-    /**
-     * WebView handles touch events asynchronously since some events must be passed to WebKit
-     * for potentially slower processing. TouchEventQueue serializes touch events regardless
-     * of which path they take to ensure that no events are ever processed out of order
-     * by WebView.
-     */
-    private class TouchEventQueue {
-        private long mNextTouchSequence = Long.MIN_VALUE + 1;
-        private long mLastHandledTouchSequence = Long.MIN_VALUE;
-        private long mIgnoreUntilSequence = Long.MIN_VALUE + 1;
-
-        // Events waiting to be processed.
-        private QueuedTouch mTouchEventQueue;
-
-        // Known events that are waiting on a response before being enqueued.
-        private QueuedTouch mPreQueue;
-
-        // Pool of QueuedTouch objects saved for later use.
-        private QueuedTouch mQueuedTouchRecycleBin;
-        private int mQueuedTouchRecycleCount;
-
-        private long mLastEventTime = Long.MAX_VALUE;
-        private static final int MAX_RECYCLED_QUEUED_TOUCH = 15;
-
-        // milliseconds until we abandon hope of getting all of a previous gesture
-        private static final int QUEUED_GESTURE_TIMEOUT = 1000;
-
-        private QueuedTouch obtainQueuedTouch() {
-            if (mQueuedTouchRecycleBin != null) {
-                QueuedTouch result = mQueuedTouchRecycleBin;
-                mQueuedTouchRecycleBin = result.mNext;
-                mQueuedTouchRecycleCount--;
-                return result;
-            }
-            return new QueuedTouch();
-        }
-
-        /**
-         * Allow events with any currently missing sequence numbers to be skipped in processing.
-         */
-        public void ignoreCurrentlyMissingEvents() {
-            mIgnoreUntilSequence = mNextTouchSequence;
-
-            // Run any events we have available and complete, pre-queued or otherwise.
-            runQueuedAndPreQueuedEvents();
-        }
-
-        private void runQueuedAndPreQueuedEvents() {
-            QueuedTouch qd = mPreQueue;
-            boolean fromPreQueue = true;
-            while (qd != null && qd.mSequence == mLastHandledTouchSequence + 1) {
-                handleQueuedTouch(qd);
-                QueuedTouch recycleMe = qd;
-                if (fromPreQueue) {
-                    mPreQueue = qd.mNext;
-                } else {
-                    mTouchEventQueue = qd.mNext;
-                }
-                recycleQueuedTouch(recycleMe);
-                mLastHandledTouchSequence++;
-
-                long nextPre = mPreQueue != null ? mPreQueue.mSequence : Long.MAX_VALUE;
-                long nextQueued = mTouchEventQueue != null ?
-                        mTouchEventQueue.mSequence : Long.MAX_VALUE;
-                fromPreQueue = nextPre < nextQueued;
-                qd = fromPreQueue ? mPreQueue : mTouchEventQueue;
-            }
-        }
-
-        /**
-         * Add a TouchEventData to the pre-queue.
-         *
-         * An event in the pre-queue is an event that we know about that
-         * has been sent to webkit, but that we haven't received back and
-         * enqueued into the normal touch queue yet. If webkit ever times
-         * out and we need to ignore currently missing events, we'll run
-         * events from the pre-queue to patch the holes.
-         *
-         * @param ted TouchEventData to pre-queue
-         */
-        public void preQueueTouchEventData(TouchEventData ted) {
-            QueuedTouch newTouch = obtainQueuedTouch().set(ted);
-            if (mPreQueue == null) {
-                mPreQueue = newTouch;
-            } else {
-                QueuedTouch insertionPoint = mPreQueue;
-                while (insertionPoint.mNext != null &&
-                        insertionPoint.mNext.mSequence < newTouch.mSequence) {
-                    insertionPoint = insertionPoint.mNext;
-                }
-                newTouch.mNext = insertionPoint.mNext;
-                insertionPoint.mNext = newTouch;
-            }
-        }
-
-        private void recycleQueuedTouch(QueuedTouch qd) {
-            if (mQueuedTouchRecycleCount < MAX_RECYCLED_QUEUED_TOUCH) {
-                qd.mNext = mQueuedTouchRecycleBin;
-                mQueuedTouchRecycleBin = qd;
-                mQueuedTouchRecycleCount++;
-            }
-        }
-
-        /**
-         * Reset the touch event queue. This will dump any pending events
-         * and reset the sequence numbering.
-         */
-        public void reset() {
-            mNextTouchSequence = Long.MIN_VALUE + 1;
-            mLastHandledTouchSequence = Long.MIN_VALUE;
-            mIgnoreUntilSequence = Long.MIN_VALUE + 1;
-            while (mTouchEventQueue != null) {
-                QueuedTouch recycleMe = mTouchEventQueue;
-                mTouchEventQueue = mTouchEventQueue.mNext;
-                recycleQueuedTouch(recycleMe);
-            }
-            while (mPreQueue != null) {
-                QueuedTouch recycleMe = mPreQueue;
-                mPreQueue = mPreQueue.mNext;
-                recycleQueuedTouch(recycleMe);
-            }
-        }
-
-        /**
-         * Return the next valid sequence number for tagging incoming touch events.
-         * @return The next touch event sequence number
-         */
-        public long nextTouchSequence() {
-            return mNextTouchSequence++;
-        }
-
-        /**
-         * Enqueue a touch event in the form of TouchEventData.
-         * The sequence number will be read from the mSequence field of the argument.
-         *
-         * If the touch event's sequence number is the next in line to be processed, it will
-         * be handled before this method returns. Any subsequent events that have already
-         * been queued will also be processed in their proper order.
-         *
-         * @param ted Touch data to be processed in order.
-         * @return true if the event was processed before returning, false if it was just enqueued.
-         */
-        public boolean enqueueTouchEvent(TouchEventData ted) {
-            // Remove from the pre-queue if present
-            QueuedTouch preQueue = mPreQueue;
-            if (preQueue != null) {
-                // On exiting this block, preQueue is set to the pre-queued QueuedTouch object
-                // if it was present in the pre-queue, and removed from the pre-queue itself.
-                if (preQueue.mSequence == ted.mSequence) {
-                    mPreQueue = preQueue.mNext;
-                } else {
-                    QueuedTouch prev = preQueue;
-                    preQueue = null;
-                    while (prev.mNext != null) {
-                        if (prev.mNext.mSequence == ted.mSequence) {
-                            preQueue = prev.mNext;
-                            prev.mNext = preQueue.mNext;
-                            break;
-                        } else {
-                            prev = prev.mNext;
-                        }
-                    }
-                }
-            }
-
-            if (ted.mSequence < mLastHandledTouchSequence) {
-                // Stale event and we already moved on; drop it. (Should not be common.)
-                Log.w(LOGTAG, "Stale touch event " + MotionEvent.actionToString(ted.mAction) +
-                        " received from webcore; ignoring");
-                return false;
-            }
-
-            if (dropStaleGestures(ted.mMotionEvent, ted.mSequence)) {
-                return false;
-            }
-
-            // dropStaleGestures above might have fast-forwarded us to
-            // an event we have already.
-            runNextQueuedEvents();
-
-            if (mLastHandledTouchSequence + 1 == ted.mSequence) {
-                if (preQueue != null) {
-                    recycleQueuedTouch(preQueue);
-                    preQueue = null;
-                }
-                handleQueuedTouchEventData(ted);
-
-                mLastHandledTouchSequence++;
-
-                // Do we have any more? Run them if so.
-                runNextQueuedEvents();
-            } else {
-                // Reuse the pre-queued object if we had it.
-                QueuedTouch qd = preQueue != null ? preQueue : obtainQueuedTouch().set(ted);
-                mTouchEventQueue = mTouchEventQueue == null ? qd : mTouchEventQueue.add(qd);
-            }
-            return true;
-        }
-
-        /**
-         * Enqueue a touch event in the form of a MotionEvent from the framework.
-         *
-         * If the touch event's sequence number is the next in line to be processed, it will
-         * be handled before this method returns. Any subsequent events that have already
-         * been queued will also be processed in their proper order.
-         *
-         * @param ev MotionEvent to be processed in order
-         */
-        public void enqueueTouchEvent(MotionEvent ev) {
-            final long sequence = nextTouchSequence();
-
-            if (dropStaleGestures(ev, sequence)) {
-                return;
-            }
-
-            // dropStaleGestures above might have fast-forwarded us to
-            // an event we have already.
-            runNextQueuedEvents();
-
-            if (mLastHandledTouchSequence + 1 == sequence) {
-                handleQueuedMotionEvent(ev);
-
-                mLastHandledTouchSequence++;
-
-                // Do we have any more? Run them if so.
-                runNextQueuedEvents();
-            } else {
-                QueuedTouch qd = obtainQueuedTouch().set(ev, sequence);
-                mTouchEventQueue = mTouchEventQueue == null ? qd : mTouchEventQueue.add(qd);
-            }
-        }
-
-        private void runNextQueuedEvents() {
-            QueuedTouch qd = mTouchEventQueue;
-            while (qd != null && qd.mSequence == mLastHandledTouchSequence + 1) {
-                handleQueuedTouch(qd);
-                QueuedTouch recycleMe = qd;
-                qd = qd.mNext;
-                recycleQueuedTouch(recycleMe);
-                mLastHandledTouchSequence++;
-            }
-            mTouchEventQueue = qd;
-        }
-
-        private boolean dropStaleGestures(MotionEvent ev, long sequence) {
-            if (ev != null && ev.getAction() == MotionEvent.ACTION_MOVE && !mConfirmMove) {
-                // This is to make sure that we don't attempt to process a tap
-                // or long press when webkit takes too long to get back to us.
-                // The movement will be properly confirmed when we process the
-                // enqueued event later.
-                final int dx = Math.round(ev.getX()) - mLastTouchX;
-                final int dy = Math.round(ev.getY()) - mLastTouchY;
-                if (dx * dx + dy * dy > mTouchSlopSquare) {
-                    mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
-                    mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
-                }
-            }
-
-            if (mTouchEventQueue == null) {
-                return sequence <= mLastHandledTouchSequence;
-            }
-
-            // If we have a new down event and it's been a while since the last event
-            // we saw, catch up as best we can and keep going.
-            if (ev != null && ev.getAction() == MotionEvent.ACTION_DOWN) {
-                long eventTime = ev.getEventTime();
-                long lastHandledEventTime = mLastEventTime;
-                if (eventTime > lastHandledEventTime + QUEUED_GESTURE_TIMEOUT) {
-                    Log.w(LOGTAG, "Got ACTION_DOWN but still waiting on stale event. " +
-                            "Catching up.");
-                    runQueuedAndPreQueuedEvents();
-
-                    // Drop leftovers that we truly don't have.
-                    QueuedTouch qd = mTouchEventQueue;
-                    while (qd != null && qd.mSequence < sequence) {
-                        QueuedTouch recycleMe = qd;
-                        qd = qd.mNext;
-                        recycleQueuedTouch(recycleMe);
-                    }
-                    mTouchEventQueue = qd;
-                    mLastHandledTouchSequence = sequence - 1;
-                }
-            }
-
-            if (mIgnoreUntilSequence - 1 > mLastHandledTouchSequence) {
-                QueuedTouch qd = mTouchEventQueue;
-                while (qd != null && qd.mSequence < mIgnoreUntilSequence) {
-                    QueuedTouch recycleMe = qd;
-                    qd = qd.mNext;
-                    recycleQueuedTouch(recycleMe);
-                }
-                mTouchEventQueue = qd;
-                mLastHandledTouchSequence = mIgnoreUntilSequence - 1;
-            }
-
-            if (mPreQueue != null) {
-                // Drop stale prequeued events
-                QueuedTouch qd = mPreQueue;
-                while (qd != null && qd.mSequence < mIgnoreUntilSequence) {
-                    QueuedTouch recycleMe = qd;
-                    qd = qd.mNext;
-                    recycleQueuedTouch(recycleMe);
-                }
-                mPreQueue = qd;
-            }
-
-            return sequence <= mLastHandledTouchSequence;
-        }
-
-        private void handleQueuedTouch(QueuedTouch qt) {
-            if (qt.mTed != null) {
-                handleQueuedTouchEventData(qt.mTed);
-            } else {
-                handleQueuedMotionEvent(qt.mEvent);
-                qt.mEvent.recycle();
-            }
-        }
-
-        private void handleQueuedMotionEvent(MotionEvent ev) {
-            mLastEventTime = ev.getEventTime();
-            int action = ev.getActionMasked();
-            if (ev.getPointerCount() > 1) {  // Multi-touch
-                handleMultiTouchInWebView(ev);
-            } else {
-                final ScaleGestureDetector detector = mZoomManager.getMultiTouchGestureDetector();
-                if (detector != null && mPreventDefault != PREVENT_DEFAULT_YES) {
-                    // ScaleGestureDetector needs a consistent event stream to operate properly.
-                    // It won't take any action with fewer than two pointers, but it needs to
-                    // update internal bookkeeping state.
-                    detector.onTouchEvent(ev);
-                }
-
-                handleTouchEventCommon(ev, action, Math.round(ev.getX()), Math.round(ev.getY()));
-            }
-        }
-
-        private void handleQueuedTouchEventData(TouchEventData ted) {
-            if (ted.mMotionEvent != null) {
-                mLastEventTime = ted.mMotionEvent.getEventTime();
-            }
-            if (!ted.mReprocess) {
-                if (ted.mAction == MotionEvent.ACTION_DOWN
-                        && mPreventDefault == PREVENT_DEFAULT_MAYBE_YES) {
-                    // if prevent default is called from WebCore, UI
-                    // will not handle the rest of the touch events any
-                    // more.
-                    mPreventDefault = ted.mNativeResult ? PREVENT_DEFAULT_YES
-                            : PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN;
-                } else if (ted.mAction == MotionEvent.ACTION_MOVE
-                        && mPreventDefault == PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN) {
-                    // the return for the first ACTION_MOVE will decide
-                    // whether UI will handle touch or not. Currently no
-                    // support for alternating prevent default
-                    mPreventDefault = ted.mNativeResult ? PREVENT_DEFAULT_YES
-                            : PREVENT_DEFAULT_NO;
-                }
-                if (mPreventDefault == PREVENT_DEFAULT_YES) {
-                    mTouchHighlightRegion.setEmpty();
-                }
-            } else {
-                if (ted.mPoints.length > 1) {  // multi-touch
-                    if (!ted.mNativeResult && mPreventDefault != PREVENT_DEFAULT_YES) {
-                        mPreventDefault = PREVENT_DEFAULT_NO;
-                        handleMultiTouchInWebView(ted.mMotionEvent);
-                    } else {
-                        mPreventDefault = PREVENT_DEFAULT_YES;
-                    }
-                    return;
-                }
-
-                // prevent default is not called in WebCore, so the
-                // message needs to be reprocessed in UI
-                if (!ted.mNativeResult) {
-                    // Following is for single touch.
-                    switch (ted.mAction) {
-                        case MotionEvent.ACTION_DOWN:
-                            mLastDeferTouchX = ted.mPointsInView[0].x;
-                            mLastDeferTouchY = ted.mPointsInView[0].y;
-                            mDeferTouchMode = TOUCH_INIT_MODE;
-                            break;
-                        case MotionEvent.ACTION_MOVE: {
-                            // no snapping in defer process
-                            int x = ted.mPointsInView[0].x;
-                            int y = ted.mPointsInView[0].y;
-
-                            if (mDeferTouchMode != TOUCH_DRAG_MODE) {
-                                mDeferTouchMode = TOUCH_DRAG_MODE;
-                                mLastDeferTouchX = x;
-                                mLastDeferTouchY = y;
-                                startScrollingLayer(x, y);
-                                startDrag();
-                            }
-                            int deltaX = pinLocX((int) (mScrollX
-                                    + mLastDeferTouchX - x))
-                                    - mScrollX;
-                            int deltaY = pinLocY((int) (mScrollY
-                                    + mLastDeferTouchY - y))
-                                    - mScrollY;
-                            doDrag(deltaX, deltaY);
-                            if (deltaX != 0) mLastDeferTouchX = x;
-                            if (deltaY != 0) mLastDeferTouchY = y;
-                            break;
-                        }
-                        case MotionEvent.ACTION_UP:
-                        case MotionEvent.ACTION_CANCEL:
-                            if (mDeferTouchMode == TOUCH_DRAG_MODE) {
-                                // no fling in defer process
-                                mScroller.springBack(mScrollX, mScrollY, 0,
-                                        computeMaxScrollX(), 0,
-                                        computeMaxScrollY());
-                                invalidate();
-                                WebViewCore.resumePriority();
-                                WebViewCore.resumeUpdatePicture(mWebViewCore);
-                            }
-                            mDeferTouchMode = TOUCH_DONE_MODE;
-                            break;
-                        case WebViewCore.ACTION_DOUBLETAP:
-                            // doDoubleTap() needs mLastTouchX/Y as anchor
-                            mLastDeferTouchX = ted.mPointsInView[0].x;
-                            mLastDeferTouchY = ted.mPointsInView[0].y;
-                            mZoomManager.handleDoubleTap(mLastTouchX, mLastTouchY);
-                            mDeferTouchMode = TOUCH_DONE_MODE;
-                            break;
-                        case WebViewCore.ACTION_LONGPRESS:
-                            HitTestResult hitTest = getHitTestResult();
-                            if (hitTest != null && hitTest.mType
-                                    != HitTestResult.UNKNOWN_TYPE) {
-                                performLongClick();
-                            }
-                            mDeferTouchMode = TOUCH_DONE_MODE;
-                            break;
-                    }
-                }
-            }
-        }
-    }
-
-    //-------------------------------------------------------------------------
-    // Methods can be called from a separate thread, like WebViewCore
-    // If it needs to call the View system, it has to send message.
-    //-------------------------------------------------------------------------
-
-    /**
-     * General handler to receive message coming from webkit thread
-     */
-    class PrivateHandler extends Handler {
-        @Override
-        public void handleMessage(Message msg) {
-            // exclude INVAL_RECT_MSG_ID since it is frequently output
-            if (DebugFlags.WEB_VIEW && msg.what != INVAL_RECT_MSG_ID) {
-                if (msg.what >= FIRST_PRIVATE_MSG_ID
-                        && msg.what <= LAST_PRIVATE_MSG_ID) {
-                    Log.v(LOGTAG, HandlerPrivateDebugString[msg.what
-                            - FIRST_PRIVATE_MSG_ID]);
-                } else if (msg.what >= FIRST_PACKAGE_MSG_ID
-                        && msg.what <= LAST_PACKAGE_MSG_ID) {
-                    Log.v(LOGTAG, HandlerPackageDebugString[msg.what
-                            - FIRST_PACKAGE_MSG_ID]);
-                } else {
-                    Log.v(LOGTAG, Integer.toString(msg.what));
-                }
-            }
-            if (mWebViewCore == null) {
-                // after WebView's destroy() is called, skip handling messages.
-                return;
-            }
-            if (mBlockWebkitViewMessages
-                    && msg.what != WEBCORE_INITIALIZED_MSG_ID) {
-                // Blocking messages from webkit
-                return;
-            }
-            switch (msg.what) {
-                case REMEMBER_PASSWORD: {
-                    mDatabase.setUsernamePassword(
-                            msg.getData().getString("host"),
-                            msg.getData().getString("username"),
-                            msg.getData().getString("password"));
-                    ((Message) msg.obj).sendToTarget();
-                    break;
-                }
-                case NEVER_REMEMBER_PASSWORD: {
-                    mDatabase.setUsernamePassword(
-                            msg.getData().getString("host"), null, null);
-                    ((Message) msg.obj).sendToTarget();
-                    break;
-                }
-                case PREVENT_DEFAULT_TIMEOUT: {
-                    // if timeout happens, cancel it so that it won't block UI
-                    // to continue handling touch events
-                    if ((msg.arg1 == MotionEvent.ACTION_DOWN
-                            && mPreventDefault == PREVENT_DEFAULT_MAYBE_YES)
-                            || (msg.arg1 == MotionEvent.ACTION_MOVE
-                            && mPreventDefault == PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN)) {
-                        cancelWebCoreTouchEvent(
-                                viewToContentX(mLastTouchX + mScrollX),
-                                viewToContentY(mLastTouchY + mScrollY),
-                                true);
-                    }
-                    break;
-                }
-                case SCROLL_SELECT_TEXT: {
-                    if (mAutoScrollX == 0 && mAutoScrollY == 0) {
-                        mSentAutoScrollMessage = false;
-                        break;
-                    }
-                    if (mCurrentScrollingLayerId == 0) {
-                        pinScrollBy(mAutoScrollX, mAutoScrollY, true, 0);
-                    } else {
-                        scrollLayerTo(mScrollingLayerRect.left + mAutoScrollX,
-                                mScrollingLayerRect.top + mAutoScrollY);
-                    }
-                    sendEmptyMessageDelayed(
-                            SCROLL_SELECT_TEXT, SELECT_SCROLL_INTERVAL);
-                    break;
-                }
-                case UPDATE_SELECTION: {
-                    if (mTouchMode == TOUCH_INIT_MODE
-                            || mTouchMode == TOUCH_SHORTPRESS_MODE
-                            || mTouchMode == TOUCH_SHORTPRESS_START_MODE) {
-                        updateSelection();
-                    }
-                    break;
-                }
-                case SWITCH_TO_SHORTPRESS: {
-                    if (mTouchMode == TOUCH_INIT_MODE) {
-                        if (!sDisableNavcache
-                                && mPreventDefault != PREVENT_DEFAULT_YES) {
-                            mTouchMode = TOUCH_SHORTPRESS_START_MODE;
-                            updateSelection();
-                        } else {
-                            // set to TOUCH_SHORTPRESS_MODE so that it won't
-                            // trigger double tap any more
-                            mTouchMode = TOUCH_SHORTPRESS_MODE;
-                        }
-                    } else if (mTouchMode == TOUCH_DOUBLE_TAP_MODE) {
-                        mTouchMode = TOUCH_DONE_MODE;
-                    }
-                    break;
-                }
-                case SWITCH_TO_LONGPRESS: {
-                    if (sDisableNavcache) {
-                        removeTouchHighlight();
-                    }
-                    if (inFullScreenMode() || mDeferTouchProcess) {
-                        TouchEventData ted = new TouchEventData();
-                        ted.mAction = WebViewCore.ACTION_LONGPRESS;
-                        ted.mIds = new int[1];
-                        ted.mIds[0] = 0;
-                        ted.mPoints = new Point[1];
-                        ted.mPoints[0] = new Point(viewToContentX(mLastTouchX + mScrollX),
-                                                   viewToContentY(mLastTouchY + mScrollY));
-                        ted.mPointsInView = new Point[1];
-                        ted.mPointsInView[0] = new Point(mLastTouchX, mLastTouchY);
-                        // metaState for long press is tricky. Should it be the
-                        // state when the press started or when the press was
-                        // released? Or some intermediary key state? For
-                        // simplicity for now, we don't set it.
-                        ted.mMetaState = 0;
-                        ted.mReprocess = mDeferTouchProcess;
-                        ted.mNativeLayer = nativeScrollableLayer(
-                                ted.mPoints[0].x, ted.mPoints[0].y,
-                                ted.mNativeLayerRect, null);
-                        ted.mSequence = mTouchEventQueue.nextTouchSequence();
-                        mTouchEventQueue.preQueueTouchEventData(ted);
-                        mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
-                    } else if (mPreventDefault != PREVENT_DEFAULT_YES) {
-                        mTouchMode = TOUCH_DONE_MODE;
-                        performLongClick();
-                    }
-                    break;
-                }
-                case RELEASE_SINGLE_TAP: {
-                    doShortPress();
-                    break;
-                }
-                case SCROLL_TO_MSG_ID: {
-                    // arg1 = animate, arg2 = onlyIfImeIsShowing
-                    // obj = Point(x, y)
-                    if (msg.arg2 == 1) {
-                        // This scroll is intended to bring the textfield into
-                        // view, but is only necessary if the IME is showing
-                        InputMethodManager imm = InputMethodManager.peekInstance();
-                        if (imm == null || !imm.isAcceptingText()
-                                || (!imm.isActive(WebView.this) && (!inEditingMode()
-                                || !imm.isActive(mWebTextView)))) {
-                            break;
-                        }
-                    }
-                    final Point p = (Point) msg.obj;
-                    if (msg.arg1 == 1) {
-                        spawnContentScrollTo(p.x, p.y);
-                    } else {
-                        setContentScrollTo(p.x, p.y);
-                    }
-                    break;
-                }
-                case UPDATE_ZOOM_RANGE: {
-                    WebViewCore.ViewState viewState = (WebViewCore.ViewState) msg.obj;
-                    // mScrollX contains the new minPrefWidth
-                    mZoomManager.updateZoomRange(viewState, getViewWidth(), viewState.mScrollX);
-                    break;
-                }
-                case UPDATE_ZOOM_DENSITY: {
-                    final float density = (Float) msg.obj;
-                    mZoomManager.updateDefaultZoomDensity(density);
-                    break;
-                }
-                case REPLACE_BASE_CONTENT: {
-                    nativeReplaceBaseContent(msg.arg1);
-                    break;
-                }
-                case NEW_PICTURE_MSG_ID: {
-                    // called for new content
-                    final WebViewCore.DrawData draw = (WebViewCore.DrawData) msg.obj;
-                    setNewPicture(draw, true);
-                    break;
-                }
-                case WEBCORE_INITIALIZED_MSG_ID:
-                    // nativeCreate sets mNativeClass to a non-zero value
-                    String drawableDir = BrowserFrame.getRawResFilename(
-                            BrowserFrame.DRAWABLEDIR, mContext);
-                    WindowManager windowManager =
-                            (WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE);
-                    Display display = windowManager.getDefaultDisplay();
-                    nativeCreate(msg.arg1, drawableDir,
-                            ActivityManager.isHighEndGfx(display));
-                    if (mDelaySetPicture != null) {
-                        setNewPicture(mDelaySetPicture, true);
-                        mDelaySetPicture = null;
-                    }
-                    if (mIsPaused) {
-                        nativeSetPauseDrawing(mNativeClass, true);
-                    }
-                    break;
-                case UPDATE_TEXTFIELD_TEXT_MSG_ID:
-                    // Make sure that the textfield is currently focused
-                    // and representing the same node as the pointer.
-                    if (msg.arg2 == mTextGeneration) {
-                        String text = (String) msg.obj;
-                        if (null == text) {
-                            text = "";
-                        }
-                        if (inEditingMode() &&
-                                mWebTextView.isSameTextField(msg.arg1)) {
-                            mWebTextView.setTextAndKeepSelection(text);
-                        } else if (mInputConnection != null &&
-                                mFieldPointer == msg.arg1) {
-                            mInputConnection.setTextAndKeepSelection(text);
-                        }
-                    }
-                    break;
-                case REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID:
-                    displaySoftKeyboard(true);
-                    // fall through to UPDATE_TEXT_SELECTION_MSG_ID
-                case UPDATE_TEXT_SELECTION_MSG_ID:
-                    updateTextSelectionFromMessage(msg.arg1, msg.arg2,
-                            (WebViewCore.TextSelectionData) msg.obj);
-                    break;
-                case FORM_DID_BLUR:
-                    if (inEditingMode()
-                            && mWebTextView.isSameTextField(msg.arg1)) {
-                        hideSoftKeyboard();
-                    }
-                    break;
-                case RETURN_LABEL:
-                    if (inEditingMode()
-                            && mWebTextView.isSameTextField(msg.arg1)) {
-                        mWebTextView.setHint((String) msg.obj);
-                        InputMethodManager imm
-                                = InputMethodManager.peekInstance();
-                        // The hint is propagated to the IME in
-                        // onCreateInputConnection.  If the IME is already
-                        // active, restart it so that its hint text is updated.
-                        if (imm != null && imm.isActive(mWebTextView)) {
-                            imm.restartInput(mWebTextView);
-                        }
-                    }
-                    break;
-                case UNHANDLED_NAV_KEY:
-                    navHandledKey(msg.arg1, 1, false, 0);
-                    break;
-                case UPDATE_TEXT_ENTRY_MSG_ID:
-                    // this is sent after finishing resize in WebViewCore. Make
-                    // sure the text edit box is still on the  screen.
-                    if (inEditingMode() && nativeCursorIsTextInput()) {
-                        updateWebTextViewPosition();
-                    }
-                    break;
-                case CLEAR_TEXT_ENTRY:
-                    clearTextEntry();
-                    break;
-                case INVAL_RECT_MSG_ID: {
-                    Rect r = (Rect)msg.obj;
-                    if (r == null) {
-                        invalidate();
-                    } else {
-                        // we need to scale r from content into view coords,
-                        // which viewInvalidate() does for us
-                        viewInvalidate(r.left, r.top, r.right, r.bottom);
-                    }
-                    break;
-                }
-                case REQUEST_FORM_DATA:
-                    AutoCompleteAdapter adapter = (AutoCompleteAdapter) msg.obj;
-                    if (mWebTextView.isSameTextField(msg.arg1)) {
-                        mWebTextView.setAdapterCustom(adapter);
-                    }
-                    break;
-
-                case LONG_PRESS_CENTER:
-                    // as this is shared by keydown and trackballdown, reset all
-                    // the states
-                    mGotCenterDown = false;
-                    mTrackballDown = false;
-                    performLongClick();
-                    break;
-
-                case WEBCORE_NEED_TOUCH_EVENTS:
-                    mForwardTouchEvents = (msg.arg1 != 0);
-                    break;
-
-                case PREVENT_TOUCH_ID:
-                    if (inFullScreenMode()) {
-                        break;
-                    }
-                    TouchEventData ted = (TouchEventData) msg.obj;
-
-                    if (mTouchEventQueue.enqueueTouchEvent(ted)) {
-                        // WebCore is responding to us; remove pending timeout.
-                        // It will be re-posted when needed.
-                        removeMessages(PREVENT_DEFAULT_TIMEOUT);
-                    }
-                    break;
-
-                case REQUEST_KEYBOARD:
-                    if (msg.arg1 == 0) {
-                        hideSoftKeyboard();
-                    } else {
-                        displaySoftKeyboard(false);
-                    }
-                    break;
-
-                case DRAG_HELD_MOTIONLESS:
-                    mHeldMotionless = MOTIONLESS_TRUE;
-                    invalidate();
-                    // fall through to keep scrollbars awake
-
-                case AWAKEN_SCROLL_BARS:
-                    if (mTouchMode == TOUCH_DRAG_MODE
-                            && mHeldMotionless == MOTIONLESS_TRUE) {
-                        awakenScrollBars(ViewConfiguration
-                                .getScrollDefaultDelay(), false);
-                        mPrivateHandler.sendMessageDelayed(mPrivateHandler
-                                .obtainMessage(AWAKEN_SCROLL_BARS),
-                                ViewConfiguration.getScrollDefaultDelay());
-                    }
-                    break;
-
-                case DO_MOTION_UP:
-                    doMotionUp(msg.arg1, msg.arg2);
-                    break;
-
-                case SCREEN_ON:
-                    setKeepScreenOn(msg.arg1 == 1);
-                    break;
-
-                case ENTER_FULLSCREEN_VIDEO:
-                    int layerId = msg.arg1;
-
-                    String url = (String) msg.obj;
-                    if (mHTML5VideoViewProxy != null) {
-                        mHTML5VideoViewProxy.enterFullScreenVideo(layerId, url);
-                    }
-                    break;
-
-                case EXIT_FULLSCREEN_VIDEO:
-                    if (mHTML5VideoViewProxy != null) {
-                        mHTML5VideoViewProxy.exitFullScreenVideo();
-                    }
-                    break;
-
-                case SHOW_FULLSCREEN: {
-                    View view = (View) msg.obj;
-                    int orientation = msg.arg1;
-                    int npp = msg.arg2;
-
-                    if (inFullScreenMode()) {
-                        Log.w(LOGTAG, "Should not have another full screen.");
-                        dismissFullScreenMode();
-                    }
-                    mFullScreenHolder = new PluginFullScreenHolder(WebView.this, orientation, npp);
-                    mFullScreenHolder.setContentView(view);
-                    mFullScreenHolder.show();
-                    invalidate();
-
-                    break;
-                }
-                case HIDE_FULLSCREEN:
-                    dismissFullScreenMode();
-                    break;
-
-                case DOM_FOCUS_CHANGED:
-                    if (inEditingMode()) {
-                        nativeClearCursor();
-                        rebuildWebTextView();
-                    }
-                    break;
-
-                case SHOW_RECT_MSG_ID: {
-                    WebViewCore.ShowRectData data = (WebViewCore.ShowRectData) msg.obj;
-                    int x = mScrollX;
-                    int left = contentToViewX(data.mLeft);
-                    int width = contentToViewDimension(data.mWidth);
-                    int maxWidth = contentToViewDimension(data.mContentWidth);
-                    int viewWidth = getViewWidth();
-                    if (width < viewWidth) {
-                        // center align
-                        x += left + width / 2 - mScrollX - viewWidth / 2;
-                    } else {
-                        x += (int) (left + data.mXPercentInDoc * width
-                                - mScrollX - data.mXPercentInView * viewWidth);
-                    }
-                    if (DebugFlags.WEB_VIEW) {
-                        Log.v(LOGTAG, "showRectMsg=(left=" + left + ",width=" +
-                              width + ",maxWidth=" + maxWidth +
-                              ",viewWidth=" + viewWidth + ",x="
-                              + x + ",xPercentInDoc=" + data.mXPercentInDoc +
-                              ",xPercentInView=" + data.mXPercentInView+ ")");
-                    }
-                    // use the passing content width to cap x as the current
-                    // mContentWidth may not be updated yet
-                    x = Math.max(0,
-                            (Math.min(maxWidth, x + viewWidth)) - viewWidth);
-                    int top = contentToViewY(data.mTop);
-                    int height = contentToViewDimension(data.mHeight);
-                    int maxHeight = contentToViewDimension(data.mContentHeight);
-                    int viewHeight = getViewHeight();
-                    int y = (int) (top + data.mYPercentInDoc * height -
-                                   data.mYPercentInView * viewHeight);
-                    if (DebugFlags.WEB_VIEW) {
-                        Log.v(LOGTAG, "showRectMsg=(top=" + top + ",height=" +
-                              height + ",maxHeight=" + maxHeight +
-                              ",viewHeight=" + viewHeight + ",y="
-                              + y + ",yPercentInDoc=" + data.mYPercentInDoc +
-                              ",yPercentInView=" + data.mYPercentInView+ ")");
-                    }
-                    // use the passing content height to cap y as the current
-                    // mContentHeight may not be updated yet
-                    y = Math.max(0,
-                            (Math.min(maxHeight, y + viewHeight) - viewHeight));
-                    // We need to take into account the visible title height
-                    // when scrolling since y is an absolute view position.
-                    y = Math.max(0, y - getVisibleTitleHeightImpl());
-                    scrollTo(x, y);
-                    }
-                    break;
-
-                case CENTER_FIT_RECT:
-                    centerFitRect((Rect)msg.obj);
-                    break;
-
-                case SET_SCROLLBAR_MODES:
-                    mHorizontalScrollBarMode = msg.arg1;
-                    mVerticalScrollBarMode = msg.arg2;
-                    break;
-
-                case SELECTION_STRING_CHANGED:
-                    if (mAccessibilityInjector != null) {
-                        String selectionString = (String) msg.obj;
-                        mAccessibilityInjector.onSelectionStringChange(selectionString);
-                    }
-                    break;
-
-                case HIT_TEST_RESULT:
-                    WebKitHitTest hit = (WebKitHitTest) msg.obj;
-                    mFocusedNode = hit;
-                    setTouchHighlightRects(hit);
-                    setHitTestResult(hit);
-                    break;
-
-                case SAVE_WEBARCHIVE_FINISHED:
-                    SaveWebArchiveMessage saveMessage = (SaveWebArchiveMessage)msg.obj;
-                    if (saveMessage.mCallback != null) {
-                        saveMessage.mCallback.onReceiveValue(saveMessage.mResultFile);
-                    }
-                    break;
-
-                case SET_AUTOFILLABLE:
-                    mAutoFillData = (WebViewCore.AutoFillData) msg.obj;
-                    if (mWebTextView != null) {
-                        mWebTextView.setAutoFillable(mAutoFillData.getQueryId());
-                        rebuildWebTextView();
-                    }
-                    break;
-
-                case AUTOFILL_COMPLETE:
-                    if (mWebTextView != null) {
-                        // Clear the WebTextView adapter when AutoFill finishes
-                        // so that the drop down gets cleared.
-                        mWebTextView.setAdapterCustom(null);
-                    }
-                    break;
-
-                case SELECT_AT:
-                    nativeSelectAt(msg.arg1, msg.arg2);
-                    break;
-
-                case COPY_TO_CLIPBOARD:
-                    copyToClipboard((String) msg.obj);
-                    break;
-
-                case INIT_EDIT_FIELD:
-                    if (mInputConnection != null) {
-                        TextFieldInitData initData = (TextFieldInitData) msg.obj;
-                        mTextGeneration = 0;
-                        mFieldPointer = initData.mFieldPointer;
-                        mInputConnection.initEditorInfo(initData);
-                        mInputConnection.setTextAndKeepSelection(initData.mText);
-                    }
-                    break;
-
-                case REPLACE_TEXT:{
-                    String text = (String)msg.obj;
-                    int start = msg.arg1;
-                    int end = msg.arg2;
-                    int cursorPosition = start + text.length();
-                    replaceTextfieldText(start, end, text,
-                            cursorPosition, cursorPosition);
-                    break;
-                }
-
-                case UPDATE_MATCH_COUNT: {
-                    if (mFindCallback != null) {
-                        mFindCallback.updateMatchCount(msg.arg1, msg.arg2,
-                            (String) msg.obj);
-                    }
-                    break;
-                }
-                case CLEAR_CARET_HANDLE:
-                    selectionDone();
-                    break;
-
-                case KEY_PRESS:
-                    mWebViewCore.sendMessage(EventHub.KEY_PRESS, msg.arg1);
-                    break;
-
-                default:
-                    super.handleMessage(msg);
-                    break;
-            }
-        }
-    }
-
-    private void setHitTestTypeFromUrl(String url) {
-        String substr = null;
-        if (url.startsWith(SCHEME_GEO)) {
-            mInitialHitTestResult.mType = HitTestResult.GEO_TYPE;
-            substr = url.substring(SCHEME_GEO.length());
-        } else if (url.startsWith(SCHEME_TEL)) {
-            mInitialHitTestResult.mType = HitTestResult.PHONE_TYPE;
-            substr = url.substring(SCHEME_TEL.length());
-        } else if (url.startsWith(SCHEME_MAILTO)) {
-            mInitialHitTestResult.mType = HitTestResult.EMAIL_TYPE;
-            substr = url.substring(SCHEME_MAILTO.length());
-        } else {
-            mInitialHitTestResult.mType = HitTestResult.SRC_ANCHOR_TYPE;
-            mInitialHitTestResult.mExtra = url;
-            return;
-        }
-        try {
-            mInitialHitTestResult.mExtra = URLDecoder.decode(substr, "UTF-8");
-        } catch (Throwable e) {
-            Log.w(LOGTAG, "Failed to decode URL! " + substr, e);
-            mInitialHitTestResult.mType = HitTestResult.UNKNOWN_TYPE;
-        }
-    }
-
-    private void setHitTestResult(WebKitHitTest hit) {
-        if (hit == null) {
-            mInitialHitTestResult = null;
-            return;
-        }
-        mInitialHitTestResult = new HitTestResult();
-        if (hit.mLinkUrl != null) {
-            setHitTestTypeFromUrl(hit.mLinkUrl);
-            if (hit.mImageUrl != null
-                    && mInitialHitTestResult.mType == HitTestResult.SRC_ANCHOR_TYPE) {
-                mInitialHitTestResult.mType = HitTestResult.SRC_IMAGE_ANCHOR_TYPE;
-                mInitialHitTestResult.mExtra = hit.mImageUrl;
-            }
-        } else if (hit.mImageUrl != null) {
-            mInitialHitTestResult.mType = HitTestResult.IMAGE_TYPE;
-            mInitialHitTestResult.mExtra = hit.mImageUrl;
-        } else if (hit.mEditable) {
-            mInitialHitTestResult.mType = HitTestResult.EDIT_TEXT_TYPE;
-        } else if (hit.mIntentUrl != null) {
-            setHitTestTypeFromUrl(hit.mIntentUrl);
-        }
-    }
-
-    private boolean shouldDrawHighlightRect() {
-        if (mFocusedNode == null || mInitialHitTestResult == null) {
-            return false;
-        }
-        if (mTouchHighlightRegion.isEmpty()) {
-            return false;
-        }
-        if (mFocusedNode.mHasFocus && !isInTouchMode()) {
-            return !mFocusedNode.mEditable;
-        }
-        if (mInitialHitTestResult.mType == HitTestResult.UNKNOWN_TYPE) {
-            return false;
-        }
-        long delay = System.currentTimeMillis() - mTouchHighlightRequested;
-        if (delay < ViewConfiguration.getTapTimeout()) {
-            Rect r = mTouchHighlightRegion.getBounds();
-            postInvalidateDelayed(delay, r.left, r.top, r.right, r.bottom);
-            return false;
-        }
-        return true;
-    }
-
-
-    private FocusTransitionDrawable mFocusTransition = null;
-    static class FocusTransitionDrawable extends Drawable {
-        Region mPreviousRegion;
-        Region mNewRegion;
-        float mProgress = 0;
-        WebView mWebView;
-        Paint mPaint;
-        int mMaxAlpha;
-        Point mTranslate;
-
-        public FocusTransitionDrawable(WebView view) {
-            mWebView = view;
-            mPaint = new Paint(mWebView.mTouchHightlightPaint);
-            mMaxAlpha = mPaint.getAlpha();
-        }
-
-        @Override
-        public void setColorFilter(ColorFilter cf) {
-        }
-
-        @Override
-        public void setAlpha(int alpha) {
-        }
-
-        @Override
-        public int getOpacity() {
-            return 0;
-        }
-
-        public void setProgress(float p) {
-            mProgress = p;
-            if (mWebView.mFocusTransition == this) {
-                if (mProgress == 1f)
-                    mWebView.mFocusTransition = null;
-                mWebView.invalidate();
-            }
-        }
-
-        public float getProgress() {
-            return mProgress;
-        }
-
-        @Override
-        public void draw(Canvas canvas) {
-            if (mTranslate == null) {
-                Rect bounds = mPreviousRegion.getBounds();
-                Point from = new Point(bounds.centerX(), bounds.centerY());
-                mNewRegion.getBounds(bounds);
-                Point to = new Point(bounds.centerX(), bounds.centerY());
-                mTranslate = new Point(from.x - to.x, from.y - to.y);
-            }
-            int alpha = (int) (mProgress * mMaxAlpha);
-            RegionIterator iter = new RegionIterator(mPreviousRegion);
-            Rect r = new Rect();
-            mPaint.setAlpha(mMaxAlpha - alpha);
-            float tx = mTranslate.x * mProgress;
-            float ty = mTranslate.y * mProgress;
-            int save = canvas.save(Canvas.MATRIX_SAVE_FLAG);
-            canvas.translate(-tx, -ty);
-            while (iter.next(r)) {
-                canvas.drawRect(r, mPaint);
-            }
-            canvas.restoreToCount(save);
-            iter = new RegionIterator(mNewRegion);
-            r = new Rect();
-            mPaint.setAlpha(alpha);
-            save = canvas.save(Canvas.MATRIX_SAVE_FLAG);
-            tx = mTranslate.x - tx;
-            ty = mTranslate.y - ty;
-            canvas.translate(tx, ty);
-            while (iter.next(r)) {
-                canvas.drawRect(r, mPaint);
-            }
-            canvas.restoreToCount(save);
-        }
-    };
-
-    private boolean shouldAnimateTo(WebKitHitTest hit) {
-        // TODO: Don't be annoying or throw out the animation entirely
-        return false;
-    }
-
-    private void setTouchHighlightRects(WebKitHitTest hit) {
-        FocusTransitionDrawable transition = null;
-        if (shouldAnimateTo(hit)) {
-            transition = new FocusTransitionDrawable(this);
-        }
-        Rect[] rects = hit != null ? hit.mTouchRects : null;
-        if (!mTouchHighlightRegion.isEmpty()) {
-            invalidate(mTouchHighlightRegion.getBounds());
-            if (transition != null) {
-                transition.mPreviousRegion = new Region(mTouchHighlightRegion);
-            }
-            mTouchHighlightRegion.setEmpty();
-        }
-        if (rects != null) {
-            mTouchHightlightPaint.setColor(hit.mTapHighlightColor);
-            for (Rect rect : rects) {
-                Rect viewRect = contentToViewRect(rect);
-                // some sites, like stories in nytimes.com, set
-                // mouse event handler in the top div. It is not
-                // user friendly to highlight the div if it covers
-                // more than half of the screen.
-                if (viewRect.width() < getWidth() >> 1
-                        || viewRect.height() < getHeight() >> 1) {
-                    mTouchHighlightRegion.union(viewRect);
-                } else {
-                    Log.w(LOGTAG, "Skip the huge selection rect:"
-                            + viewRect);
-                }
-            }
-            invalidate(mTouchHighlightRegion.getBounds());
-            if (transition != null && transition.mPreviousRegion != null) {
-                transition.mNewRegion = new Region(mTouchHighlightRegion);
-                mFocusTransition = transition;
-                ObjectAnimator animator = ObjectAnimator.ofFloat(
-                        mFocusTransition, "progress", 1f);
-                animator.start();
-            }
-        }
-    }
-
-    /** @hide Called by JNI when pages are swapped (only occurs with hardware
-     * acceleration) */
-    protected void pageSwapCallback(boolean notifyAnimationStarted) {
-        mWebViewCore.resumeWebKitDraw();
-        if (inEditingMode()) {
-            didUpdateWebTextViewDimensions(ANYWHERE);
-        }
-        if (notifyAnimationStarted) {
-            mWebViewCore.sendMessage(EventHub.NOTIFY_ANIMATION_STARTED);
-        }
-    }
-
-    void setNewPicture(final WebViewCore.DrawData draw, boolean updateBaseLayer) {
-        if (mNativeClass == 0) {
-            if (mDelaySetPicture != null) {
-                throw new IllegalStateException("Tried to setNewPicture with"
-                        + " a delay picture already set! (memory leak)");
-            }
-            // Not initialized yet, delay set
-            mDelaySetPicture = draw;
-            return;
-        }
-        WebViewCore.ViewState viewState = draw.mViewState;
-        boolean isPictureAfterFirstLayout = viewState != null;
-
-        if (updateBaseLayer) {
-            setBaseLayer(draw.mBaseLayer, draw.mInvalRegion,
-                    getSettings().getShowVisualIndicator(),
-                    isPictureAfterFirstLayout);
-        }
-        final Point viewSize = draw.mViewSize;
-        // We update the layout (i.e. request a layout from the
-        // view system) if the last view size that we sent to
-        // WebCore matches the view size of the picture we just
-        // received in the fixed dimension.
-        final boolean updateLayout = viewSize.x == mLastWidthSent
-                && viewSize.y == mLastHeightSent;
-        // Don't send scroll event for picture coming from webkit,
-        // since the new picture may cause a scroll event to override
-        // the saved history scroll position.
-        mSendScrollEvent = false;
-        recordNewContentSize(draw.mContentSize.x,
-                draw.mContentSize.y, updateLayout);
-        if (isPictureAfterFirstLayout) {
-            // Reset the last sent data here since dealing with new page.
-            mLastWidthSent = 0;
-            mZoomManager.onFirstLayout(draw);
-            int scrollX = viewState.mShouldStartScrolledRight
-                    ? getContentWidth() : viewState.mScrollX;
-            int scrollY = viewState.mScrollY;
-            setContentScrollTo(scrollX, scrollY);
-            if (!mDrawHistory) {
-                // As we are on a new page, remove the WebTextView. This
-                // is necessary for page loads driven by webkit, and in
-                // particular when the user was on a password field, so
-                // the WebTextView was visible.
-                clearTextEntry();
-            }
-        }
-        mSendScrollEvent = true;
-
-        if (DebugFlags.WEB_VIEW) {
-            Rect b = draw.mInvalRegion.getBounds();
-            Log.v(LOGTAG, "NEW_PICTURE_MSG_ID {" +
-                    b.left+","+b.top+","+b.right+","+b.bottom+"}");
-        }
-        invalidateContentRect(draw.mInvalRegion.getBounds());
-
-        if (mPictureListener != null) {
-            mPictureListener.onNewPicture(WebView.this, capturePicture());
-        }
-
-        // update the zoom information based on the new picture
-        mZoomManager.onNewPicture(draw);
-
-        if (draw.mFocusSizeChanged && inEditingMode()) {
-            mFocusSizeChanged = true;
-        }
-        if (isPictureAfterFirstLayout) {
-            mViewManager.postReadyToDrawAll();
-        }
-    }
-
-    /**
-     * Used when receiving messages for REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID
-     * and UPDATE_TEXT_SELECTION_MSG_ID.  Update the selection of WebTextView.
-     */
-    private void updateTextSelectionFromMessage(int nodePointer,
-            int textGeneration, WebViewCore.TextSelectionData data) {
-        if (textGeneration == mTextGeneration) {
-            if (inEditingMode()
-                    && mWebTextView.isSameTextField(nodePointer)) {
-                mWebTextView.setSelectionFromWebKit(data.mStart, data.mEnd);
-            } else if (mInputConnection != null && mFieldPointer == nodePointer) {
-                mInputConnection.setSelection(data.mStart, data.mEnd);
-            }
-        }
-        nativeSetTextSelection(mNativeClass, data.mSelectTextPtr);
-
-        if (data.mSelectTextPtr != 0 &&
-                (data.mStart != data.mEnd ||
-                (mFieldPointer == nodePointer && mFieldPointer != 0))) {
-            mIsCaretSelection = (data.mStart == data.mEnd);
-            if (!mSelectingText) {
-                setupWebkitSelect();
-            } else if (!mSelectionStarted) {
-                syncSelectionCursors();
-            }
-            if (mIsCaretSelection) {
-                resetCaretTimer();
-            }
-        } else {
-            selectionDone();
-        }
-        invalidate();
-    }
-
-    // Class used to use a dropdown for a <select> element
-    private class InvokeListBox implements Runnable {
-        // Whether the listbox allows multiple selection.
-        private boolean     mMultiple;
-        // Passed in to a list with multiple selection to tell
-        // which items are selected.
-        private int[]       mSelectedArray;
-        // Passed in to a list with single selection to tell
-        // where the initial selection is.
-        private int         mSelection;
-
-        private Container[] mContainers;
-
-        // Need these to provide stable ids to my ArrayAdapter,
-        // which normally does not have stable ids. (Bug 1250098)
-        private class Container extends Object {
-            /**
-             * Possible values for mEnabled.  Keep in sync with OptionStatus in
-             * WebViewCore.cpp
-             */
-            final static int OPTGROUP = -1;
-            final static int OPTION_DISABLED = 0;
-            final static int OPTION_ENABLED = 1;
-
-            String  mString;
-            int     mEnabled;
-            int     mId;
-
-            @Override
-            public String toString() {
-                return mString;
-            }
-        }
-
-        /**
-         *  Subclass ArrayAdapter so we can disable OptionGroupLabels,
-         *  and allow filtering.
-         */
-        private class MyArrayListAdapter extends ArrayAdapter<Container> {
-            public MyArrayListAdapter() {
-                super(mContext,
-                        mMultiple ? com.android.internal.R.layout.select_dialog_multichoice :
-                        com.android.internal.R.layout.webview_select_singlechoice,
-                        mContainers);
-            }
-
-            @Override
-            public View getView(int position, View convertView,
-                    ViewGroup parent) {
-                // Always pass in null so that we will get a new CheckedTextView
-                // Otherwise, an item which was previously used as an <optgroup>
-                // element (i.e. has no check), could get used as an <option>
-                // element, which needs a checkbox/radio, but it would not have
-                // one.
-                convertView = super.getView(position, null, parent);
-                Container c = item(position);
-                if (c != null && Container.OPTION_ENABLED != c.mEnabled) {
-                    // ListView does not draw dividers between disabled and
-                    // enabled elements.  Use a LinearLayout to provide dividers
-                    LinearLayout layout = new LinearLayout(mContext);
-                    layout.setOrientation(LinearLayout.VERTICAL);
-                    if (position > 0) {
-                        View dividerTop = new View(mContext);
-                        dividerTop.setBackgroundResource(
-                                android.R.drawable.divider_horizontal_bright);
-                        layout.addView(dividerTop);
-                    }
-
-                    if (Container.OPTGROUP == c.mEnabled) {
-                        // Currently select_dialog_multichoice uses CheckedTextViews.
-                        // If that changes, the class cast will no longer be valid.
-                        if (mMultiple) {
-                            Assert.assertTrue(convertView instanceof CheckedTextView);
-                            ((CheckedTextView) convertView).setCheckMarkDrawable(null);
-                        }
-                    } else {
-                        // c.mEnabled == Container.OPTION_DISABLED
-                        // Draw the disabled element in a disabled state.
-                        convertView.setEnabled(false);
-                    }
-
-                    layout.addView(convertView);
-                    if (position < getCount() - 1) {
-                        View dividerBottom = new View(mContext);
-                        dividerBottom.setBackgroundResource(
-                                android.R.drawable.divider_horizontal_bright);
-                        layout.addView(dividerBottom);
-                    }
-                    return layout;
-                }
-                return convertView;
-            }
-
-            @Override
-            public boolean hasStableIds() {
-                // AdapterView's onChanged method uses this to determine whether
-                // to restore the old state.  Return false so that the old (out
-                // of date) state does not replace the new, valid state.
-                return false;
-            }
-
-            private Container item(int position) {
-                if (position < 0 || position >= getCount()) {
-                    return null;
-                }
-                return getItem(position);
-            }
-
-            @Override
-            public long getItemId(int position) {
-                Container item = item(position);
-                if (item == null) {
-                    return -1;
-                }
-                return item.mId;
-            }
-
-            @Override
-            public boolean areAllItemsEnabled() {
-                return false;
-            }
-
-            @Override
-            public boolean isEnabled(int position) {
-                Container item = item(position);
-                if (item == null) {
-                    return false;
-                }
-                return Container.OPTION_ENABLED == item.mEnabled;
-            }
-        }
-
-        private InvokeListBox(String[] array, int[] enabled, int[] selected) {
-            mMultiple = true;
-            mSelectedArray = selected;
-
-            int length = array.length;
-            mContainers = new Container[length];
-            for (int i = 0; i < length; i++) {
-                mContainers[i] = new Container();
-                mContainers[i].mString = array[i];
-                mContainers[i].mEnabled = enabled[i];
-                mContainers[i].mId = i;
-            }
-        }
-
-        private InvokeListBox(String[] array, int[] enabled, int selection) {
-            mSelection = selection;
-            mMultiple = false;
-
-            int length = array.length;
-            mContainers = new Container[length];
-            for (int i = 0; i < length; i++) {
-                mContainers[i] = new Container();
-                mContainers[i].mString = array[i];
-                mContainers[i].mEnabled = enabled[i];
-                mContainers[i].mId = i;
-            }
-        }
-
-        /*
-         * Whenever the data set changes due to filtering, this class ensures
-         * that the checked item remains checked.
-         */
-        private class SingleDataSetObserver extends DataSetObserver {
-            private long        mCheckedId;
-            private ListView    mListView;
-            private Adapter     mAdapter;
-
-            /*
-             * Create a new observer.
-             * @param id The ID of the item to keep checked.
-             * @param l ListView for getting and clearing the checked states
-             * @param a Adapter for getting the IDs
-             */
-            public SingleDataSetObserver(long id, ListView l, Adapter a) {
-                mCheckedId = id;
-                mListView = l;
-                mAdapter = a;
-            }
-
-            @Override
-            public void onChanged() {
-                // The filter may have changed which item is checked.  Find the
-                // item that the ListView thinks is checked.
-                int position = mListView.getCheckedItemPosition();
-                long id = mAdapter.getItemId(position);
-                if (mCheckedId != id) {
-                    // Clear the ListView's idea of the checked item, since
-                    // it is incorrect
-                    mListView.clearChoices();
-                    // Search for mCheckedId.  If it is in the filtered list,
-                    // mark it as checked
-                    int count = mAdapter.getCount();
-                    for (int i = 0; i < count; i++) {
-                        if (mAdapter.getItemId(i) == mCheckedId) {
-                            mListView.setItemChecked(i, true);
-                            break;
-                        }
-                    }
-                }
-            }
-        }
-
-        @Override
-        public void run() {
-            final ListView listView = (ListView) LayoutInflater.from(mContext)
-                    .inflate(com.android.internal.R.layout.select_dialog, null);
-            final MyArrayListAdapter adapter = new MyArrayListAdapter();
-            AlertDialog.Builder b = new AlertDialog.Builder(mContext)
-                    .setView(listView).setCancelable(true)
-                    .setInverseBackgroundForced(true);
-
-            if (mMultiple) {
-                b.setPositiveButton(android.R.string.ok, new DialogInterface.OnClickListener() {
-                    @Override
-                    public void onClick(DialogInterface dialog, int which) {
-                        mWebViewCore.sendMessage(
-                                EventHub.LISTBOX_CHOICES,
-                                adapter.getCount(), 0,
-                                listView.getCheckedItemPositions());
-                    }});
-                b.setNegativeButton(android.R.string.cancel,
-                        new DialogInterface.OnClickListener() {
-                    @Override
-                    public void onClick(DialogInterface dialog, int which) {
-                        mWebViewCore.sendMessage(
-                                EventHub.SINGLE_LISTBOX_CHOICE, -2, 0);
-                }});
-            }
-            mListBoxDialog = b.create();
-            listView.setAdapter(adapter);
-            listView.setFocusableInTouchMode(true);
-            // There is a bug (1250103) where the checks in a ListView with
-            // multiple items selected are associated with the positions, not
-            // the ids, so the items do not properly retain their checks when
-            // filtered.  Do not allow filtering on multiple lists until
-            // that bug is fixed.
-
-            listView.setTextFilterEnabled(!mMultiple);
-            if (mMultiple) {
-                listView.setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
-                int length = mSelectedArray.length;
-                for (int i = 0; i < length; i++) {
-                    listView.setItemChecked(mSelectedArray[i], true);
-                }
-            } else {
-                listView.setOnItemClickListener(new OnItemClickListener() {
-                    @Override
-                    public void onItemClick(AdapterView<?> parent, View v,
-                            int position, long id) {
-                        // Rather than sending the message right away, send it
-                        // after the page regains focus.
-                        mListBoxMessage = Message.obtain(null,
-                                EventHub.SINGLE_LISTBOX_CHOICE, (int) id, 0);
-                        mListBoxDialog.dismiss();
-                        mListBoxDialog = null;
-                    }
-                });
-                if (mSelection != -1) {
-                    listView.setSelection(mSelection);
-                    listView.setChoiceMode(ListView.CHOICE_MODE_SINGLE);
-                    listView.setItemChecked(mSelection, true);
-                    DataSetObserver observer = new SingleDataSetObserver(
-                            adapter.getItemId(mSelection), listView, adapter);
-                    adapter.registerDataSetObserver(observer);
-                }
-            }
-            mListBoxDialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
-                @Override
-                public void onCancel(DialogInterface dialog) {
-                    mWebViewCore.sendMessage(
-                                EventHub.SINGLE_LISTBOX_CHOICE, -2, 0);
-                    mListBoxDialog = null;
-                }
-            });
-            mListBoxDialog.show();
-        }
-    }
-
-    private Message mListBoxMessage;
-
-    /*
-     * Request a dropdown menu for a listbox with multiple selection.
-     *
-     * @param array Labels for the listbox.
-     * @param enabledArray  State for each element in the list.  See static
-     *      integers in Container class.
-     * @param selectedArray Which positions are initally selected.
-     */
-    void requestListBox(String[] array, int[] enabledArray, int[]
-            selectedArray) {
-        mPrivateHandler.post(
-                new InvokeListBox(array, enabledArray, selectedArray));
-    }
-
-    /*
-     * Request a dropdown menu for a listbox with single selection or a single
-     * <select> element.
-     *
-     * @param array Labels for the listbox.
-     * @param enabledArray  State for each element in the list.  See static
-     *      integers in Container class.
-     * @param selection Which position is initally selected.
-     */
-    void requestListBox(String[] array, int[] enabledArray, int selection) {
-        mPrivateHandler.post(
-                new InvokeListBox(array, enabledArray, selection));
-    }
-
-    // called by JNI
-    private void sendMoveFocus(int frame, int node) {
-        mWebViewCore.sendMessage(EventHub.SET_MOVE_FOCUS,
-                new WebViewCore.CursorData(frame, node, 0, 0));
-    }
-
-    // called by JNI
-    private void sendMoveMouse(int frame, int node, int x, int y) {
-        mWebViewCore.sendMessage(EventHub.SET_MOVE_MOUSE,
-                new WebViewCore.CursorData(frame, node, x, y));
-    }
-
-    /*
-     * Send a mouse move event to the webcore thread.
-     *
-     * @param removeFocus Pass true to remove the WebTextView, if present.
-     * @param stopPaintingCaret Stop drawing the blinking caret if true.
-     * called by JNI
-     */
-    @SuppressWarnings("unused")
-    private void sendMoveMouseIfLatest(boolean removeFocus, boolean stopPaintingCaret) {
-        if (removeFocus) {
-            clearTextEntry();
-        }
-        mWebViewCore.sendMessage(EventHub.SET_MOVE_MOUSE_IF_LATEST,
-                stopPaintingCaret ? 1 : 0, 0,
-                cursorData());
-    }
-
-    /**
-     * Called by JNI to send a message to the webcore thread that the user
-     * touched the webpage.
-     * @param touchGeneration Generation number of the touch, to ignore touches
-     *      after a new one has been generated.
-     * @param frame Pointer to the frame holding the node that was touched.
-     * @param node Pointer to the node touched.
-     * @param x x-position of the touch.
-     * @param y y-position of the touch.
-     */
-    private void sendMotionUp(int touchGeneration,
-            int frame, int node, int x, int y) {
-        WebViewCore.TouchUpData touchUpData = new WebViewCore.TouchUpData();
-        touchUpData.mMoveGeneration = touchGeneration;
-        touchUpData.mFrame = frame;
-        touchUpData.mNode = node;
-        touchUpData.mX = x;
-        touchUpData.mY = y;
-        touchUpData.mNativeLayer = nativeScrollableLayer(
-                x, y, touchUpData.mNativeLayerRect, null);
-        mWebViewCore.sendMessage(EventHub.TOUCH_UP, touchUpData);
-    }
-
-
-    private int getScaledMaxXScroll() {
-        int width;
-        if (mHeightCanMeasure == false) {
-            width = getViewWidth() / 4;
-        } else {
-            Rect visRect = new Rect();
-            calcOurVisibleRect(visRect);
-            width = visRect.width() / 2;
-        }
-        // FIXME the divisor should be retrieved from somewhere
-        return viewToContentX(width);
-    }
-
-    private int getScaledMaxYScroll() {
-        int height;
-        if (mHeightCanMeasure == false) {
-            height = getViewHeight() / 4;
-        } else {
-            Rect visRect = new Rect();
-            calcOurVisibleRect(visRect);
-            height = visRect.height() / 2;
-        }
-        // FIXME the divisor should be retrieved from somewhere
-        // the closest thing today is hard-coded into ScrollView.java
-        // (from ScrollView.java, line 363)   int maxJump = height/2;
-        return Math.round(height * mZoomManager.getInvScale());
-    }
-
-    /**
-     * Called by JNI to invalidate view
-     */
-    private void viewInvalidate() {
-        invalidate();
-    }
-
-    /**
-     * Pass the key directly to the page.  This assumes that
-     * nativePageShouldHandleShiftAndArrows() returned true.
-     */
-    private void letPageHandleNavKey(int keyCode, long time, boolean down, int metaState) {
-        int keyEventAction;
-        int eventHubAction;
-        if (down) {
-            keyEventAction = KeyEvent.ACTION_DOWN;
-            eventHubAction = EventHub.KEY_DOWN;
-            playSoundEffect(keyCodeToSoundsEffect(keyCode));
-        } else {
-            keyEventAction = KeyEvent.ACTION_UP;
-            eventHubAction = EventHub.KEY_UP;
-        }
-
-        KeyEvent event = new KeyEvent(time, time, keyEventAction, keyCode,
-                1, (metaState & KeyEvent.META_SHIFT_ON)
-                | (metaState & KeyEvent.META_ALT_ON)
-                | (metaState & KeyEvent.META_SYM_ON)
-                , KeyCharacterMap.VIRTUAL_KEYBOARD, 0, 0);
-        mWebViewCore.sendMessage(eventHubAction, event);
-    }
-
-    // return true if the key was handled
-    private boolean navHandledKey(int keyCode, int count, boolean noScroll,
-            long time) {
-        if (mNativeClass == 0) {
-            return false;
-        }
-        mInitialHitTestResult = null;
-        mLastCursorTime = time;
-        mLastCursorBounds = cursorRingBounds();
-        boolean keyHandled
-                = nativeMoveCursor(keyCode, count, noScroll) == false;
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "navHandledKey mLastCursorBounds=" + mLastCursorBounds
-                    + " mLastCursorTime=" + mLastCursorTime
-                    + " handled=" + keyHandled);
-        }
-        if (keyHandled == false) {
-            return keyHandled;
-        }
-        Rect contentCursorRingBounds = cursorRingBounds();
-        if (contentCursorRingBounds.isEmpty()) return keyHandled;
-        Rect viewCursorRingBounds = contentToViewRect(contentCursorRingBounds);
-        // set last touch so that context menu related functions will work
-        mLastTouchX = (viewCursorRingBounds.left + viewCursorRingBounds.right) / 2;
-        mLastTouchY = (viewCursorRingBounds.top + viewCursorRingBounds.bottom) / 2;
-        if (mHeightCanMeasure == false) {
-            return keyHandled;
-        }
-        Rect visRect = new Rect();
-        calcOurVisibleRect(visRect);
-        Rect outset = new Rect(visRect);
-        int maxXScroll = visRect.width() / 2;
-        int maxYScroll = visRect.height() / 2;
-        outset.inset(-maxXScroll, -maxYScroll);
-        if (Rect.intersects(outset, viewCursorRingBounds) == false) {
-            return keyHandled;
-        }
-        // FIXME: Necessary because ScrollView/ListView do not scroll left/right
-        int maxH = Math.min(viewCursorRingBounds.right - visRect.right,
-                maxXScroll);
-        if (maxH > 0) {
-            pinScrollBy(maxH, 0, true, 0);
-        } else {
-            maxH = Math.max(viewCursorRingBounds.left - visRect.left,
-                    -maxXScroll);
-            if (maxH < 0) {
-                pinScrollBy(maxH, 0, true, 0);
-            }
-        }
-        if (mLastCursorBounds.isEmpty()) return keyHandled;
-        if (mLastCursorBounds.equals(contentCursorRingBounds)) {
-            return keyHandled;
-        }
-        if (DebugFlags.WEB_VIEW) {
-            Log.v(LOGTAG, "navHandledKey contentCursorRingBounds="
-                    + contentCursorRingBounds);
-        }
-        requestRectangleOnScreen(viewCursorRingBounds);
-        return keyHandled;
-    }
-
-    /**
-     * @return Whether accessibility script has been injected.
-     */
-    private boolean accessibilityScriptInjected() {
-        // TODO: Maybe the injected script should announce its presence in
-        // the page meta-tag so the nativePageShouldHandleShiftAndArrows
-        // will check that as one of the conditions it looks for
-        return mAccessibilityScriptInjected;
-    }
-
-    /**
-     * Set the background color. It's white by default. Pass
-     * zero to make the view transparent.
-     * @param color   the ARGB color described by Color.java
-     */
-    @Override
-    public void setBackgroundColor(int color) {
-        mBackgroundColor = color;
-        mWebViewCore.sendMessage(EventHub.SET_BACKGROUND_COLOR, color);
+        return mProvider.zoomOut();
     }
 
     /**
@@ -10239,70 +1534,165 @@
     @Deprecated
     public void debugDump() {
         checkThread();
-        nativeDebugDump();
-        mWebViewCore.sendMessage(EventHub.DUMP_NAVTREE);
+        mProvider.debugDump();
     }
 
+    //-------------------------------------------------------------------------
+    // Interface for WebView providers
+    //-------------------------------------------------------------------------
+
     /**
-     * Draw the HTML page into the specified canvas. This call ignores any
-     * view-specific zoom, scroll offset, or other changes. It does not draw
-     * any view-specific chrome, such as progress or URL bars.
+     * Used by providers to obtain the underlying implementation, e.g. when the appliction
+     * responds to WebViewClient.onCreateWindow() request.
      *
-     * @hide only needs to be accessible to Browser and testing
+     * @hide WebViewProvider is not public API.
      */
-    public void drawPage(Canvas canvas) {
-        calcOurContentVisibleRectF(mVisibleContentRect);
-        nativeDraw(canvas, mVisibleContentRect, 0, 0, false);
+    public WebViewProvider getWebViewProvider() {
+        return mProvider;
     }
 
     /**
-     * Enable the communication b/t the webView and VideoViewProxy
-     *
-     * @hide only used by the Browser
+     * Callback interface, allows the provider implementation to access non-public methods
+     * and fields, and make super-class calls in this WebView instance.
+     * @hide Only for use by WebViewProvider implementations
      */
-    public void setHTML5VideoViewProxy(HTML5VideoViewProxy proxy) {
-        mHTML5VideoViewProxy = proxy;
+    public class PrivateAccess {
+        // ---- Access to super-class methods ----
+        public int super_getScrollBarStyle() {
+            return WebView.super.getScrollBarStyle();
+        }
+
+        public void super_scrollTo(int scrollX, int scrollY) {
+            WebView.super.scrollTo(scrollX, scrollY);
+        }
+
+        public void super_computeScroll() {
+            WebView.super.computeScroll();
+        }
+
+        public boolean super_performLongClick() {
+            return WebView.super.performLongClick();
+        }
+
+        public boolean super_setFrame(int left, int top, int right, int bottom) {
+            return WebView.super.setFrame(left, top, right, bottom);
+        }
+
+        public boolean super_dispatchKeyEvent(KeyEvent event) {
+            return WebView.super.dispatchKeyEvent(event);
+        }
+
+        public boolean super_onGenericMotionEvent(MotionEvent event) {
+            return WebView.super.onGenericMotionEvent(event);
+        }
+
+        public boolean super_requestFocus(int direction, Rect previouslyFocusedRect) {
+            return WebView.super.requestFocus(direction, previouslyFocusedRect);
+        }
+
+        public void super_setLayoutParams(ViewGroup.LayoutParams params) {
+            WebView.super.setLayoutParams(params);
+        }
+
+        // ---- Access to non-public methods ----
+        public void overScrollBy(int deltaX, int deltaY,
+                int scrollX, int scrollY,
+                int scrollRangeX, int scrollRangeY,
+                int maxOverScrollX, int maxOverScrollY,
+                boolean isTouchEvent) {
+            WebView.this.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX, scrollRangeY,
+                    maxOverScrollX, maxOverScrollY, isTouchEvent);
+        }
+
+        public void awakenScrollBars(int duration) {
+            WebView.this.awakenScrollBars(duration);
+        }
+
+        public void awakenScrollBars(int duration, boolean invalidate) {
+            WebView.this.awakenScrollBars(duration, invalidate);
+        }
+
+        public float getVerticalScrollFactor() {
+            return WebView.this.getVerticalScrollFactor();
+        }
+
+        public float getHorizontalScrollFactor() {
+            return WebView.this.getHorizontalScrollFactor();
+        }
+
+        public void setMeasuredDimension(int measuredWidth, int measuredHeight) {
+            WebView.this.setMeasuredDimension(measuredWidth, measuredHeight);
+        }
+
+        public void onScrollChanged(int l, int t, int oldl, int oldt) {
+            WebView.this.onScrollChanged(l, t, oldl, oldt);
+        }
+
+        public int getHorizontalScrollbarHeight() {
+            return WebView.this.getHorizontalScrollbarHeight();
+        }
+
+        // ---- Access to (non-public) fields ----
+        /** Raw setter for the scroll X value, without invoking onScrollChanged handlers etc. */
+        public void setScrollXRaw(int scrollX) {
+            WebView.this.mScrollX = scrollX;
+        }
+
+        /** Raw setter for the scroll Y value, without invoking onScrollChanged handlers etc. */
+        public void setScrollYRaw(int scrollY) {
+            WebView.this.mScrollY = scrollY;
+        }
+
     }
 
-    /**
-     * Set the time to wait between passing touches to WebCore. See also the
-     * TOUCH_SENT_INTERVAL member for further discussion.
-     *
-     * @hide This is only used by the DRT test application.
-     */
-    public void setTouchInterval(int interval) {
-        mCurrentTouchInterval = interval;
+    //-------------------------------------------------------------------------
+    // Private internal stuff
+    //-------------------------------------------------------------------------
+
+    // Cache the factory both for efficiency, and ensure any one process gets all webviews from the
+    // same provider.
+    private static WebViewFactoryProvider sProviderFactory;
+
+    private WebViewProvider mProvider;
+
+    private void ensureProviderCreated() {
+        checkThread();
+        if (mProvider == null) {
+            if (DEBUG) Log.v(LOGTAG, "instantiating webview provider instance");
+            // As this can get called during the base class constructor chain, pass the minimum
+            // number of dependencies here; the rest are deferred to init().
+            mProvider = getFactory().createWebView(this, new PrivateAccess());
+        }
     }
 
-    /**
-     * Copy text into the clipboard. This is called indirectly from
-     * WebViewCore.
-     * @param text The text to put into the clipboard.
-     */
-    private void copyToClipboard(String text) {
-        ClipboardManager cm = (ClipboardManager)getContext()
-                .getSystemService(Context.CLIPBOARD_SERVICE);
-        ClipData clip = ClipData.newPlainText(getTitle(), text);
-        cm.setPrimaryClip(clip);
+    private static synchronized WebViewFactoryProvider getFactory() {
+        // For now the main purpose of this function (and the factory abstration) is to keep
+        // us honest and minimize usage of WebViewClassic internals when binding the proxy.
+        checkThread();
+        if (sProviderFactory != null) return sProviderFactory;
+
+        sProviderFactory = getFactoryByName(DEFAULT_WEB_VIEW_FACTORY);
+        if (sProviderFactory == null) {
+            if (DEBUG) Log.v (LOGTAG, "Falling back to explicit linkage");
+            sProviderFactory = new WebViewClassic.Factory();
+        }
+        return sProviderFactory;
     }
 
-    /**
-     *  Update our cache with updatedText.
-     *  @param updatedText  The new text to put in our cache.
-     *  @hide
-     */
-    protected void updateCachedTextfield(String updatedText) {
-        // Also place our generation number so that when we look at the cache
-        // we recognize that it is up to date.
-        nativeUpdateCachedTextfield(updatedText, mTextGeneration);
-    }
-
-    /*package*/ void autoFillForm(int autoFillQueryId) {
-        mWebViewCore.sendMessage(EventHub.AUTOFILL_FORM, autoFillQueryId, /* unused */0);
-    }
-
-    /* package */ ViewManager getViewManager() {
-        return mViewManager;
+    private static WebViewFactoryProvider getFactoryByName(String providerName) {
+        try {
+            if (DEBUG) Log.v(LOGTAG, "attempt to load class " + providerName);
+            Class<?> c = Class.forName(providerName);
+            if (DEBUG) Log.v(LOGTAG, "instantiating factory");
+            return (WebViewFactoryProvider) c.newInstance();
+        } catch (ClassNotFoundException e) {
+            Log.e(LOGTAG, "error loading " + providerName, e);
+        } catch (IllegalAccessException e) {
+            Log.e(LOGTAG, "error loading " + providerName, e);
+        } catch (InstantiationException e) {
+            Log.e(LOGTAG, "error loading " + providerName, e);
+        }
+        return null;
     }
 
     private static void checkThread() {
@@ -10317,234 +1707,252 @@
         }
     }
 
-    /** @hide send content invalidate */
-    protected void contentInvalidateAll() {
-        if (mWebViewCore != null && !mBlockWebkitViewMessages) {
-            mWebViewCore.sendMessage(EventHub.CONTENT_INVALIDATE_ALL);
-        }
+    //-------------------------------------------------------------------------
+    // Override View methods
+    //-------------------------------------------------------------------------
+
+    // TODO: Add a test that enumerates all methods in ViewDelegte & ScrollDelegate, and ensures
+    // there's a corresponding override (or better, caller) for each of them in here.
+
+    @Override
+    protected void onAttachedToWindow() {
+        super.onAttachedToWindow();
+        mProvider.getViewDelegate().onAttachedToWindow();
     }
 
-    /** @hide discard all textures from tiles */
-    protected void discardAllTextures() {
-        nativeDiscardAllTextures();
+    @Override
+    protected void onDetachedFromWindow() {
+        mProvider.getViewDelegate().onDetachedFromWindow();
+        super.onDetachedFromWindow();
     }
 
-    /**
-     * Begin collecting per-tile profiling data
-     *
-     * @hide only used by profiling tests
-     */
-    public void tileProfilingStart() {
-        nativeTileProfilingStart();
-    }
-    /**
-     * Return per-tile profiling data
-     *
-     * @hide only used by profiling tests
-     */
-    public float tileProfilingStop() {
-        return nativeTileProfilingStop();
+    @Override
+    public void setLayoutParams(ViewGroup.LayoutParams params) {
+        mProvider.getViewDelegate().setLayoutParams(params);
     }
 
-    /** @hide only used by profiling tests */
-    public void tileProfilingClear() {
-        nativeTileProfilingClear();
-    }
-    /** @hide only used by profiling tests */
-    public int tileProfilingNumFrames() {
-        return nativeTileProfilingNumFrames();
-    }
-    /** @hide only used by profiling tests */
-    public int tileProfilingNumTilesInFrame(int frame) {
-        return nativeTileProfilingNumTilesInFrame(frame);
-    }
-    /** @hide only used by profiling tests */
-    public int tileProfilingGetInt(int frame, int tile, String key) {
-        return nativeTileProfilingGetInt(frame, tile, key);
-    }
-    /** @hide only used by profiling tests */
-    public float tileProfilingGetFloat(int frame, int tile, String key) {
-        return nativeTileProfilingGetFloat(frame, tile, key);
+    @Override
+    public void setOverScrollMode(int mode) {
+        super.setOverScrollMode(mode);
+        // This method may called in the constructor chain, before the WebView provider is
+        // created. (Fortunately, this is the only method we override that can get called by
+        // any of the base class constructors).
+        ensureProviderCreated();
+        mProvider.getViewDelegate().setOverScrollMode(mode);
     }
 
-    /**
-     * Checks the focused content for an editable text field. This can be
-     * text input or ContentEditable.
-     * @return true if the focused item is an editable text field.
-     */
-    boolean focusCandidateIsEditableText() {
-        boolean isEditable = false;
-        // TODO: reverse sDisableNavcache so that its name is positive
-        boolean isNavcacheEnabled = !sDisableNavcache;
-        if (isNavcacheEnabled) {
-            isEditable = nativeFocusCandidateIsEditableText(mNativeClass);
-        } else if (mFocusedNode != null) {
-            isEditable = mFocusedNode.mEditable;
-        }
-        return isEditable;
+    @Override
+    public void setScrollBarStyle(int style) {
+        mProvider.getViewDelegate().setScrollBarStyle(style);
+        super.setScrollBarStyle(style);
     }
 
-    // TODO: Remove this
-    Rect cursorRingBounds() {
-        if (sDisableNavcache) {
-            return new Rect();
-        }
-        return nativeGetCursorRingBounds();
+    @Override
+    protected int computeHorizontalScrollRange() {
+        return mProvider.getScrollDelegate().computeHorizontalScrollRange();
     }
 
-    private native int nativeCacheHitFramePointer();
-    private native boolean  nativeCacheHitIsPlugin();
-    private native Rect nativeCacheHitNodeBounds();
-    private native int nativeCacheHitNodePointer();
-    /* package */ native void nativeClearCursor();
-    private native void     nativeCreate(int ptr, String drawableDir, boolean isHighEndGfx);
-    private native int      nativeCursorFramePointer();
-    private native Rect     nativeCursorNodeBounds();
-    private native int nativeCursorNodePointer();
-    private native boolean  nativeCursorIntersects(Rect visibleRect);
-    private native boolean  nativeCursorIsAnchor();
-    private native boolean  nativeCursorIsTextInput();
-    private native Point    nativeCursorPosition();
-    private native String   nativeCursorText();
-    /**
-     * Returns true if the native cursor node says it wants to handle key events
-     * (ala plugins). This can only be called if mNativeClass is non-zero!
-     */
-    private native boolean  nativeCursorWantsKeyEvents();
-    private native void     nativeDebugDump();
-    private native void     nativeDestroy();
+    @Override
+    protected int computeHorizontalScrollOffset() {
+        return mProvider.getScrollDelegate().computeHorizontalScrollOffset();
+    }
 
-    /**
-     * Draw the picture set with a background color and extra. If
-     * "splitIfNeeded" is true and the return value is not 0, the return value
-     * MUST be passed to WebViewCore with SPLIT_PICTURE_SET message so that the
-     * native allocation can be freed.
-     */
-    private native int nativeDraw(Canvas canvas, RectF visibleRect,
-            int color, int extra, boolean splitIfNeeded);
-    private native void     nativeDumpDisplayTree(String urlOrNull);
-    private native boolean  nativeEvaluateLayersAnimations(int nativeInstance);
-    private native int      nativeGetDrawGLFunction(int nativeInstance, Rect rect,
-            Rect viewRect, RectF visibleRect, float scale, int extras);
-    private native void     nativeUpdateDrawGLFunction(Rect rect, Rect viewRect,
-            RectF visibleRect, float scale);
-    private native void     nativeExtendSelection(int x, int y);
-    /* package */ native int      nativeFocusCandidateFramePointer();
-    /* package */ native boolean  nativeFocusCandidateHasNextTextfield();
-    /* package */ native boolean  nativeFocusCandidateIsPassword();
-    private native boolean  nativeFocusCandidateIsRtlText();
-    private native boolean  nativeFocusCandidateIsTextInput();
-    private native boolean nativeFocusCandidateIsEditableText(int nativeClass);
-    /* package */ native int      nativeFocusCandidateMaxLength();
-    /* package */ native boolean  nativeFocusCandidateIsAutoComplete();
-    /* package */ native boolean  nativeFocusCandidateIsSpellcheck();
-    /* package */ native String   nativeFocusCandidateName();
-    private native Rect     nativeFocusCandidateNodeBounds();
-    /**
-     * @return A Rect with left, top, right, bottom set to the corresponding
-     * padding values in the focus candidate, if it is a textfield/textarea with
-     * a style.  Otherwise return null.  This is not actually a rectangle; Rect
-     * is being used to pass four integers.
-     */
-    private native Rect     nativeFocusCandidatePaddingRect();
-    /* package */ native int      nativeFocusCandidatePointer();
-    private native String   nativeFocusCandidateText();
-    /* package */ native float    nativeFocusCandidateTextSize();
-    /* package */ native int nativeFocusCandidateLineHeight();
-    /**
-     * Returns an integer corresponding to WebView.cpp::type.
-     * See WebTextView.setType()
-     */
-    private native int      nativeFocusCandidateType();
-    private native int      nativeFocusCandidateLayerId();
-    private native boolean  nativeFocusIsPlugin();
-    private native Rect     nativeFocusNodeBounds();
-    /* package */ native int nativeFocusNodePointer();
-    private native Rect     nativeGetCursorRingBounds();
-    private native String   nativeGetSelection();
-    private native boolean  nativeHasCursorNode();
-    private native boolean  nativeHasFocusNode();
-    private native void     nativeHideCursor();
-    private native boolean  nativeHitSelection(int x, int y);
-    private native String   nativeImageURI(int x, int y);
-    private native Rect     nativeLayerBounds(int layer);
-    /* package */ native boolean nativeMoveCursorToNextTextInput();
-    // return true if the page has been scrolled
-    private native boolean  nativeMotionUp(int x, int y, int slop);
-    // returns false if it handled the key
-    private native boolean  nativeMoveCursor(int keyCode, int count,
-            boolean noScroll);
-    private native int      nativeMoveGeneration();
-    /**
-     * @return true if the page should get the shift and arrow keys, rather
-     * than select text/navigation.
-     *
-     * If the focus is a plugin, or if the focus and cursor match and are
-     * a contentEditable element, then the page should handle these keys.
-     */
-    private native boolean  nativePageShouldHandleShiftAndArrows();
-    private native boolean  nativePointInNavCache(int x, int y, int slop);
-    private native void     nativeSelectBestAt(Rect rect);
-    private native void     nativeSelectAt(int x, int y);
-    private native void     nativeSetExtendSelection();
-    private native void     nativeSetFindIsUp(boolean isUp);
-    private native void     nativeSetHeightCanMeasure(boolean measure);
-    private native boolean  nativeSetBaseLayer(int nativeInstance,
-            int layer, Region invalRegion,
-            boolean showVisualIndicator, boolean isPictureAfterFirstLayout);
-    private native int      nativeGetBaseLayer();
-    private native void     nativeShowCursorTimed();
-    private native void     nativeReplaceBaseContent(int content);
-    private native void     nativeCopyBaseContentToPicture(Picture pict);
-    private native boolean  nativeHasContent();
-    private native void     nativeSetSelectionPointer(int nativeInstance,
-            boolean set, float scale, int x, int y);
-    private native boolean  nativeStartSelection(int x, int y);
-    private native void     nativeStopGL();
-    private native Rect     nativeSubtractLayers(Rect content);
-    private native int      nativeTextGeneration();
-    private native void     nativeDiscardAllTextures();
-    private native void     nativeTileProfilingStart();
-    private native float    nativeTileProfilingStop();
-    private native void     nativeTileProfilingClear();
-    private native int      nativeTileProfilingNumFrames();
-    private native int      nativeTileProfilingNumTilesInFrame(int frame);
-    private native int      nativeTileProfilingGetInt(int frame, int tile, String key);
-    private native float    nativeTileProfilingGetFloat(int frame, int tile, String key);
-    // Never call this version except by updateCachedTextfield(String) -
-    // we always want to pass in our generation number.
-    private native void     nativeUpdateCachedTextfield(String updatedText,
-            int generation);
-    private native boolean  nativeWordSelection(int x, int y);
-    // return NO_LEFTEDGE means failure.
-    static final int NO_LEFTEDGE = -1;
-    native int nativeGetBlockLeftEdge(int x, int y, float scale);
+    @Override
+    protected int computeVerticalScrollRange() {
+        return mProvider.getScrollDelegate().computeVerticalScrollRange();
+    }
 
-    private native void     nativeUseHardwareAccelSkia(boolean enabled);
+    @Override
+    protected int computeVerticalScrollOffset() {
+        return mProvider.getScrollDelegate().computeVerticalScrollOffset();
+    }
 
-    // Returns a pointer to the scrollable LayerAndroid at the given point.
-    private native int      nativeScrollableLayer(int x, int y, Rect scrollRect,
-            Rect scrollBounds);
-    /**
-     * Scroll the specified layer.
-     * @param layer Id of the layer to scroll, as determined by nativeScrollableLayer.
-     * @param newX Destination x position to which to scroll.
-     * @param newY Destination y position to which to scroll.
-     * @return True if the layer is successfully scrolled.
-     */
-    private native boolean  nativeScrollLayer(int layer, int newX, int newY);
-    private native void     nativeSetIsScrolling(boolean isScrolling);
-    private native int      nativeGetBackgroundColor();
-    native boolean  nativeSetProperty(String key, String value);
-    native String   nativeGetProperty(String key);
-    /**
-     * See {@link ComponentCallbacks2} for the trim levels and descriptions
-     */
-    private static native void     nativeOnTrimMemory(int level);
-    private static native void nativeSetPauseDrawing(int instance, boolean pause);
-    private static native boolean nativeDisableNavcache();
-    private static native void nativeSetTextSelection(int instance, int selection);
-    private static native int nativeGetHandleLayerId(int instance, int handle,
-            Rect cursorLocation);
-    private static native boolean nativeIsBaseFirst(int instance);
+    @Override
+    protected int computeVerticalScrollExtent() {
+        return mProvider.getScrollDelegate().computeVerticalScrollExtent();
+    }
+
+    @Override
+    public void computeScroll() {
+        mProvider.getScrollDelegate().computeScroll();
+    }
+
+    @Override
+    public boolean onHoverEvent(MotionEvent event) {
+        return mProvider.getViewDelegate().onHoverEvent(event);
+    }
+
+    @Override
+    public boolean onTouchEvent(MotionEvent event) {
+        return mProvider.getViewDelegate().onTouchEvent(event);
+    }
+
+    @Override
+    public boolean onGenericMotionEvent(MotionEvent event) {
+        return mProvider.getViewDelegate().onGenericMotionEvent(event);
+    }
+
+    @Override
+    public boolean onTrackballEvent(MotionEvent event) {
+        return mProvider.getViewDelegate().onTrackballEvent(event);
+    }
+
+    @Override
+    public boolean onKeyDown(int keyCode, KeyEvent event) {
+        return mProvider.getViewDelegate().onKeyDown(keyCode, event);
+    }
+
+    @Override
+    public boolean onKeyUp(int keyCode, KeyEvent event) {
+        return mProvider.getViewDelegate().onKeyUp(keyCode, event);
+    }
+
+    @Override
+    public boolean onKeyMultiple(int keyCode, int repeatCount, KeyEvent event) {
+        return mProvider.getViewDelegate().onKeyMultiple(keyCode, repeatCount, event);
+    }
+
+    /*
+    TODO: These are not currently implemented in WebViewClassic, but it seems inconsistent not
+    to be delegating them too.
+
+    @Override
+    public boolean onKeyPreIme(int keyCode, KeyEvent event) {
+        return mProvider.getViewDelegate().onKeyPreIme(keyCode, event);
+    }
+    @Override
+    public boolean onKeyLongPress(int keyCode, KeyEvent event) {
+        return mProvider.getViewDelegate().onKeyLongPress(keyCode, event);
+    }
+    @Override
+    public boolean onKeyShortcut(int keyCode, KeyEvent event) {
+        return mProvider.getViewDelegate().onKeyShortcut(keyCode, event);
+    }
+    */
+
+    @Deprecated
+    @Override
+    public boolean shouldDelayChildPressedState() {
+        return mProvider.getViewDelegate().shouldDelayChildPressedState();
+    }
+
+    @Override
+    public void onInitializeAccessibilityNodeInfo(AccessibilityNodeInfo info) {
+        super.onInitializeAccessibilityNodeInfo(info);
+        mProvider.getViewDelegate().onInitializeAccessibilityNodeInfo(info);
+    }
+
+    @Override
+    public void onInitializeAccessibilityEvent(AccessibilityEvent event) {
+        super.onInitializeAccessibilityEvent(event);
+        mProvider.getViewDelegate().onInitializeAccessibilityEvent(event);
+    }
+
+    /** @hide */
+    @Override
+    protected void onDrawVerticalScrollBar(Canvas canvas, Drawable scrollBar,
+            int l, int t, int r, int b) {
+        mProvider.getViewDelegate().onDrawVerticalScrollBar(canvas, scrollBar, l, t, r, b);
+    }
+
+    @Override
+    protected void onOverScrolled(int scrollX, int scrollY, boolean clampedX, boolean clampedY) {
+        mProvider.getViewDelegate().onOverScrolled(scrollX, scrollY, clampedX, clampedY);
+    }
+
+    @Override
+    protected void onWindowVisibilityChanged(int visibility) {
+        super.onWindowVisibilityChanged(visibility);
+        mProvider.getViewDelegate().onWindowVisibilityChanged(visibility);
+    }
+
+    @Override
+    protected boolean drawChild(Canvas canvas, View child, long drawingTime) {
+        // Not using short-circuit OR: provider does suppress base-class call.
+        return mProvider.getViewDelegate().drawChild(canvas, child, drawingTime) |
+                super.drawChild(canvas, child, drawingTime);
+    }
+
+    @Override
+    protected void onDraw(Canvas canvas) {
+        mProvider.getViewDelegate().onDraw(canvas);
+    }
+
+    @Override
+    public boolean performLongClick() {
+        return mProvider.getViewDelegate().performLongClick();
+    }
+
+    @Override
+    protected void onConfigurationChanged(Configuration newConfig) {
+        mProvider.getViewDelegate().onConfigurationChanged(newConfig);
+    }
+
+    @Override
+    public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
+        return mProvider.getViewDelegate().onCreateInputConnection(outAttrs);
+    }
+
+    @Override
+    protected void onVisibilityChanged(View changedView, int visibility) {
+        super.onVisibilityChanged(changedView, visibility);
+        mProvider.getViewDelegate().onVisibilityChanged(changedView, visibility);
+    }
+
+    @Override
+    public void onWindowFocusChanged(boolean hasWindowFocus) {
+        mProvider.getViewDelegate().onWindowFocusChanged(hasWindowFocus);
+        super.onWindowFocusChanged(hasWindowFocus);
+    }
+
+    @Override
+    protected void onFocusChanged(boolean focused, int direction, Rect previouslyFocusedRect) {
+        mProvider.getViewDelegate().onFocusChanged(focused, direction, previouslyFocusedRect);
+        super.onFocusChanged(focused, direction, previouslyFocusedRect);
+    }
+
+    /** @hide */
+    @Override
+    protected boolean setFrame(int left, int top, int right, int bottom) {
+        return mProvider.getViewDelegate().setFrame(left, top, right, bottom);
+    }
+
+    @Override
+    protected void onSizeChanged(int w, int h, int ow, int oh) {
+        super.onSizeChanged(w, h, ow, oh);
+        mProvider.getViewDelegate().onSizeChanged(w, h, ow, oh);
+    }
+
+    @Override
+    protected void onScrollChanged(int l, int t, int oldl, int oldt) {
+        super.onScrollChanged(l, t, oldl, oldt);
+        mProvider.getViewDelegate().onScrollChanged(l, t, oldl, oldt);
+    }
+
+    @Override
+    public boolean dispatchKeyEvent(KeyEvent event) {
+        return mProvider.getViewDelegate().dispatchKeyEvent(event);
+    }
+
+    @Override
+    public boolean requestFocus(int direction, Rect previouslyFocusedRect) {
+        return mProvider.getViewDelegate().requestFocus(direction, previouslyFocusedRect);
+    }
+
+    @Deprecated
+    @Override
+    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
+        mProvider.getViewDelegate().onMeasure(widthMeasureSpec, heightMeasureSpec);
+    }
+
+    @Override
+    public boolean requestChildRectangleOnScreen(View child, Rect rect, boolean immediate) {
+        return mProvider.getViewDelegate().requestChildRectangleOnScreen(child, rect, immediate);
+    }
+
+    @Override
+    public void setBackgroundColor(int color) {
+        mProvider.getViewDelegate().setBackgroundColor(color);
+    }
 }
diff --git a/core/java/android/webkit/WebViewClassic.java b/core/java/android/webkit/WebViewClassic.java
new file mode 100644
index 0000000..c9a3ff1
--- /dev/null
+++ b/core/java/android/webkit/WebViewClassic.java
@@ -0,0 +1,9373 @@
+/*
+ * Copyright (C) 2012 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 android.webkit;
+
+import android.animation.ObjectAnimator;
+import android.annotation.Widget;
+import android.app.ActivityManager;
+import android.app.AlertDialog;
+import android.content.BroadcastReceiver;
+import android.content.ClipData;
+import android.content.ClipboardManager;
+import android.content.ComponentCallbacks2;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.DialogInterface.OnCancelListener;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.content.pm.PackageManager;
+import android.content.res.Configuration;
+import android.database.DataSetObserver;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.graphics.BitmapShader;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.ColorFilter;
+import android.graphics.DrawFilter;
+import android.graphics.Paint;
+import android.graphics.PaintFlagsDrawFilter;
+import android.graphics.Picture;
+import android.graphics.Point;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.graphics.Region;
+import android.graphics.RegionIterator;
+import android.graphics.Shader;
+import android.graphics.drawable.Drawable;
+import android.net.Proxy;
+import android.net.ProxyProperties;
+import android.net.Uri;
+import android.net.http.SslCertificate;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.os.Handler;
+import android.os.Looper;
+import android.os.Message;
+import android.os.StrictMode;
+import android.os.SystemClock;
+import android.provider.Settings;
+import android.security.KeyChain;
+import android.speech.tts.TextToSpeech;
+import android.text.Editable;
+import android.text.InputType;
+import android.text.Selection;
+import android.text.TextUtils;
+import android.util.DisplayMetrics;
+import android.util.EventLog;
+import android.util.Log;
+import android.view.Display;
+import android.view.Gravity;
+import android.view.HapticFeedbackConstants;
+import android.view.HardwareCanvas;
+import android.view.InputDevice;
+import android.view.KeyCharacterMap;
+import android.view.KeyEvent;
+import android.view.LayoutInflater;
+import android.view.MotionEvent;
+import android.view.ScaleGestureDetector;
+import android.view.SoundEffectConstants;
+import android.view.VelocityTracker;
+import android.view.View;
+import android.view.View.MeasureSpec;
+import android.view.ViewConfiguration;
+import android.view.ViewGroup;
+import android.view.ViewParent;
+import android.view.ViewTreeObserver;
+import android.view.WindowManager;
+import android.view.accessibility.AccessibilityEvent;
+import android.view.accessibility.AccessibilityManager;
+import android.view.accessibility.AccessibilityNodeInfo;
+import android.view.inputmethod.BaseInputConnection;
+import android.view.inputmethod.EditorInfo;
+import android.view.inputmethod.InputConnection;
+import android.view.inputmethod.InputMethodManager;
+import android.webkit.WebView.HitTestResult;
+import android.webkit.WebView.PictureListener;
+import android.webkit.WebViewCore.DrawData;
+import android.webkit.WebViewCore.EventHub;
+import android.webkit.WebViewCore.TextFieldInitData;
+import android.webkit.WebViewCore.TouchEventData;
+import android.webkit.WebViewCore.TouchHighlightData;
+import android.webkit.WebViewCore.WebKitHitTest;
+import android.widget.AbsoluteLayout;
+import android.widget.Adapter;
+import android.widget.AdapterView;
+import android.widget.AdapterView.OnItemClickListener;
+import android.widget.ArrayAdapter;
+import android.widget.CheckedTextView;
+import android.widget.LinearLayout;
+import android.widget.ListView;
+import android.widget.OverScroller;
+import android.widget.PopupWindow;
+import android.widget.TextView;
+import android.widget.Toast;
+
+import junit.framework.Assert;
+
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.net.URLDecoder;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.HashSet;
+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;
+
+/**
+ * <p>A View that displays web pages. This class is the basis upon which you
+ * can roll your own web browser or simply display some online content within your Activity.
+ * It uses the WebKit rendering engine to display
+ * web pages and includes methods to navigate forward and backward
+ * through a history, zoom in and out, perform text searches and more.</p>
+ * <p>To enable the built-in zoom, set
+ * {@link #getSettings() WebSettings}.{@link WebSettings#setBuiltInZoomControls(boolean)}
+ * (introduced in API version 3).
+ * <p>Note that, in order for your Activity to access the Internet and load web pages
+ * in a WebView, you must add the {@code INTERNET} permissions to your
+ * Android Manifest file:</p>
+ * <pre>&lt;uses-permission android:name="android.permission.INTERNET" /></pre>
+ *
+ * <p>This must be a child of the <a
+ * href="{@docRoot}guide/topics/manifest/manifest-element.html">{@code <manifest>}</a>
+ * element.</p>
+ *
+ * <p>See the <a href="{@docRoot}resources/tutorials/views/hello-webview.html">Web View
+ * tutorial</a>.</p>
+ *
+ * <h3>Basic usage</h3>
+ *
+ * <p>By default, a WebView provides no browser-like widgets, does not
+ * enable JavaScript and web page errors are ignored. If your goal is only
+ * to display some HTML as a part of your UI, this is probably fine;
+ * the user won't need to interact with the web page beyond reading
+ * it, and the web page won't need to interact with the user. If you
+ * actually want a full-blown web browser, then you probably want to
+ * invoke the Browser application with a URL Intent rather than show it
+ * with a WebView. For example:
+ * <pre>
+ * Uri uri = Uri.parse("http://www.example.com");
+ * Intent intent = new Intent(Intent.ACTION_VIEW, uri);
+ * startActivity(intent);
+ * </pre>
+ * <p>See {@link android.content.Intent} for more information.</p>
+ *
+ * <p>To provide a WebView in your own Activity, include a {@code <WebView>} in your layout,
+ * or set the entire Activity window as a WebView during {@link
+ * android.app.Activity#onCreate(Bundle) onCreate()}:</p>
+ * <pre class="prettyprint">
+ * WebView webview = new WebView(this);
+ * setContentView(webview);
+ * </pre>
+ *
+ * <p>Then load the desired web page:</p>
+ * <pre>
+ * // Simplest usage: note that an exception will NOT be thrown
+ * // if there is an error loading this page (see below).
+ * webview.loadUrl("http://slashdot.org/");
+ *
+ * // OR, you can also load from an HTML string:
+ * String summary = "&lt;html>&lt;body>You scored &lt;b>192&lt;/b> points.&lt;/body>&lt;/html>";
+ * webview.loadData(summary, "text/html", null);
+ * // ... although note that there are restrictions on what this HTML can do.
+ * // See the JavaDocs for {@link #loadData(String,String,String) loadData()} and {@link
+ * #loadDataWithBaseURL(String,String,String,String,String) loadDataWithBaseURL()} for more info.
+ * </pre>
+ *
+ * <p>A WebView has several customization points where you can add your
+ * own behavior. These are:</p>
+ *
+ * <ul>
+ *   <li>Creating and setting a {@link android.webkit.WebChromeClient} subclass.
+ *       This class is called when something that might impact a
+ *       browser UI happens, for instance, progress updates and
+ *       JavaScript alerts are sent here (see <a
+ * href="{@docRoot}guide/developing/debug-tasks.html#DebuggingWebPages">Debugging Tasks</a>).
+ *   </li>
+ *   <li>Creating and setting a {@link android.webkit.WebViewClient} subclass.
+ *       It will be called when things happen that impact the
+ *       rendering of the content, eg, errors or form submissions. You
+ *       can also intercept URL loading here (via {@link
+ * android.webkit.WebViewClient#shouldOverrideUrlLoading(WebView,String)
+ * shouldOverrideUrlLoading()}).</li>
+ *   <li>Modifying the {@link android.webkit.WebSettings}, such as
+ * enabling JavaScript with {@link android.webkit.WebSettings#setJavaScriptEnabled(boolean)
+ * setJavaScriptEnabled()}. </li>
+ *   <li>Injecting Java objects into the WebView using the
+ *       {@link android.webkit.WebView#addJavascriptInterface} method. This
+ *       method allows you to inject Java objects into a page's JavaScript
+ *       context, so that they can be accessed by JavaScript in the page.</li>
+ * </ul>
+ *
+ * <p>Here's a more complicated example, showing error handling,
+ *    settings, and progress notification:</p>
+ *
+ * <pre class="prettyprint">
+ * // Let's display the progress in the activity title bar, like the
+ * // browser app does.
+ * getWindow().requestFeature(Window.FEATURE_PROGRESS);
+ *
+ * webview.getSettings().setJavaScriptEnabled(true);
+ *
+ * final Activity activity = this;
+ * webview.setWebChromeClient(new WebChromeClient() {
+ *   public void onProgressChanged(WebView view, int progress) {
+ *     // Activities and WebViews measure progress with different scales.
+ *     // The progress meter will automatically disappear when we reach 100%
+ *     activity.setProgress(progress * 1000);
+ *   }
+ * });
+ * webview.setWebViewClient(new WebViewClient() {
+ *   public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
+ *     Toast.makeText(activity, "Oh no! " + description, Toast.LENGTH_SHORT).show();
+ *   }
+ * });
+ *
+ * webview.loadUrl("http://slashdot.org/");
+ * </pre>
+ *
+ * <h3>Cookie and window management</h3>
+ *
+ * <p>For obvious security reasons, your application has its own
+ * cache, cookie store etc.&mdash;it does not share the Browser
+ * application's data. Cookies are managed on a separate thread, so
+ * operations like index building don't block the UI
+ * thread. Follow the instructions in {@link android.webkit.CookieSyncManager}
+ * if you want to use cookies in your application.
+ * </p>
+ *
+ * <p>By default, requests by the HTML to open new windows are
+ * ignored. This is true whether they be opened by JavaScript or by
+ * the target attribute on a link. You can customize your
+ * {@link WebChromeClient} to provide your own behaviour for opening multiple windows,
+ * and render them in whatever manner you want.</p>
+ *
+ * <p>The standard behavior for an Activity is to be destroyed and
+ * recreated when the device orientation or any other configuration changes. This will cause
+ * the WebView to reload the current page. If you don't want that, you
+ * can set your Activity to handle the {@code orientation} and {@code keyboardHidden}
+ * changes, and then just leave the WebView alone. It'll automatically
+ * re-orient itself as appropriate. Read <a
+ * href="{@docRoot}guide/topics/resources/runtime-changes.html">Handling Runtime Changes</a> for
+ * more information about how to handle configuration changes during runtime.</p>
+ *
+ *
+ * <h3>Building web pages to support different screen densities</h3>
+ *
+ * <p>The screen density of a device is based on the screen resolution. A screen with low density
+ * has fewer available pixels per inch, where a screen with high density
+ * has more &mdash; sometimes significantly more &mdash; pixels per inch. The density of a
+ * screen is important because, other things being equal, a UI element (such as a button) whose
+ * height and width are defined in terms of screen pixels will appear larger on the lower density
+ * screen and smaller on the higher density screen.
+ * For simplicity, Android collapses all actual screen densities into three generalized densities:
+ * high, medium, and low.</p>
+ * <p>By default, WebView scales a web page so that it is drawn at a size that matches the default
+ * appearance on a medium density screen. So, it applies 1.5x scaling on a high density screen
+ * (because its pixels are smaller) and 0.75x scaling on a low density screen (because its pixels
+ * are bigger).
+ * Starting with API Level 5 (Android 2.0), WebView supports DOM, CSS, and meta tag features to help
+ * you (as a web developer) target screens with different screen densities.</p>
+ * <p>Here's a summary of the features you can use to handle different screen densities:</p>
+ * <ul>
+ * <li>The {@code window.devicePixelRatio} DOM property. The value of this property specifies the
+ * default scaling factor used for the current device. For example, if the value of {@code
+ * window.devicePixelRatio} is "1.0", then the device is considered a medium density (mdpi) device
+ * and default scaling is not applied to the web page; if the value is "1.5", then the device is
+ * considered a high density device (hdpi) and the page content is scaled 1.5x; if the
+ * value is "0.75", then the device is considered a low density device (ldpi) and the content is
+ * scaled 0.75x. However, if you specify the {@code "target-densitydpi"} meta property
+ * (discussed below), then you can stop this default scaling behavior.</li>
+ * <li>The {@code -webkit-device-pixel-ratio} CSS media query. Use this to specify the screen
+ * densities for which this style sheet is to be used. The corresponding value should be either
+ * "0.75", "1", or "1.5", to indicate that the styles are for devices with low density, medium
+ * density, or high density screens, respectively. For example:
+ * <pre>
+ * &lt;link rel="stylesheet" media="screen and (-webkit-device-pixel-ratio:1.5)" href="hdpi.css" /&gt;</pre>
+ * <p>The {@code hdpi.css} stylesheet is only used for devices with a screen pixel ration of 1.5,
+ * which is the high density pixel ratio.</p>
+ * </li>
+ * <li>The {@code target-densitydpi} property for the {@code viewport} meta tag. You can use
+ * this to specify the target density for which the web page is designed, using the following
+ * values:
+ * <ul>
+ * <li>{@code device-dpi} - Use the device's native dpi as the target dpi. Default scaling never
+ * occurs.</li>
+ * <li>{@code high-dpi} - Use hdpi as the target dpi. Medium and low density screens scale down
+ * as appropriate.</li>
+ * <li>{@code medium-dpi} - Use mdpi as the target dpi. High density screens scale up and
+ * low density screens scale down. This is also the default behavior.</li>
+ * <li>{@code low-dpi} - Use ldpi as the target dpi. Medium and high density screens scale up
+ * as appropriate.</li>
+ * <li><em>{@code <value>}</em> - Specify a dpi value to use as the target dpi (accepted
+ * values are 70-400).</li>
+ * </ul>
+ * <p>Here's an example meta tag to specify the target density:</p>
+ * <pre>&lt;meta name="viewport" content="target-densitydpi=device-dpi" /&gt;</pre></li>
+ * </ul>
+ * <p>If you want to modify your web page for different densities, by using the {@code
+ * -webkit-device-pixel-ratio} CSS media query and/or the {@code
+ * window.devicePixelRatio} DOM property, then you should set the {@code target-densitydpi} meta
+ * property to {@code device-dpi}. This stops Android from performing scaling in your web page and
+ * allows you to make the necessary adjustments for each density via CSS and JavaScript.</p>
+ *
+ * <h3>HTML5 Video support</h3>
+ *
+ * <p>In order to support inline HTML5 video in your application, you need to have hardware
+ * acceleration turned on, and set a {@link android.webkit.WebChromeClient}. For full screen support,
+ * implementations of {@link WebChromeClient#onShowCustomView(View, WebChromeClient.CustomViewCallback)}
+ * and {@link WebChromeClient#onHideCustomView()} are required,
+ * {@link WebChromeClient#getVideoLoadingProgressView()} is optional.
+ * </p>
+ *
+ * @hide
+ */
+// TODO: Remove duplicated API documentation and @hide from fields and methods, and
+// checkThread() call. (All left in for now to ease branch merging.)
+// TODO: Check if any WebView published API methods are called from within here, and if so
+// we should bounce the call out via the proxy to enable any sub-class to override it.
+@Widget
+@SuppressWarnings("deprecation")
+public final class WebViewClassic implements WebViewProvider, WebViewProvider.ScrollDelegate,
+        WebViewProvider.ViewDelegate {
+    private class InnerGlobalLayoutListener implements ViewTreeObserver.OnGlobalLayoutListener {
+        @Override
+        public void onGlobalLayout() {
+            if (mWebView.isShown()) {
+                setGLRectViewport();
+            }
+        }
+    }
+
+    private class InnerScrollChangedListener implements ViewTreeObserver.OnScrollChangedListener {
+        @Override
+        public void onScrollChanged() {
+            if (mWebView.isShown()) {
+                setGLRectViewport();
+            }
+        }
+    }
+
+    /**
+     * InputConnection used for ContentEditable. This captures changes
+     * to the text and sends them either as key strokes or text changes.
+     */
+    private class WebViewInputConnection extends BaseInputConnection {
+        // Used for mapping characters to keys typed.
+        private KeyCharacterMap mKeyCharacterMap;
+        private boolean mIsKeySentByMe;
+        private int mInputType;
+        private int mImeOptions;
+        private String mHint;
+        private int mMaxLength;
+
+        public WebViewInputConnection() {
+            super(mWebView, true);
+        }
+
+        @Override
+        public boolean sendKeyEvent(KeyEvent event) {
+            // Some IMEs send key events directly using sendKeyEvents.
+            // WebViewInputConnection should treat these as text changes.
+            if (!mIsKeySentByMe) {
+                if (event.getAction() == KeyEvent.ACTION_UP) {
+                    if (event.getKeyCode() == KeyEvent.KEYCODE_DEL) {
+                        return deleteSurroundingText(1, 0);
+                    } else if (event.getKeyCode() == KeyEvent.KEYCODE_FORWARD_DEL) {
+                        return deleteSurroundingText(0, 1);
+                    } else if (event.getUnicodeChar() != 0){
+                        String newComposingText =
+                                Character.toString((char)event.getUnicodeChar());
+                        return commitText(newComposingText, 1);
+                    }
+                } else if (event.getAction() == KeyEvent.ACTION_DOWN &&
+                        (event.getKeyCode() == KeyEvent.KEYCODE_DEL
+                        || event.getKeyCode() == KeyEvent.KEYCODE_FORWARD_DEL
+                        || event.getUnicodeChar() != 0)) {
+                    return true; // only act on action_down
+                }
+            }
+            return super.sendKeyEvent(event);
+        }
+
+        public void setTextAndKeepSelection(CharSequence text) {
+            Editable editable = getEditable();
+            int selectionStart = Selection.getSelectionStart(editable);
+            int selectionEnd = Selection.getSelectionEnd(editable);
+            text = limitReplaceTextByMaxLength(text, editable.length());
+            editable.replace(0, editable.length(), text);
+            restartInput();
+            // Keep the previous selection.
+            selectionStart = Math.min(selectionStart, editable.length());
+            selectionEnd = Math.min(selectionEnd, editable.length());
+            setSelection(selectionStart, selectionEnd);
+        }
+
+        public void replaceSelection(CharSequence text) {
+            Editable editable = getEditable();
+            int selectionStart = Selection.getSelectionStart(editable);
+            int selectionEnd = Selection.getSelectionEnd(editable);
+            text = limitReplaceTextByMaxLength(text, selectionEnd - selectionStart);
+            setNewText(selectionStart, selectionEnd, text);
+            editable.replace(selectionStart, selectionEnd, text);
+            restartInput();
+            // Move caret to the end of the new text
+            int newCaret = selectionStart + text.length();
+            setSelection(newCaret, newCaret);
+        }
+
+        @Override
+        public boolean setComposingText(CharSequence text, int newCursorPosition) {
+            Editable editable = getEditable();
+            int start = getComposingSpanStart(editable);
+            int end = getComposingSpanEnd(editable);
+            if (start < 0 || end < 0) {
+                start = Selection.getSelectionStart(editable);
+                end = Selection.getSelectionEnd(editable);
+            }
+            if (end < start) {
+                int temp = end;
+                end = start;
+                start = temp;
+            }
+            CharSequence limitedText = limitReplaceTextByMaxLength(text, end - start);
+            setNewText(start, end, limitedText);
+            if (limitedText != text) {
+                newCursorPosition -= text.length() - limitedText.length();
+            }
+            super.setComposingText(limitedText, newCursorPosition);
+            if (limitedText != text) {
+                restartInput();
+                int lastCaret = start + limitedText.length();
+                finishComposingText();
+                setSelection(lastCaret, lastCaret);
+            }
+            return true;
+        }
+
+        @Override
+        public boolean commitText(CharSequence text, int newCursorPosition) {
+            setComposingText(text, newCursorPosition);
+            int cursorPosition = Selection.getSelectionEnd(getEditable());
+            setComposingRegion(cursorPosition, cursorPosition);
+            return true;
+        }
+
+        @Override
+        public boolean deleteSurroundingText(int leftLength, int rightLength) {
+            Editable editable = getEditable();
+            int cursorPosition = Selection.getSelectionEnd(editable);
+            int startDelete = Math.max(0, cursorPosition - leftLength);
+            int endDelete = Math.min(editable.length(),
+                    cursorPosition + rightLength);
+            setNewText(startDelete, endDelete, "");
+            return super.deleteSurroundingText(leftLength, rightLength);
+        }
+
+        @Override
+        public boolean performEditorAction(int editorAction) {
+
+            boolean handled = true;
+            switch (editorAction) {
+            case EditorInfo.IME_ACTION_NEXT:
+                mWebView.requestFocus(View.FOCUS_FORWARD);
+                break;
+            case EditorInfo.IME_ACTION_PREVIOUS:
+                mWebView.requestFocus(View.FOCUS_BACKWARD);
+                break;
+            case EditorInfo.IME_ACTION_DONE:
+                WebViewClassic.this.hideSoftKeyboard();
+                break;
+            case EditorInfo.IME_ACTION_GO:
+            case EditorInfo.IME_ACTION_SEARCH:
+                WebViewClassic.this.hideSoftKeyboard();
+                String text = getEditable().toString();
+                passToJavaScript(text, new KeyEvent(KeyEvent.ACTION_DOWN,
+                        KeyEvent.KEYCODE_ENTER));
+                passToJavaScript(text, new KeyEvent(KeyEvent.ACTION_UP,
+                        KeyEvent.KEYCODE_ENTER));
+                break;
+
+            default:
+                handled = super.performEditorAction(editorAction);
+                break;
+            }
+
+            return handled;
+        }
+
+        public void initEditorInfo(WebViewCore.TextFieldInitData initData) {
+            int type = initData.mType;
+            int inputType = InputType.TYPE_CLASS_TEXT
+                    | InputType.TYPE_TEXT_VARIATION_WEB_EDIT_TEXT;
+            int imeOptions = EditorInfo.IME_FLAG_NO_EXTRACT_UI
+                    | EditorInfo.IME_FLAG_NO_FULLSCREEN;
+            if (!initData.mIsSpellCheckEnabled) {
+                inputType |= InputType.TYPE_TEXT_FLAG_NO_SUGGESTIONS;
+            }
+            if (WebTextView.TEXT_AREA != type
+                    && initData.mIsTextFieldNext) {
+                imeOptions |= EditorInfo.IME_FLAG_NAVIGATE_NEXT;
+            }
+            switch (type) {
+                case WebTextView.NORMAL_TEXT_FIELD:
+                    imeOptions |= EditorInfo.IME_ACTION_GO;
+                    break;
+                case WebTextView.TEXT_AREA:
+                    inputType |= InputType.TYPE_TEXT_FLAG_MULTI_LINE
+                            | InputType.TYPE_TEXT_FLAG_CAP_SENTENCES
+                            | InputType.TYPE_TEXT_FLAG_AUTO_CORRECT;
+                    imeOptions |= EditorInfo.IME_ACTION_NONE;
+                    break;
+                case WebTextView.PASSWORD:
+                    inputType |= EditorInfo.TYPE_TEXT_VARIATION_WEB_PASSWORD;
+                    imeOptions |= EditorInfo.IME_ACTION_GO;
+                    break;
+                case WebTextView.SEARCH:
+                    imeOptions |= EditorInfo.IME_ACTION_SEARCH;
+                    break;
+                case WebTextView.EMAIL:
+                    // inputType needs to be overwritten because of the different text variation.
+                    inputType = InputType.TYPE_CLASS_TEXT
+                            | InputType.TYPE_TEXT_VARIATION_WEB_EMAIL_ADDRESS;
+                    imeOptions |= EditorInfo.IME_ACTION_GO;
+                    break;
+                case WebTextView.NUMBER:
+                    // inputType needs to be overwritten because of the different class.
+                    inputType = InputType.TYPE_CLASS_NUMBER | InputType.TYPE_NUMBER_VARIATION_NORMAL
+                            | InputType.TYPE_NUMBER_FLAG_SIGNED | InputType.TYPE_NUMBER_FLAG_DECIMAL;
+                    // Number and telephone do not have both a Tab key and an
+                    // action, so set the action to NEXT
+                    imeOptions |= EditorInfo.IME_ACTION_NEXT;
+                    break;
+                case WebTextView.TELEPHONE:
+                    // inputType needs to be overwritten because of the different class.
+                    inputType = InputType.TYPE_CLASS_PHONE;
+                    imeOptions |= EditorInfo.IME_ACTION_NEXT;
+                    break;
+                case WebTextView.URL:
+                    // TYPE_TEXT_VARIATION_URI prevents Tab key from showing, so
+                    // exclude it for now.
+                    imeOptions |= EditorInfo.IME_ACTION_GO;
+                    inputType |= InputType.TYPE_TEXT_VARIATION_URI;
+                    break;
+                default:
+                    imeOptions |= EditorInfo.IME_ACTION_GO;
+                    break;
+            }
+            mHint = initData.mLabel;
+            mInputType = inputType;
+            mImeOptions = imeOptions;
+            mMaxLength = initData.mMaxLength;
+        }
+
+        public void setupEditorInfo(EditorInfo outAttrs) {
+            outAttrs.inputType = mInputType;
+            outAttrs.imeOptions = mImeOptions;
+            outAttrs.hintText = mHint;
+            outAttrs.initialCapsMode = getCursorCapsMode(InputType.TYPE_CLASS_TEXT);
+        }
+
+        /**
+         * Sends a text change to webkit indirectly. If it is a single-
+         * character add or delete, it sends it as a key stroke. If it cannot
+         * be represented as a key stroke, it sends it as a field change.
+         * @param start The start offset (inclusive) of the text being changed.
+         * @param end The end offset (exclusive) of the text being changed.
+         * @param text The new text to replace the changed text.
+         */
+        private void setNewText(int start, int end, CharSequence text) {
+            mIsKeySentByMe = true;
+            Editable editable = getEditable();
+            CharSequence original = editable.subSequence(start, end);
+            boolean isCharacterAdd = false;
+            boolean isCharacterDelete = false;
+            int textLength = text.length();
+            int originalLength = original.length();
+            if (textLength > originalLength) {
+                isCharacterAdd = (textLength == originalLength + 1)
+                        && TextUtils.regionMatches(text, 0, original, 0,
+                                originalLength);
+            } else if (originalLength > textLength) {
+                isCharacterDelete = (textLength == originalLength - 1)
+                        && TextUtils.regionMatches(text, 0, original, 0,
+                                textLength);
+            }
+            if (isCharacterAdd) {
+                sendCharacter(text.charAt(textLength - 1));
+            } else if (isCharacterDelete) {
+                sendKey(KeyEvent.KEYCODE_DEL);
+            } else if ((textLength != originalLength) ||
+                    !TextUtils.regionMatches(text, 0, original, 0,
+                            textLength)) {
+                // Send a message so that key strokes and text replacement
+                // do not come out of order.
+                Message replaceMessage = mPrivateHandler.obtainMessage(
+                        REPLACE_TEXT, start,  end, text.toString());
+                mPrivateHandler.sendMessage(replaceMessage);
+            }
+            mIsKeySentByMe = false;
+        }
+
+        /**
+         * Send a single character to the WebView as a key down and up event.
+         * @param c The character to be sent.
+         */
+        private void sendCharacter(char c) {
+            if (mKeyCharacterMap == null) {
+                mKeyCharacterMap = KeyCharacterMap.load(KeyCharacterMap.VIRTUAL_KEYBOARD);
+            }
+            char[] chars = new char[1];
+            chars[0] = c;
+            KeyEvent[] events = mKeyCharacterMap.getEvents(chars);
+            if (events != null) {
+                for (KeyEvent event : events) {
+                    sendKeyEvent(event);
+                }
+            } else {
+                Message msg = mPrivateHandler.obtainMessage(KEY_PRESS, (int) c, 0);
+                mPrivateHandler.sendMessage(msg);
+            }
+        }
+
+        /**
+         * Send a key event for a specific key code, not a standard
+         * unicode character.
+         * @param keyCode The key code to send.
+         */
+        private void sendKey(int keyCode) {
+            long eventTime = SystemClock.uptimeMillis();
+            sendKeyEvent(new KeyEvent(eventTime, eventTime,
+                    KeyEvent.ACTION_DOWN, keyCode, 0, 0,
+                    KeyCharacterMap.VIRTUAL_KEYBOARD, 0,
+                    KeyEvent.FLAG_SOFT_KEYBOARD));
+            sendKeyEvent(new KeyEvent(SystemClock.uptimeMillis(), eventTime,
+                    KeyEvent.ACTION_UP, keyCode, 0, 0,
+                    KeyCharacterMap.VIRTUAL_KEYBOARD, 0,
+                    KeyEvent.FLAG_SOFT_KEYBOARD));
+        }
+
+        private CharSequence limitReplaceTextByMaxLength(CharSequence text,
+                int numReplaced) {
+            if (mMaxLength > 0) {
+                Editable editable = getEditable();
+                int maxReplace = mMaxLength - editable.length() + numReplaced;
+                if (maxReplace < text.length()) {
+                    maxReplace = Math.max(maxReplace, 0);
+                    // New length is greater than the maximum. trim it down.
+                    text = text.subSequence(0, maxReplace);
+                }
+            }
+            return text;
+        }
+
+        private void restartInput() {
+            InputMethodManager imm = InputMethodManager.peekInstance();
+            if (imm != null) {
+                // Since the text has changed, do not allow the IME to replace the
+                // existing text as though it were a completion.
+                imm.restartInput(mWebView);
+            }
+        }
+    }
+
+    private class PastePopupWindow extends PopupWindow implements View.OnClickListener {
+        private ViewGroup mContentView;
+        private TextView mPasteTextView;
+
+        public PastePopupWindow() {
+            super(mContext, null,
+                    com.android.internal.R.attr.textSelectHandleWindowStyle);
+            setClippingEnabled(true);
+            LinearLayout linearLayout = new LinearLayout(mContext);
+            linearLayout.setOrientation(LinearLayout.HORIZONTAL);
+            mContentView = linearLayout;
+            mContentView.setBackgroundResource(
+                    com.android.internal.R.drawable.text_edit_paste_window);
+
+            LayoutInflater inflater = (LayoutInflater)mContext.
+                    getSystemService(Context.LAYOUT_INFLATER_SERVICE);
+
+            ViewGroup.LayoutParams wrapContent = new ViewGroup.LayoutParams(
+                    ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
+
+            mPasteTextView = (TextView) inflater.inflate(
+                    com.android.internal.R.layout.text_edit_action_popup_text, null);
+            mPasteTextView.setLayoutParams(wrapContent);
+            mContentView.addView(mPasteTextView);
+            mPasteTextView.setText(com.android.internal.R.string.paste);
+            mPasteTextView.setOnClickListener(this);
+            this.setContentView(mContentView);
+        }
+
+        public void show(Rect cursorRect, int windowLeft, int windowTop) {
+            measureContent();
+
+            int width = mContentView.getMeasuredWidth();
+            int height = mContentView.getMeasuredHeight();
+            int y = cursorRect.top - height;
+            if (y < windowTop) {
+                // There's not enough room vertically, move it below the
+                // handle.
+                // The selection handle is vertically offset by 1/4 of the
+                // line height.
+                ensureSelectionHandles();
+                y = cursorRect.bottom - (cursorRect.height() / 4) +
+                        mSelectHandleCenter.getIntrinsicHeight();
+            }
+            int x = cursorRect.centerX() - (width / 2);
+            if (x < windowLeft) {
+                x = windowLeft;
+            }
+            if (!isShowing()) {
+                showAtLocation(mWebView, Gravity.NO_GRAVITY, x, y);
+            }
+            update(x, y, width, height);
+        }
+
+        public void hide() {
+            dismiss();
+        }
+
+        @Override
+        public void onClick(View view) {
+            pasteFromClipboard();
+            selectionDone();
+        }
+
+        protected void measureContent() {
+            final DisplayMetrics displayMetrics = mContext.getResources().getDisplayMetrics();
+            mContentView.measure(
+                    View.MeasureSpec.makeMeasureSpec(displayMetrics.widthPixels,
+                            View.MeasureSpec.AT_MOST),
+                    View.MeasureSpec.makeMeasureSpec(displayMetrics.heightPixels,
+                            View.MeasureSpec.AT_MOST));
+        }
+    }
+
+    // The listener to capture global layout change event.
+    private InnerGlobalLayoutListener mGlobalLayoutListener = null;
+
+    // The listener to capture scroll event.
+    private InnerScrollChangedListener mScrollChangedListener = null;
+
+    // if AUTO_REDRAW_HACK is true, then the CALL key will toggle redrawing
+    // the screen all-the-time. Good for profiling our drawing code
+    static private final boolean AUTO_REDRAW_HACK = false;
+    // true means redraw the screen all-the-time. Only with AUTO_REDRAW_HACK
+    private boolean mAutoRedraw;
+
+    // Reference to the AlertDialog displayed by InvokeListBox.
+    // It's used to dismiss the dialog in destroy if not done before.
+    private AlertDialog mListBoxDialog = null;
+
+    static final String LOGTAG = "webview";
+
+    private ZoomManager mZoomManager;
+
+    private final Rect mGLRectViewport = new Rect();
+    private final Rect mViewRectViewport = new Rect();
+    private final RectF mVisibleContentRect = new RectF();
+    private boolean mGLViewportEmpty = false;
+    WebViewInputConnection mInputConnection = null;
+    private int mFieldPointer;
+    private PastePopupWindow mPasteWindow;
+
+    private static class OnTrimMemoryListener implements ComponentCallbacks2 {
+        private static OnTrimMemoryListener sInstance = null;
+
+        static void init(Context c) {
+            if (sInstance == null) {
+                sInstance = new OnTrimMemoryListener(c.getApplicationContext());
+            }
+        }
+
+        private OnTrimMemoryListener(Context c) {
+            c.registerComponentCallbacks(this);
+        }
+
+        @Override
+        public void onConfigurationChanged(Configuration newConfig) {
+            // Ignore
+        }
+
+        @Override
+        public void onLowMemory() {
+            // Ignore
+        }
+
+        @Override
+        public void onTrimMemory(int level) {
+            if (DebugFlags.WEB_VIEW) {
+                Log.d("WebView", "onTrimMemory: " + level);
+            }
+            // When framework reset EGL context during high memory pressure, all
+            // the existing GL resources for the html5 video will be destroyed
+            // at native side.
+            // Here we just need to clean up the Surface Texture which is static.
+            HTML5VideoInline.cleanupSurfaceTexture();
+            WebViewClassic.nativeOnTrimMemory(level);
+        }
+
+    }
+
+    // A final CallbackProxy shared by WebViewCore and BrowserFrame.
+    private CallbackProxy mCallbackProxy;
+
+    private WebViewDatabase mDatabase;
+
+    // SSL certificate for the main top-level page (if secure)
+    private SslCertificate mCertificate;
+
+    // Native WebView pointer that is 0 until the native object has been
+    // created.
+    private int mNativeClass;
+    // This would be final but it needs to be set to null when the WebView is
+    // destroyed.
+    private WebViewCore mWebViewCore;
+    // Handler for dispatching UI messages.
+    /* package */ final Handler mPrivateHandler = new PrivateHandler();
+    // Used to ignore changes to webkit text that arrives to the UI side after
+    // more key events.
+    private int mTextGeneration;
+
+    /* package */ void incrementTextGeneration() { mTextGeneration++; }
+
+    // Used by WebViewCore to create child views.
+    /* package */ ViewManager mViewManager;
+
+    // Used to display in full screen mode
+    PluginFullScreenHolder mFullScreenHolder;
+
+    /**
+     * Position of the last touch event in pixels.
+     * Use integer to prevent loss of dragging delta calculation accuracy;
+     * which was done in float and converted to integer, and resulted in gradual
+     * and compounding touch position and view dragging mismatch.
+     */
+    private int mLastTouchX;
+    private int mLastTouchY;
+    private int mStartTouchX;
+    private int mStartTouchY;
+    private float mAverageAngle;
+
+    /**
+     * Time of the last touch event.
+     */
+    private long mLastTouchTime;
+
+    /**
+     * Time of the last time sending touch event to WebViewCore
+     */
+    private long mLastSentTouchTime;
+
+    /**
+     * The minimum elapsed time before sending another ACTION_MOVE event to
+     * WebViewCore. This really should be tuned for each type of the devices.
+     * For example in Google Map api test case, it takes Dream device at least
+     * 150ms to do a full cycle in the WebViewCore by processing a touch event,
+     * triggering the layout and drawing the picture. While the same process
+     * takes 60+ms on the current high speed device. If we make
+     * TOUCH_SENT_INTERVAL too small, there will be multiple touch events sent
+     * to WebViewCore queue and the real layout and draw events will be pushed
+     * to further, which slows down the refresh rate. Choose 50 to favor the
+     * current high speed devices. For Dream like devices, 100 is a better
+     * choice. Maybe make this in the buildspec later.
+     * (Update 12/14/2010: changed to 0 since current device should be able to
+     * handle the raw events and Map team voted to have the raw events too.
+     */
+    private static final int TOUCH_SENT_INTERVAL = 0;
+    private int mCurrentTouchInterval = TOUCH_SENT_INTERVAL;
+
+    /**
+     * Helper class to get velocity for fling
+     */
+    VelocityTracker mVelocityTracker;
+    private int mMaximumFling;
+    private float mLastVelocity;
+    private float mLastVelX;
+    private float mLastVelY;
+
+    // The id of the native layer being scrolled.
+    private int mCurrentScrollingLayerId;
+    private Rect mScrollingLayerRect = new Rect();
+
+    // only trigger accelerated fling if the new velocity is at least
+    // MINIMUM_VELOCITY_RATIO_FOR_ACCELERATION times of the previous velocity
+    private static final float MINIMUM_VELOCITY_RATIO_FOR_ACCELERATION = 0.2f;
+
+    /**
+     * Touch mode
+     */
+    private int mTouchMode = TOUCH_DONE_MODE;
+    private static final int TOUCH_INIT_MODE = 1;
+    private static final int TOUCH_DRAG_START_MODE = 2;
+    private static final int TOUCH_DRAG_MODE = 3;
+    private static final int TOUCH_SHORTPRESS_START_MODE = 4;
+    private static final int TOUCH_SHORTPRESS_MODE = 5;
+    private static final int TOUCH_DOUBLE_TAP_MODE = 6;
+    private static final int TOUCH_DONE_MODE = 7;
+    private static final int TOUCH_PINCH_DRAG = 8;
+    private static final int TOUCH_DRAG_LAYER_MODE = 9;
+
+    // Whether to forward the touch events to WebCore
+    // Can only be set by WebKit via JNI.
+    private boolean mForwardTouchEvents = false;
+
+    // Whether to prevent default during touch. The initial value depends on
+    // mForwardTouchEvents. If WebCore wants all the touch events, it says yes
+    // for touch down. Otherwise UI will wait for the answer of the first
+    // confirmed move before taking over the control.
+    private static final int PREVENT_DEFAULT_NO = 0;
+    private static final int PREVENT_DEFAULT_MAYBE_YES = 1;
+    private static final int PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN = 2;
+    private static final int PREVENT_DEFAULT_YES = 3;
+    private static final int PREVENT_DEFAULT_IGNORE = 4;
+    private int mPreventDefault = PREVENT_DEFAULT_IGNORE;
+
+    // true when the touch movement exceeds the slop
+    private boolean mConfirmMove;
+
+    // if true, touch events will be first processed by WebCore, if prevent
+    // default is not set, the UI will continue handle them.
+    private boolean mDeferTouchProcess;
+
+    // to avoid interfering with the current touch events, track them
+    // separately. Currently no snapping or fling in the deferred process mode
+    private int mDeferTouchMode = TOUCH_DONE_MODE;
+    private float mLastDeferTouchX;
+    private float mLastDeferTouchY;
+
+    // Whether or not to draw the cursor ring.
+    private boolean mDrawCursorRing = true;
+
+    // true if onPause has been called (and not onResume)
+    private boolean mIsPaused;
+
+    private HitTestResult mInitialHitTestResult;
+    private WebKitHitTest mFocusedNode;
+
+    /**
+     * Customizable constant
+     */
+    // pre-computed square of ViewConfiguration.getScaledTouchSlop()
+    private int mTouchSlopSquare;
+    // pre-computed square of ViewConfiguration.getScaledDoubleTapSlop()
+    private int mDoubleTapSlopSquare;
+    // pre-computed density adjusted navigation slop
+    private int mNavSlop;
+    // This should be ViewConfiguration.getTapTimeout()
+    // But system time out is 100ms, which is too short for the browser.
+    // In the browser, if it switches out of tap too soon, jump tap won't work.
+    // In addition, a double tap on a trackpad will always have a duration of
+    // 300ms, so this value must be at least that (otherwise we will timeout the
+    // first tap and convert it to a long press).
+    private static final int TAP_TIMEOUT = 300;
+    // This should be ViewConfiguration.getLongPressTimeout()
+    // But system time out is 500ms, which is too short for the browser.
+    // With a short timeout, it's difficult to treat trigger a short press.
+    private static final int LONG_PRESS_TIMEOUT = 1000;
+    // needed to avoid flinging after a pause of no movement
+    private static final int MIN_FLING_TIME = 250;
+    // draw unfiltered after drag is held without movement
+    private static final int MOTIONLESS_TIME = 100;
+    // The amount of content to overlap between two screens when going through
+    // pages with the space bar, in pixels.
+    private static final int PAGE_SCROLL_OVERLAP = 24;
+
+    /**
+     * These prevent calling requestLayout if either dimension is fixed. This
+     * depends on the layout parameters and the measure specs.
+     */
+    boolean mWidthCanMeasure;
+    boolean mHeightCanMeasure;
+
+    // Remember the last dimensions we sent to the native side so we can avoid
+    // sending the same dimensions more than once.
+    int mLastWidthSent;
+    int mLastHeightSent;
+    // Since view height sent to webkit could be fixed to avoid relayout, this
+    // value records the last sent actual view height.
+    int mLastActualHeightSent;
+
+    private int mContentWidth;   // cache of value from WebViewCore
+    private int mContentHeight;  // cache of value from WebViewCore
+
+    // Need to have the separate control for horizontal and vertical scrollbar
+    // style than the View's single scrollbar style
+    private boolean mOverlayHorizontalScrollbar = true;
+    private boolean mOverlayVerticalScrollbar = false;
+
+    // our standard speed. this way small distances will be traversed in less
+    // time than large distances, but we cap the duration, so that very large
+    // distances won't take too long to get there.
+    private static final int STD_SPEED = 480;  // pixels per second
+    // time for the longest scroll animation
+    private static final int MAX_DURATION = 750;   // milliseconds
+    private static final int SLIDE_TITLE_DURATION = 500;   // milliseconds
+
+    // Used by OverScrollGlow
+    OverScroller mScroller;
+
+    private boolean mInOverScrollMode = false;
+    private static Paint mOverScrollBackground;
+    private static Paint mOverScrollBorder;
+
+    private boolean mWrapContent;
+    private static final int MOTIONLESS_FALSE           = 0;
+    private static final int MOTIONLESS_PENDING         = 1;
+    private static final int MOTIONLESS_TRUE            = 2;
+    private static final int MOTIONLESS_IGNORE          = 3;
+    private int mHeldMotionless;
+
+    // An instance for injecting accessibility in WebViews with disabled
+    // JavaScript or ones for which no accessibility script exists
+    private AccessibilityInjector mAccessibilityInjector;
+
+    // flag indicating if accessibility script is injected so we
+    // know to handle Shift and arrows natively first
+    private boolean mAccessibilityScriptInjected;
+
+
+    /**
+     * How long the caret handle will last without being touched.
+     */
+    private static final long CARET_HANDLE_STAMINA_MS = 3000;
+
+    private Drawable mSelectHandleLeft;
+    private Drawable mSelectHandleRight;
+    private Drawable mSelectHandleCenter;
+    private Rect mSelectCursorBase = new Rect();
+    private int mSelectCursorBaseLayerId;
+    private Rect mSelectCursorExtent = new Rect();
+    private int mSelectCursorExtentLayerId;
+    private Rect mSelectDraggingCursor;
+    private Point mSelectDraggingOffset = new Point();
+    private boolean mIsCaretSelection;
+    static final int HANDLE_ID_START = 0;
+    static final int HANDLE_ID_END = 1;
+    static final int HANDLE_ID_BASE = 2;
+    static final int HANDLE_ID_EXTENT = 3;
+
+    // the color used to highlight the touch rectangles
+    static final int HIGHLIGHT_COLOR = 0x6633b5e5;
+    // the region indicating where the user touched on the screen
+    private Region mTouchHighlightRegion = new Region();
+    // the paint for the touch highlight
+    private Paint mTouchHightlightPaint = new Paint();
+    // debug only
+    private static final boolean DEBUG_TOUCH_HIGHLIGHT = true;
+    private static final int TOUCH_HIGHLIGHT_ELAPSE_TIME = 2000;
+    private Paint mTouchCrossHairColor;
+    private int mTouchHighlightX;
+    private int mTouchHighlightY;
+    private long mTouchHighlightRequested;
+
+    // Basically this proxy is used to tell the Video to update layer tree at
+    // SetBaseLayer time and to pause when WebView paused.
+    private HTML5VideoViewProxy mHTML5VideoViewProxy;
+
+    // If we are using a set picture, don't send view updates to webkit
+    private boolean mBlockWebkitViewMessages = false;
+
+    // cached value used to determine if we need to switch drawing models
+    private boolean mHardwareAccelSkia = false;
+
+    /*
+     * Private message ids
+     */
+    private static final int REMEMBER_PASSWORD          = 1;
+    private static final int NEVER_REMEMBER_PASSWORD    = 2;
+    private static final int SWITCH_TO_SHORTPRESS       = 3;
+    private static final int SWITCH_TO_LONGPRESS        = 4;
+    private static final int RELEASE_SINGLE_TAP         = 5;
+    private static final int DRAG_HELD_MOTIONLESS       = 8;
+    private static final int AWAKEN_SCROLL_BARS         = 9;
+    private static final int PREVENT_DEFAULT_TIMEOUT    = 10;
+    private static final int SCROLL_SELECT_TEXT         = 11;
+
+
+    private static final int FIRST_PRIVATE_MSG_ID = REMEMBER_PASSWORD;
+    private static final int LAST_PRIVATE_MSG_ID = SCROLL_SELECT_TEXT;
+
+    /*
+     * Package message ids
+     */
+    static final int SCROLL_TO_MSG_ID                   = 101;
+    static final int NEW_PICTURE_MSG_ID                 = 105;
+    static final int WEBCORE_INITIALIZED_MSG_ID         = 107;
+    static final int UPDATE_TEXTFIELD_TEXT_MSG_ID       = 108;
+    static final int UPDATE_ZOOM_RANGE                  = 109;
+    static final int UNHANDLED_NAV_KEY                  = 110;
+    static final int CLEAR_TEXT_ENTRY                   = 111;
+    static final int UPDATE_TEXT_SELECTION_MSG_ID       = 112;
+    static final int SHOW_RECT_MSG_ID                   = 113;
+    static final int LONG_PRESS_CENTER                  = 114;
+    static final int PREVENT_TOUCH_ID                   = 115;
+    static final int WEBCORE_NEED_TOUCH_EVENTS          = 116;
+    // obj=Rect in doc coordinates
+    static final int INVAL_RECT_MSG_ID                  = 117;
+    static final int REQUEST_KEYBOARD                   = 118;
+    static final int SHOW_FULLSCREEN                    = 120;
+    static final int HIDE_FULLSCREEN                    = 121;
+    static final int REPLACE_BASE_CONTENT               = 123;
+    static final int FORM_DID_BLUR                      = 124;
+    static final int UPDATE_MATCH_COUNT                 = 126;
+    static final int CENTER_FIT_RECT                    = 127;
+    static final int REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID = 128;
+    static final int SET_SCROLLBAR_MODES                = 129;
+    static final int SELECTION_STRING_CHANGED           = 130;
+    static final int HIT_TEST_RESULT                    = 131;
+    static final int SAVE_WEBARCHIVE_FINISHED           = 132;
+
+    static final int SET_AUTOFILLABLE                   = 133;
+    static final int AUTOFILL_COMPLETE                  = 134;
+
+    static final int SCREEN_ON                          = 136;
+    static final int ENTER_FULLSCREEN_VIDEO             = 137;
+    static final int UPDATE_ZOOM_DENSITY                = 139;
+    static final int EXIT_FULLSCREEN_VIDEO              = 140;
+
+    static final int COPY_TO_CLIPBOARD                  = 141;
+    static final int INIT_EDIT_FIELD                    = 142;
+    static final int REPLACE_TEXT                       = 143;
+    static final int CLEAR_CARET_HANDLE                 = 144;
+    static final int KEY_PRESS                          = 145;
+
+    private static final int FIRST_PACKAGE_MSG_ID = SCROLL_TO_MSG_ID;
+    private static final int LAST_PACKAGE_MSG_ID = HIT_TEST_RESULT;
+
+    static final String[] HandlerPrivateDebugString = {
+        "REMEMBER_PASSWORD", //              = 1;
+        "NEVER_REMEMBER_PASSWORD", //        = 2;
+        "SWITCH_TO_SHORTPRESS", //           = 3;
+        "SWITCH_TO_LONGPRESS", //            = 4;
+        "RELEASE_SINGLE_TAP", //             = 5;
+        "REQUEST_FORM_DATA", //              = 6;
+        "RESUME_WEBCORE_PRIORITY", //        = 7;
+        "DRAG_HELD_MOTIONLESS", //           = 8;
+        "AWAKEN_SCROLL_BARS", //             = 9;
+        "PREVENT_DEFAULT_TIMEOUT", //        = 10;
+        "SCROLL_SELECT_TEXT" //              = 11;
+    };
+
+    static final String[] HandlerPackageDebugString = {
+        "SCROLL_TO_MSG_ID", //               = 101;
+        "102", //                            = 102;
+        "103", //                            = 103;
+        "104", //                            = 104;
+        "NEW_PICTURE_MSG_ID", //             = 105;
+        "UPDATE_TEXT_ENTRY_MSG_ID", //       = 106;
+        "WEBCORE_INITIALIZED_MSG_ID", //     = 107;
+        "UPDATE_TEXTFIELD_TEXT_MSG_ID", //   = 108;
+        "UPDATE_ZOOM_RANGE", //              = 109;
+        "UNHANDLED_NAV_KEY", //              = 110;
+        "CLEAR_TEXT_ENTRY", //               = 111;
+        "UPDATE_TEXT_SELECTION_MSG_ID", //   = 112;
+        "SHOW_RECT_MSG_ID", //               = 113;
+        "LONG_PRESS_CENTER", //              = 114;
+        "PREVENT_TOUCH_ID", //               = 115;
+        "WEBCORE_NEED_TOUCH_EVENTS", //      = 116;
+        "INVAL_RECT_MSG_ID", //              = 117;
+        "REQUEST_KEYBOARD", //               = 118;
+        "DO_MOTION_UP", //                   = 119;
+        "SHOW_FULLSCREEN", //                = 120;
+        "HIDE_FULLSCREEN", //                = 121;
+        "DOM_FOCUS_CHANGED", //              = 122;
+        "REPLACE_BASE_CONTENT", //           = 123;
+        "FORM_DID_BLUR", //                  = 124;
+        "RETURN_LABEL", //                   = 125;
+        "UPDATE_MATCH_COUNT", //             = 126;
+        "CENTER_FIT_RECT", //                = 127;
+        "REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID", // = 128;
+        "SET_SCROLLBAR_MODES", //            = 129;
+        "SELECTION_STRING_CHANGED", //       = 130;
+        "SET_TOUCH_HIGHLIGHT_RECTS", //      = 131;
+        "SAVE_WEBARCHIVE_FINISHED", //       = 132;
+        "SET_AUTOFILLABLE", //               = 133;
+        "AUTOFILL_COMPLETE", //              = 134;
+        "SELECT_AT", //                      = 135;
+        "SCREEN_ON", //                      = 136;
+        "ENTER_FULLSCREEN_VIDEO", //         = 137;
+        "UPDATE_SELECTION", //               = 138;
+        "UPDATE_ZOOM_DENSITY" //             = 139;
+    };
+
+    // If the site doesn't use the viewport meta tag to specify the viewport,
+    // use DEFAULT_VIEWPORT_WIDTH as the default viewport width
+    static final int DEFAULT_VIEWPORT_WIDTH = 980;
+
+    // normally we try to fit the content to the minimum preferred width
+    // calculated by the Webkit. To avoid the bad behavior when some site's
+    // minimum preferred width keeps growing when changing the viewport width or
+    // the minimum preferred width is huge, an upper limit is needed.
+    static int sMaxViewportWidth = DEFAULT_VIEWPORT_WIDTH;
+
+    // initial scale in percent. 0 means using default.
+    private int mInitialScaleInPercent = 0;
+
+    // Whether or not a scroll event should be sent to webkit.  This is only set
+    // to false when restoring the scroll position.
+    private boolean mSendScrollEvent = true;
+
+    private int mSnapScrollMode = SNAP_NONE;
+    private static final int SNAP_NONE = 0;
+    private static final int SNAP_LOCK = 1; // not a separate state
+    private static final int SNAP_X = 2; // may be combined with SNAP_LOCK
+    private static final int SNAP_Y = 4; // may be combined with SNAP_LOCK
+    private boolean mSnapPositive;
+
+    // keep these in sync with their counterparts in WebView.cpp
+    private static final int DRAW_EXTRAS_NONE = 0;
+    private static final int DRAW_EXTRAS_SELECTION = 1;
+    private static final int DRAW_EXTRAS_CURSOR_RING = 2;
+
+    // keep this in sync with WebCore:ScrollbarMode in WebKit
+    private static final int SCROLLBAR_AUTO = 0;
+    private static final int SCROLLBAR_ALWAYSOFF = 1;
+    // as we auto fade scrollbar, this is ignored.
+    private static final int SCROLLBAR_ALWAYSON = 2;
+    private int mHorizontalScrollBarMode = SCROLLBAR_AUTO;
+    private int mVerticalScrollBarMode = SCROLLBAR_AUTO;
+
+    // constants for determining script injection strategy
+    private static final int ACCESSIBILITY_SCRIPT_INJECTION_UNDEFINED = -1;
+    private static final int ACCESSIBILITY_SCRIPT_INJECTION_OPTED_OUT = 0;
+    private static final int ACCESSIBILITY_SCRIPT_INJECTION_PROVIDED = 1;
+
+    // the alias via which accessibility JavaScript interface is exposed
+    private static final String ALIAS_ACCESSIBILITY_JS_INTERFACE = "accessibility";
+
+    // Template for JavaScript that injects a screen-reader.
+    private static final String ACCESSIBILITY_SCREEN_READER_JAVASCRIPT_TEMPLATE =
+        "javascript:(function() {" +
+        "    var chooser = document.createElement('script');" +
+        "    chooser.type = 'text/javascript';" +
+        "    chooser.src = '%1s';" +
+        "    document.getElementsByTagName('head')[0].appendChild(chooser);" +
+        "  })();";
+
+    // Regular expression that matches the "axs" URL parameter.
+    // The value of 0 means the accessibility script is opted out
+    // The value of 1 means the accessibility script is already injected
+    private static final String PATTERN_MATCH_AXS_URL_PARAMETER = "(\\?axs=(0|1))|(&axs=(0|1))";
+
+    // TextToSpeech instance exposed to JavaScript to the injected screenreader.
+    private TextToSpeech mTextToSpeech;
+
+    // variable to cache the above pattern in case accessibility is enabled.
+    private Pattern mMatchAxsUrlParameterPattern;
+
+    /**
+     * Max distance to overscroll by in pixels.
+     * This how far content can be pulled beyond its normal bounds by the user.
+     */
+    private int mOverscrollDistance;
+
+    /**
+     * Max distance to overfling by in pixels.
+     * This is how far flinged content can move beyond the end of its normal bounds.
+     */
+    private int mOverflingDistance;
+
+    private OverScrollGlow mOverScrollGlow;
+
+    // Used to match key downs and key ups
+    private Vector<Integer> mKeysPressed;
+
+    /* package */ static boolean mLogEvent = true;
+
+    // for event log
+    private long mLastTouchUpTime = 0;
+
+    private WebViewCore.AutoFillData mAutoFillData;
+
+    private static boolean sNotificationsEnabled = true;
+
+    /**
+     * URI scheme for telephone number
+     */
+    public static final String SCHEME_TEL = "tel:";
+    /**
+     * URI scheme for email address
+     */
+    public static final String SCHEME_MAILTO = "mailto:";
+    /**
+     * URI scheme for map address
+     */
+    public static final String SCHEME_GEO = "geo:0,0?q=";
+
+    private int mBackgroundColor = Color.WHITE;
+
+    private static final long SELECT_SCROLL_INTERVAL = 1000 / 60; // 60 / second
+    private int mAutoScrollX = 0;
+    private int mAutoScrollY = 0;
+    private int mMinAutoScrollX = 0;
+    private int mMaxAutoScrollX = 0;
+    private int mMinAutoScrollY = 0;
+    private int mMaxAutoScrollY = 0;
+    private Rect mScrollingLayerBounds = new Rect();
+    private boolean mSentAutoScrollMessage = false;
+
+    // used for serializing asynchronously handled touch events.
+    private final TouchEventQueue mTouchEventQueue = new TouchEventQueue();
+
+    // Used to track whether picture updating was paused due to a window focus change.
+    private boolean mPictureUpdatePausedForFocusChange = false;
+
+    // Used to notify listeners of a new picture.
+    private PictureListener mPictureListener;
+
+    /**
+     * Refer to {@link WebView#requestFocusNodeHref(Message)} for more information
+     */
+    static class FocusNodeHref {
+        static final String TITLE = "title";
+        static final String URL = "url";
+        static final String SRC = "src";
+    }
+
+    public WebViewClassic(WebView webView, WebView.PrivateAccess privateAccess) {
+        mWebView = webView;
+        mWebViewPrivate = privateAccess;
+        mContext = webView.getContext();
+    }
+
+    /**
+     * Construct a new WebView with layout parameters, a default style and a set
+     * of custom Javscript interfaces to be added to the WebView at initialization
+     * time. This guarantees that these interfaces will be available when the JS
+     * context is initialized.
+     * @param javaScriptInterfaces is a Map of interface names, as keys, and
+     * object implementing those interfaces, as values.
+     * @param privateBrowsing If true the web view will be initialized in private mode.
+     * @hide This is an implementation detail.
+     */
+    @Override
+    public void init(Map<String, Object> javaScriptInterfaces, boolean privateBrowsing) {
+        checkThread();
+
+        Context context = mContext;
+
+        // Used by the chrome stack to find application paths
+        JniUtil.setContext(context);
+
+        mCallbackProxy = new CallbackProxy(context, this);
+        mViewManager = new ViewManager(this);
+        L10nUtils.setApplicationContext(context.getApplicationContext());
+        mWebViewCore = new WebViewCore(context, this, mCallbackProxy, javaScriptInterfaces);
+        mDatabase = WebViewDatabase.getInstance(context);
+        mScroller = new OverScroller(context, null, 0, 0, false); //TODO Use OverScroller's flywheel
+        mZoomManager = new ZoomManager(this, mCallbackProxy);
+
+        /* The init method must follow the creation of certain member variables,
+         * such as the mZoomManager.
+         */
+        init();
+        setupPackageListener(context);
+        setupProxyListener(context);
+        setupTrustStorageListener(context);
+        updateMultiTouchSupport(context);
+
+        if (privateBrowsing) {
+            startPrivateBrowsing();
+        }
+
+        mAutoFillData = new WebViewCore.AutoFillData();
+    }
+
+    // === START: WebView Proxy binding ===
+    // Keep the webview proxy / SPI related stuff in this section, to minimize merge conflicts.
+
+    static class Factory implements WebViewFactoryProvider,  WebViewFactoryProvider.Statics {
+        @Override
+        public WebViewProvider createWebView(WebView webView, WebView.PrivateAccess privateAccess) {
+            return new WebViewClassic(webView, privateAccess);
+        }
+
+        @Override
+        public Statics getStatics() { return this; }
+
+        @Override
+        public String findAddress(String addr) {
+            return WebViewClassic.findAddress(addr);
+        }
+        @Override
+        public void setPlatformNotificationsEnabled(boolean enable) {
+            if (enable) {
+                WebViewClassic.enablePlatformNotifications();
+            } else {
+                WebViewClassic.disablePlatformNotifications();
+            }
+        }
+
+    }
+
+    // The webview that is bound to this WebViewClassic instance. Primarily needed for supplying
+    // as the first param in the WebViewClient and WebChromeClient callbacks.
+    final private WebView mWebView;
+    // Callback interface, provides priviledged access into the WebView instance.
+    final private WebView.PrivateAccess mWebViewPrivate;
+    // Cached reference to mWebView.getContext(), for convenience.
+    final private Context mContext;
+
+    /**
+     * @return The webview proxy that this classic webview is bound to.
+     */
+    public WebView getWebView() {
+        return mWebView;
+    }
+
+    @Override
+    public ViewDelegate getViewDelegate() {
+        return this;
+    }
+
+    @Override
+    public ScrollDelegate getScrollDelegate() {
+        return this;
+    }
+
+    public static WebViewClassic fromWebView(WebView webView) {
+        return webView == null ? null : (WebViewClassic) webView.getWebViewProvider();
+    }
+
+    // Accessors, purely for convenience (and to reduce code churn during webview proxy migration).
+    int getScrollX() {
+        return mWebView.getScrollX();
+    }
+
+    int getScrollY() {
+        return mWebView.getScrollY();
+    }
+
+    int getWidth() {
+        return mWebView.getWidth();
+    }
+
+    int getHeight() {
+        return mWebView.getHeight();
+    }
+
+    Context getContext() {
+        return mContext;
+    }
+
+    void invalidate() {
+        mWebView.invalidate();
+    }
+
+    // Setters for the Scroll X & Y, without invoking the onScrollChanged etc code paths.
+    void setScrollXRaw(int mScrollX) {
+        mWebViewPrivate.setScrollXRaw(mScrollX);
+    }
+
+    void setScrollYRaw(int mScrollY) {
+        mWebViewPrivate.setScrollYRaw(mScrollY);
+    }
+
+    // === END: WebView Proxy binding ===
+
+    private static class TrustStorageListener extends BroadcastReceiver {
+        @Override
+        public void onReceive(Context context, Intent intent) {
+            if (intent.getAction().equals(KeyChain.ACTION_STORAGE_CHANGED)) {
+                handleCertTrustChanged();
+            }
+        }
+    }
+    private static TrustStorageListener sTrustStorageListener;
+
+    /**
+     * Handles update to the trust storage.
+     */
+    private static void handleCertTrustChanged() {
+        // send a message for indicating trust storage change
+        WebViewCore.sendStaticMessage(EventHub.TRUST_STORAGE_UPDATED, null);
+    }
+
+    /*
+     * @param context This method expects this to be a valid context.
+     */
+    private static void setupTrustStorageListener(Context context) {
+        if (sTrustStorageListener != null ) {
+            return;
+        }
+        IntentFilter filter = new IntentFilter();
+        filter.addAction(KeyChain.ACTION_STORAGE_CHANGED);
+        sTrustStorageListener = new TrustStorageListener();
+        Intent current =
+            context.getApplicationContext().registerReceiver(sTrustStorageListener, filter);
+        if (current != null) {
+            handleCertTrustChanged();
+        }
+    }
+
+    private static class ProxyReceiver extends BroadcastReceiver {
+        @Override
+        public void onReceive(Context context, Intent intent) {
+            if (intent.getAction().equals(Proxy.PROXY_CHANGE_ACTION)) {
+                handleProxyBroadcast(intent);
+            }
+        }
+    }
+
+    /*
+     * Receiver for PROXY_CHANGE_ACTION, will be null when it is not added handling broadcasts.
+     */
+    private static ProxyReceiver sProxyReceiver;
+
+    /*
+     * @param context This method expects this to be a valid context
+     */
+    private static synchronized void setupProxyListener(Context context) {
+        if (sProxyReceiver != null || sNotificationsEnabled == false) {
+            return;
+        }
+        IntentFilter filter = new IntentFilter();
+        filter.addAction(Proxy.PROXY_CHANGE_ACTION);
+        sProxyReceiver = new ProxyReceiver();
+        Intent currentProxy = context.getApplicationContext().registerReceiver(
+                sProxyReceiver, filter);
+        if (currentProxy != null) {
+            handleProxyBroadcast(currentProxy);
+        }
+    }
+
+    /*
+     * @param context This method expects this to be a valid context
+     */
+    private static synchronized void disableProxyListener(Context context) {
+        if (sProxyReceiver == null)
+            return;
+
+        context.getApplicationContext().unregisterReceiver(sProxyReceiver);
+        sProxyReceiver = null;
+    }
+
+    private static void handleProxyBroadcast(Intent intent) {
+        ProxyProperties proxyProperties = (ProxyProperties)intent.getExtra(Proxy.EXTRA_PROXY_INFO);
+        if (proxyProperties == null || proxyProperties.getHost() == null) {
+            WebViewCore.sendStaticMessage(EventHub.PROXY_CHANGED, null);
+            return;
+        }
+        WebViewCore.sendStaticMessage(EventHub.PROXY_CHANGED, proxyProperties);
+    }
+
+    /*
+     * A variable to track if there is a receiver added for ACTION_PACKAGE_ADDED
+     * or ACTION_PACKAGE_REMOVED.
+     */
+    private static boolean sPackageInstallationReceiverAdded = false;
+
+    /*
+     * A set of Google packages we monitor for the
+     * navigator.isApplicationInstalled() API. Add additional packages as
+     * needed.
+     */
+    private static Set<String> sGoogleApps;
+    static {
+        sGoogleApps = new HashSet<String>();
+        sGoogleApps.add("com.google.android.youtube");
+    }
+
+    private static class PackageListener extends 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;
+            }
+
+            if (sGoogleApps.contains(packageName)) {
+                if (Intent.ACTION_PACKAGE_ADDED.equals(action)) {
+                    WebViewCore.sendStaticMessage(EventHub.ADD_PACKAGE_NAME, packageName);
+                } else {
+                    WebViewCore.sendStaticMessage(EventHub.REMOVE_PACKAGE_NAME, packageName);
+                }
+            }
+
+            PluginManager pm = PluginManager.getInstance(context);
+            if (pm.containsPluginPermissionAndSignatures(packageName)) {
+                pm.refreshPlugins(Intent.ACTION_PACKAGE_ADDED.equals(action));
+            }
+        }
+    }
+
+    private void setupPackageListener(Context context) {
+
+        /*
+         * we must synchronize the instance check and the creation of the
+         * receiver to ensure that only ONE receiver exists for all WebView
+         * instances.
+         */
+        synchronized (WebViewClassic.class) {
+
+            // if the receiver already exists then we do not need to register it
+            // again
+            if (sPackageInstallationReceiverAdded) {
+                return;
+            }
+
+            IntentFilter filter = new IntentFilter(Intent.ACTION_PACKAGE_ADDED);
+            filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
+            filter.addDataScheme("package");
+            BroadcastReceiver packageListener = new PackageListener();
+            context.getApplicationContext().registerReceiver(packageListener, filter);
+            sPackageInstallationReceiverAdded = true;
+        }
+
+        // check if any of the monitored apps are already installed
+        AsyncTask<Void, Void, Set<String>> task = new AsyncTask<Void, Void, Set<String>>() {
+
+            @Override
+            protected Set<String> doInBackground(Void... unused) {
+                Set<String> installedPackages = new HashSet<String>();
+                PackageManager pm = mContext.getPackageManager();
+                for (String name : sGoogleApps) {
+                    try {
+                        pm.getPackageInfo(name,
+                                PackageManager.GET_ACTIVITIES | PackageManager.GET_SERVICES);
+                        installedPackages.add(name);
+                    } catch (PackageManager.NameNotFoundException e) {
+                        // package not found
+                    }
+                }
+                return installedPackages;
+            }
+
+            // Executes on the UI thread
+            @Override
+            protected void onPostExecute(Set<String> installedPackages) {
+                if (mWebViewCore != null) {
+                    mWebViewCore.sendMessage(EventHub.ADD_PACKAGE_NAMES, installedPackages);
+                }
+            }
+        };
+        task.execute();
+    }
+
+    void updateMultiTouchSupport(Context context) {
+        mZoomManager.updateMultiTouchSupport(context);
+    }
+
+    private void init() {
+        OnTrimMemoryListener.init(mContext);
+        mWebView.setWillNotDraw(false);
+        mWebView.setFocusable(true);
+        mWebView.setFocusableInTouchMode(true);
+        mWebView.setClickable(true);
+        mWebView.setLongClickable(true);
+
+        final ViewConfiguration configuration = ViewConfiguration.get(mContext);
+        int slop = configuration.getScaledTouchSlop();
+        mTouchSlopSquare = slop * slop;
+        slop = configuration.getScaledDoubleTapSlop();
+        mDoubleTapSlopSquare = slop * slop;
+        final float density = mContext.getResources().getDisplayMetrics().density;
+        // use one line height, 16 based on our current default font, for how
+        // far we allow a touch be away from the edge of a link
+        mNavSlop = (int) (16 * density);
+        mZoomManager.init(density);
+        mMaximumFling = configuration.getScaledMaximumFlingVelocity();
+
+        // Compute the inverse of the density squared.
+        DRAG_LAYER_INVERSE_DENSITY_SQUARED = 1 / (density * density);
+
+        mOverscrollDistance = configuration.getScaledOverscrollDistance();
+        mOverflingDistance = configuration.getScaledOverflingDistance();
+
+        setScrollBarStyle(mWebViewPrivate.super_getScrollBarStyle());
+        // Initially use a size of two, since the user is likely to only hold
+        // down two keys at a time (shift + another key)
+        mKeysPressed = new Vector<Integer>(2);
+        mHTML5VideoViewProxy = null ;
+    }
+
+    @Override
+    public boolean shouldDelayChildPressedState() {
+        return true;
+    }
+
+    /**
+     * Adds accessibility APIs to JavaScript.
+     *
+     * Note: This method is responsible to performing the necessary
+     *       check if the accessibility APIs should be exposed.
+     */
+    private void addAccessibilityApisToJavaScript() {
+        if (AccessibilityManager.getInstance(mContext).isEnabled()
+                && getSettings().getJavaScriptEnabled()) {
+            // exposing the TTS for now ...
+            final Context ctx = mContext;
+            if (ctx != null) {
+                final String packageName = ctx.getPackageName();
+                if (packageName != null) {
+                    mTextToSpeech = new TextToSpeech(ctx, null, null,
+                            packageName + ".**webview**", true);
+                    addJavascriptInterface(mTextToSpeech, ALIAS_ACCESSIBILITY_JS_INTERFACE);
+                }
+            }
+        }
+    }
+
+    /**
+     * Removes accessibility APIs from JavaScript.
+     */
+    private void removeAccessibilityApisFromJavaScript() {
+        // exposing the TTS for now ...
+        if (mTextToSpeech != null) {
+            removeJavascriptInterface(ALIAS_ACCESSIBILITY_JS_INTERFACE);
+            mTextToSpeech.shutdown();
+            mTextToSpeech = null;
+        }
+    }
+
+    @Override
+    public void onInitializeAccessibilityNodeInfo(AccessibilityNodeInfo info) {
+        info.setScrollable(isScrollableForAccessibility());
+    }
+
+    @Override
+    public void onInitializeAccessibilityEvent(AccessibilityEvent event) {
+        event.setScrollable(isScrollableForAccessibility());
+        event.setScrollX(getScrollX());
+        event.setScrollY(getScrollY());
+        final int convertedContentWidth = contentToViewX(getContentWidth());
+        final int adjustedViewWidth = getWidth() - mWebView.getPaddingLeft()
+                - mWebView.getPaddingLeft();
+        event.setMaxScrollX(Math.max(convertedContentWidth - adjustedViewWidth, 0));
+        final int convertedContentHeight = contentToViewY(getContentHeight());
+        final int adjustedViewHeight = getHeight() - mWebView.getPaddingTop()
+                - mWebView.getPaddingBottom();
+        event.setMaxScrollY(Math.max(convertedContentHeight - adjustedViewHeight, 0));
+    }
+
+    private boolean isScrollableForAccessibility() {
+        return (contentToViewX(getContentWidth()) > getWidth() - mWebView.getPaddingLeft()
+                - mWebView.getPaddingRight()
+                || contentToViewY(getContentHeight()) > getHeight() - mWebView.getPaddingTop()
+                - mWebView.getPaddingBottom());
+    }
+
+    @Override
+    public void setOverScrollMode(int mode) {
+        if (mode != View.OVER_SCROLL_NEVER) {
+            if (mOverScrollGlow == null) {
+                mOverScrollGlow = new OverScrollGlow(this);
+            }
+        } else {
+            mOverScrollGlow = null;
+        }
+    }
+
+    /* package */ void adjustDefaultZoomDensity(int zoomDensity) {
+        final float density = mContext.getResources().getDisplayMetrics().density
+                * 100 / zoomDensity;
+        updateDefaultZoomDensity(density);
+    }
+
+    /* package */ void updateDefaultZoomDensity(float density) {
+        mNavSlop = (int) (16 * density);
+        mZoomManager.updateDefaultZoomDensity(density);
+    }
+
+    /* package */ boolean onSavePassword(String schemePlusHost, String username,
+            String password, final Message resumeMsg) {
+       boolean rVal = false;
+       if (resumeMsg == null) {
+           // null resumeMsg implies saving password silently
+           mDatabase.setUsernamePassword(schemePlusHost, username, password);
+       } else {
+            final Message remember = mPrivateHandler.obtainMessage(
+                    REMEMBER_PASSWORD);
+            remember.getData().putString("host", schemePlusHost);
+            remember.getData().putString("username", username);
+            remember.getData().putString("password", password);
+            remember.obj = resumeMsg;
+
+            final Message neverRemember = mPrivateHandler.obtainMessage(
+                    NEVER_REMEMBER_PASSWORD);
+            neverRemember.getData().putString("host", schemePlusHost);
+            neverRemember.getData().putString("username", username);
+            neverRemember.getData().putString("password", password);
+            neverRemember.obj = resumeMsg;
+
+            new AlertDialog.Builder(mContext)
+                    .setTitle(com.android.internal.R.string.save_password_label)
+                    .setMessage(com.android.internal.R.string.save_password_message)
+                    .setPositiveButton(com.android.internal.R.string.save_password_notnow,
+                    new DialogInterface.OnClickListener() {
+                        @Override
+                        public void onClick(DialogInterface dialog, int which) {
+                            resumeMsg.sendToTarget();
+                        }
+                    })
+                    .setNeutralButton(com.android.internal.R.string.save_password_remember,
+                    new DialogInterface.OnClickListener() {
+                        @Override
+                        public void onClick(DialogInterface dialog, int which) {
+                            remember.sendToTarget();
+                        }
+                    })
+                    .setNegativeButton(com.android.internal.R.string.save_password_never,
+                    new DialogInterface.OnClickListener() {
+                        @Override
+                        public void onClick(DialogInterface dialog, int which) {
+                            neverRemember.sendToTarget();
+                        }
+                    })
+                    .setOnCancelListener(new OnCancelListener() {
+                        @Override
+                        public void onCancel(DialogInterface dialog) {
+                            resumeMsg.sendToTarget();
+                        }
+                    }).show();
+            // Return true so that WebViewCore will pause while the dialog is
+            // up.
+            rVal = true;
+        }
+       return rVal;
+    }
+
+    @Override
+    public void setScrollBarStyle(int style) {
+        if (style == View.SCROLLBARS_INSIDE_INSET
+                || style == View.SCROLLBARS_OUTSIDE_INSET) {
+            mOverlayHorizontalScrollbar = mOverlayVerticalScrollbar = false;
+        } else {
+            mOverlayHorizontalScrollbar = mOverlayVerticalScrollbar = true;
+        }
+    }
+
+    /**
+     * Specify whether the horizontal scrollbar has overlay style.
+     * @param overlay TRUE if horizontal scrollbar should have overlay style.
+     */
+    public void setHorizontalScrollbarOverlay(boolean overlay) {
+        checkThread();
+        mOverlayHorizontalScrollbar = overlay;
+    }
+
+    /**
+     * Specify whether the vertical scrollbar has overlay style.
+     * @param overlay TRUE if vertical scrollbar should have overlay style.
+     */
+    public void setVerticalScrollbarOverlay(boolean overlay) {
+        checkThread();
+        mOverlayVerticalScrollbar = overlay;
+    }
+
+    /**
+     * Return whether horizontal scrollbar has overlay style
+     * @return TRUE if horizontal scrollbar has overlay style.
+     */
+    public boolean overlayHorizontalScrollbar() {
+        checkThread();
+        return mOverlayHorizontalScrollbar;
+    }
+
+    /**
+     * Return whether vertical scrollbar has overlay style
+     * @return TRUE if vertical scrollbar has overlay style.
+     */
+    public boolean overlayVerticalScrollbar() {
+        checkThread();
+        return mOverlayVerticalScrollbar;
+    }
+
+    /*
+     * Return the width of the view where the content of WebView should render
+     * to.
+     * Note: this can be called from WebCoreThread.
+     */
+    /* package */ int getViewWidth() {
+        if (!mWebView.isVerticalScrollBarEnabled() || mOverlayVerticalScrollbar) {
+            return getWidth();
+        } else {
+            return Math.max(0, getWidth() - mWebView.getVerticalScrollbarWidth());
+        }
+    }
+
+    // Interface to enable the browser to override title bar handling.
+    public interface TitleBarDelegate {
+        int getTitleHeight();
+        public void onSetEmbeddedTitleBar(final View title);
+    }
+
+    /**
+     * Returns the height (in pixels) of the embedded title bar (if any). Does not care about
+     * scrolling
+     * @hide
+     */
+    protected int getTitleHeight() {
+        if (mWebView instanceof TitleBarDelegate) {
+            return ((TitleBarDelegate) mWebView).getTitleHeight();
+        }
+        return mTitleBar != null ? mTitleBar.getHeight() : 0;
+    }
+
+    /**
+     * Return the visible height (in pixels) of the embedded title bar (if any).
+     *
+     * @return This method is obsolete and always returns 0.
+     * @deprecated This method is now obsolete.
+     */
+    @Deprecated
+    public int getVisibleTitleHeight() {
+        // Actually, this method returns the height of the embedded title bar if one is set via the
+        // hidden setEmbeddedTitleBar method.
+        checkThread();
+        return getVisibleTitleHeightImpl();
+    }
+
+    private int getVisibleTitleHeightImpl() {
+        // need to restrict mScrollY due to over scroll
+        return Math.max(getTitleHeight() - Math.max(0, getScrollY()),
+                getOverlappingActionModeHeight());
+    }
+
+    private int mCachedOverlappingActionModeHeight = -1;
+
+    private int getOverlappingActionModeHeight() {
+        if (mFindCallback == null) {
+            return 0;
+        }
+        if (mCachedOverlappingActionModeHeight < 0) {
+            mWebView.getGlobalVisibleRect(mGlobalVisibleRect, mGlobalVisibleOffset);
+            mCachedOverlappingActionModeHeight = Math.max(0,
+                    mFindCallback.getActionModeGlobalBottom() - mGlobalVisibleRect.top);
+        }
+        return mCachedOverlappingActionModeHeight;
+    }
+
+    /*
+     * Return the height of the view where the content of WebView should render
+     * to.  Note that this excludes mTitleBar, if there is one.
+     * Note: this can be called from WebCoreThread.
+     */
+    /* package */ int getViewHeight() {
+        return getViewHeightWithTitle() - getVisibleTitleHeightImpl();
+    }
+
+    int getViewHeightWithTitle() {
+        int height = getHeight();
+        if (mWebView.isHorizontalScrollBarEnabled() && !mOverlayHorizontalScrollbar) {
+            height -= mWebViewPrivate.getHorizontalScrollbarHeight();
+        }
+        return height;
+    }
+
+    /**
+     * @return The SSL certificate for the main top-level page or null if
+     * there is no certificate (the site is not secure).
+     */
+    public SslCertificate getCertificate() {
+        checkThread();
+        return mCertificate;
+    }
+
+    /**
+     * Sets the SSL certificate for the main top-level page.
+     */
+    public void setCertificate(SslCertificate certificate) {
+        checkThread();
+        if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, "setCertificate=" + certificate);
+        }
+        // here, the certificate can be null (if the site is not secure)
+        mCertificate = certificate;
+    }
+
+    //-------------------------------------------------------------------------
+    // Methods called by activity
+    //-------------------------------------------------------------------------
+
+    /**
+     * Save the username and password for a particular host in the WebView's
+     * internal database.
+     * @param host The host that required the credentials.
+     * @param username The username for the given host.
+     * @param password The password for the given host.
+     */
+    public void savePassword(String host, String username, String password) {
+        checkThread();
+        mDatabase.setUsernamePassword(host, username, password);
+    }
+
+    /**
+     * Set the HTTP authentication credentials for a given host and realm.
+     *
+     * @param host The host for the credentials.
+     * @param realm The realm for the credentials.
+     * @param username The username for the password. If it is null, it means
+     *                 password can't be saved.
+     * @param password The password
+     */
+    public void setHttpAuthUsernamePassword(String host, String realm,
+            String username, String password) {
+        checkThread();
+        mDatabase.setHttpAuthUsernamePassword(host, realm, username, password);
+    }
+
+    /**
+     * Retrieve the HTTP authentication username and password for a given
+     * host & realm pair
+     *
+     * @param host The host for which the credentials apply.
+     * @param realm The realm for which the credentials apply.
+     * @return String[] if found, String[0] is username, which can be null and
+     *         String[1] is password. Return null if it can't find anything.
+     */
+    public String[] getHttpAuthUsernamePassword(String host, String realm) {
+        checkThread();
+        return mDatabase.getHttpAuthUsernamePassword(host, realm);
+    }
+
+    /**
+     * Remove Find or Select ActionModes, if active.
+     */
+    private void clearActionModes() {
+        if (mSelectCallback != null) {
+            mSelectCallback.finish();
+        }
+        if (mFindCallback != null) {
+            mFindCallback.finish();
+        }
+    }
+
+    /**
+     * Called to clear state when moving from one page to another, or changing
+     * in some other way that makes elements associated with the current page
+     * (such as ActionModes) no longer relevant.
+     */
+    private void clearHelpers() {
+        hideSoftKeyboard();
+        clearActionModes();
+        dismissFullScreenMode();
+        cancelSelectDialog();
+    }
+
+    private void cancelSelectDialog() {
+        if (mListBoxDialog != null) {
+            mListBoxDialog.cancel();
+            mListBoxDialog = null;
+        }
+    }
+
+    /**
+     * Destroy the internal state of the WebView. This method should be called
+     * after the WebView has been removed from the view system. No other
+     * methods may be called on a WebView after destroy.
+     */
+    public void destroy() {
+        checkThread();
+        destroyImpl();
+    }
+
+    private void destroyImpl() {
+        clearHelpers();
+        if (mListBoxDialog != null) {
+            mListBoxDialog.dismiss();
+            mListBoxDialog = null;
+        }
+        if (mNativeClass != 0) nativeStopGL();
+        if (mWebViewCore != null) {
+            // Tell WebViewCore to destroy itself
+            synchronized (this) {
+                WebViewCore webViewCore = mWebViewCore;
+                mWebViewCore = null; // prevent using partial webViewCore
+                webViewCore.destroy();
+            }
+            // Remove any pending messages that might not be serviced yet.
+            mPrivateHandler.removeCallbacksAndMessages(null);
+        }
+        if (mNativeClass != 0) {
+            nativeDestroy();
+            mNativeClass = 0;
+        }
+    }
+
+    /**
+     * Enables platform notifications of data state and proxy changes.
+     * Notifications are enabled by default.
+     *
+     * @deprecated This method is now obsolete.
+     */
+    @Deprecated
+    public static void enablePlatformNotifications() {
+        checkThread();
+        synchronized (WebViewClassic.class) {
+            sNotificationsEnabled = true;
+            Context context = JniUtil.getContext();
+            if (context != null)
+                setupProxyListener(context);
+        }
+    }
+
+    /**
+     * Disables platform notifications of data state and proxy changes.
+     * Notifications are enabled by default.
+     *
+     * @deprecated This method is now obsolete.
+     */
+    @Deprecated
+    public static void disablePlatformNotifications() {
+        checkThread();
+        synchronized (WebViewClassic.class) {
+            sNotificationsEnabled = false;
+            Context context = JniUtil.getContext();
+            if (context != null)
+                disableProxyListener(context);
+        }
+    }
+
+    /**
+     * Sets JavaScript engine flags.
+     *
+     * @param flags JS engine flags in a String
+     *
+     * @hide This is an implementation detail.
+     */
+    public void setJsFlags(String flags) {
+        checkThread();
+        mWebViewCore.sendMessage(EventHub.SET_JS_FLAGS, flags);
+    }
+
+    /**
+     * Inform WebView of the network state. This is used to set
+     * the JavaScript property window.navigator.isOnline and
+     * generates the online/offline event as specified in HTML5, sec. 5.7.7
+     * @param networkUp boolean indicating if network is available
+     */
+    public void setNetworkAvailable(boolean networkUp) {
+        checkThread();
+        mWebViewCore.sendMessage(EventHub.SET_NETWORK_STATE,
+                networkUp ? 1 : 0, 0);
+    }
+
+    /**
+     * Inform WebView about the current network type.
+     * {@hide}
+     */
+    public void setNetworkType(String type, String subtype) {
+        checkThread();
+        Map<String, String> map = new HashMap<String, String>();
+        map.put("type", type);
+        map.put("subtype", subtype);
+        mWebViewCore.sendMessage(EventHub.SET_NETWORK_TYPE, map);
+    }
+    /**
+     * Save the state of this WebView used in
+     * {@link android.app.Activity#onSaveInstanceState}. Please note that this
+     * method no longer stores the display data for this WebView. The previous
+     * behavior could potentially leak files if {@link #restoreState} was never
+     * called. See {@link #savePicture} and {@link #restorePicture} for saving
+     * and restoring the display data.
+     * @param outState The Bundle to store the WebView state.
+     * @return The same copy of the back/forward list used to save the state. If
+     *         saveState fails, the returned list will be null.
+     * @see #savePicture
+     * @see #restorePicture
+     */
+    public WebBackForwardList saveState(Bundle outState) {
+        checkThread();
+        if (outState == null) {
+            return null;
+        }
+        // We grab a copy of the back/forward list because a client of WebView
+        // may have invalidated the history list by calling clearHistory.
+        WebBackForwardList list = copyBackForwardList();
+        final int currentIndex = list.getCurrentIndex();
+        final int size = list.getSize();
+        // We should fail saving the state if the list is empty or the index is
+        // not in a valid range.
+        if (currentIndex < 0 || currentIndex >= size || size == 0) {
+            return null;
+        }
+        outState.putInt("index", currentIndex);
+        // FIXME: This should just be a byte[][] instead of ArrayList but
+        // Parcel.java does not have the code to handle multi-dimensional
+        // arrays.
+        ArrayList<byte[]> history = new ArrayList<byte[]>(size);
+        for (int i = 0; i < size; i++) {
+            WebHistoryItem item = list.getItemAtIndex(i);
+            if (null == item) {
+                // FIXME: this shouldn't happen
+                // need to determine how item got set to null
+                Log.w(LOGTAG, "saveState: Unexpected null history item.");
+                return null;
+            }
+            byte[] data = item.getFlattenedData();
+            if (data == null) {
+                // It would be very odd to not have any data for a given history
+                // item. And we will fail to rebuild the history list without
+                // flattened data.
+                return null;
+            }
+            history.add(data);
+        }
+        outState.putSerializable("history", history);
+        if (mCertificate != null) {
+            outState.putBundle("certificate",
+                               SslCertificate.saveState(mCertificate));
+        }
+        outState.putBoolean("privateBrowsingEnabled", isPrivateBrowsingEnabled());
+        mZoomManager.saveZoomState(outState);
+        return list;
+    }
+
+    /**
+     * Save the current display data to the Bundle given. Used in conjunction
+     * with {@link #saveState}.
+     * @param b A Bundle to store the display data.
+     * @param dest The file to store the serialized picture data. Will be
+     *             overwritten with this WebView's picture data.
+     * @return True if the picture was successfully saved.
+     * @deprecated This method is now obsolete.
+     */
+    @Deprecated
+    public boolean savePicture(Bundle b, final File dest) {
+        checkThread();
+        if (dest == null || b == null) {
+            return false;
+        }
+        final Picture p = capturePicture();
+        // Use a temporary file while writing to ensure the destination file
+        // contains valid data.
+        final File temp = new File(dest.getPath() + ".writing");
+        new Thread(new Runnable() {
+            @Override
+            public void run() {
+                FileOutputStream out = null;
+                try {
+                    out = new FileOutputStream(temp);
+                    p.writeToStream(out);
+                    // Writing the picture succeeded, rename the temporary file
+                    // to the destination.
+                    temp.renameTo(dest);
+                } catch (Exception e) {
+                    // too late to do anything about it.
+                } finally {
+                    if (out != null) {
+                        try {
+                            out.close();
+                        } catch (Exception e) {
+                            // Can't do anything about that
+                        }
+                    }
+                    temp.delete();
+                }
+            }
+        }).start();
+        // now update the bundle
+        b.putInt("scrollX", getScrollX());
+        b.putInt("scrollY", getScrollY());
+        mZoomManager.saveZoomState(b);
+        return true;
+    }
+
+    private void restoreHistoryPictureFields(Picture p, Bundle b) {
+        int sx = b.getInt("scrollX", 0);
+        int sy = b.getInt("scrollY", 0);
+
+        mDrawHistory = true;
+        mHistoryPicture = p;
+
+        setScrollXRaw(sx);
+        setScrollYRaw(sy);
+        mZoomManager.restoreZoomState(b);
+        final float scale = mZoomManager.getScale();
+        mHistoryWidth = Math.round(p.getWidth() * scale);
+        mHistoryHeight = Math.round(p.getHeight() * scale);
+
+        invalidate();
+    }
+
+    /**
+     * Restore the display data that was save in {@link #savePicture}. Used in
+     * conjunction with {@link #restoreState}.
+     *
+     * Note that this will not work if the WebView is hardware accelerated.
+     * @param b A Bundle containing the saved display data.
+     * @param src The file where the picture data was stored.
+     * @return True if the picture was successfully restored.
+     * @deprecated This method is now obsolete.
+     */
+    @Deprecated
+    public boolean restorePicture(Bundle b, File src) {
+        checkThread();
+        if (src == null || b == null) {
+            return false;
+        }
+        if (!src.exists()) {
+            return false;
+        }
+        try {
+            final FileInputStream in = new FileInputStream(src);
+            final Bundle copy = new Bundle(b);
+            new Thread(new Runnable() {
+                @Override
+                public void run() {
+                    try {
+                        final Picture p = Picture.createFromStream(in);
+                        if (p != null) {
+                            // Post a runnable on the main thread to update the
+                            // history picture fields.
+                            mPrivateHandler.post(new Runnable() {
+                                @Override
+                                public void run() {
+                                    restoreHistoryPictureFields(p, copy);
+                                }
+                            });
+                        }
+                    } finally {
+                        try {
+                            in.close();
+                        } catch (Exception e) {
+                            // Nothing we can do now.
+                        }
+                    }
+                }
+            }).start();
+        } catch (FileNotFoundException e){
+            e.printStackTrace();
+        }
+        return true;
+    }
+
+    /**
+     * Saves the view data to the output stream. The output is highly
+     * version specific, and may not be able to be loaded by newer versions
+     * of WebView.
+     * @param stream The {@link OutputStream} to save to
+     * @return True if saved successfully
+     * @hide
+     */
+    public boolean saveViewState(OutputStream stream) {
+        try {
+            return ViewStateSerializer.serializeViewState(stream, this);
+        } catch (IOException e) {
+            Log.w(LOGTAG, "Failed to saveViewState", e);
+        }
+        return false;
+    }
+
+    /**
+     * Loads the view data from the input stream. See
+     * {@link #saveViewState(OutputStream)} for more information.
+     * @param stream The {@link InputStream} to load from
+     * @return True if loaded successfully
+     * @hide
+     */
+    public boolean loadViewState(InputStream stream) {
+        try {
+            mLoadedPicture = ViewStateSerializer.deserializeViewState(stream, this);
+            mBlockWebkitViewMessages = true;
+            setNewPicture(mLoadedPicture, true);
+            mLoadedPicture.mViewState = null;
+            return true;
+        } catch (IOException e) {
+            Log.w(LOGTAG, "Failed to loadViewState", e);
+        }
+        return false;
+    }
+
+    /**
+     * Clears the view state set with {@link #loadViewState(InputStream)}.
+     * This WebView will then switch to showing the content from webkit
+     * @hide
+     */
+    public void clearViewState() {
+        mBlockWebkitViewMessages = false;
+        mLoadedPicture = null;
+        invalidate();
+    }
+
+    /**
+     * Restore the state of this WebView from the given map used in
+     * {@link android.app.Activity#onRestoreInstanceState}. This method should
+     * be called to restore the state of the WebView before using the object. If
+     * it is called after the WebView has had a chance to build state (load
+     * pages, create a back/forward list, etc.) there may be undesirable
+     * side-effects. Please note that this method no longer restores the
+     * display data for this WebView. See {@link #savePicture} and {@link
+     * #restorePicture} for saving and restoring the display data.
+     * @param inState The incoming Bundle of state.
+     * @return The restored back/forward list or null if restoreState failed.
+     * @see #savePicture
+     * @see #restorePicture
+     */
+    public WebBackForwardList restoreState(Bundle inState) {
+        checkThread();
+        WebBackForwardList returnList = null;
+        if (inState == null) {
+            return returnList;
+        }
+        if (inState.containsKey("index") && inState.containsKey("history")) {
+            mCertificate = SslCertificate.restoreState(
+                inState.getBundle("certificate"));
+
+            final WebBackForwardList list = mCallbackProxy.getBackForwardList();
+            final int index = inState.getInt("index");
+            // We can't use a clone of the list because we need to modify the
+            // shared copy, so synchronize instead to prevent concurrent
+            // modifications.
+            synchronized (list) {
+                final List<byte[]> history =
+                        (List<byte[]>) inState.getSerializable("history");
+                final int size = history.size();
+                // Check the index bounds so we don't crash in native code while
+                // restoring the history index.
+                if (index < 0 || index >= size) {
+                    return null;
+                }
+                for (int i = 0; i < size; i++) {
+                    byte[] data = history.remove(0);
+                    if (data == null) {
+                        // If we somehow have null data, we cannot reconstruct
+                        // the item and thus our history list cannot be rebuilt.
+                        return null;
+                    }
+                    WebHistoryItem item = new WebHistoryItem(data);
+                    list.addHistoryItem(item);
+                }
+                // Grab the most recent copy to return to the caller.
+                returnList = copyBackForwardList();
+                // Update the copy to have the correct index.
+                returnList.setCurrentIndex(index);
+            }
+            // Restore private browsing setting.
+            if (inState.getBoolean("privateBrowsingEnabled")) {
+                getSettings().setPrivateBrowsingEnabled(true);
+            }
+            mZoomManager.restoreZoomState(inState);
+            // Remove all pending messages because we are restoring previous
+            // state.
+            mWebViewCore.removeMessages();
+            // Send a restore state message.
+            mWebViewCore.sendMessage(EventHub.RESTORE_STATE, index);
+        }
+        return returnList;
+    }
+
+    /**
+     * Load the given URL with the specified additional HTTP headers.
+     * @param url The URL of the resource to load.
+     * @param additionalHttpHeaders The additional headers to be used in the
+     *            HTTP request for this URL, specified as a map from name to
+     *            value. Note that if this map contains any of the headers
+     *            that are set by default by the WebView, such as those
+     *            controlling caching, accept types or the User-Agent, their
+     *            values may be overriden by the WebView's defaults.
+     */
+    public void loadUrl(String url, Map<String, String> additionalHttpHeaders) {
+        checkThread();
+        loadUrlImpl(url, additionalHttpHeaders);
+    }
+
+    private void loadUrlImpl(String url, Map<String, String> extraHeaders) {
+        switchOutDrawHistory();
+        WebViewCore.GetUrlData arg = new WebViewCore.GetUrlData();
+        arg.mUrl = url;
+        arg.mExtraHeaders = extraHeaders;
+        mWebViewCore.sendMessage(EventHub.LOAD_URL, arg);
+        clearHelpers();
+    }
+
+    /**
+     * Load the given URL.
+     * @param url The URL of the resource to load.
+     */
+    public void loadUrl(String url) {
+        checkThread();
+        loadUrlImpl(url);
+    }
+
+    private void loadUrlImpl(String url) {
+        if (url == null) {
+            return;
+        }
+        loadUrlImpl(url, null);
+    }
+
+    /**
+     * Load the url with postData using "POST" method into the WebView. If url
+     * is not a network url, it will be loaded with {link
+     * {@link #loadUrl(String)} instead.
+     *
+     * @param url The url of the resource to load.
+     * @param postData The data will be passed to "POST" request.
+     */
+    public void postUrl(String url, byte[] postData) {
+        checkThread();
+        if (URLUtil.isNetworkUrl(url)) {
+            switchOutDrawHistory();
+            WebViewCore.PostUrlData arg = new WebViewCore.PostUrlData();
+            arg.mUrl = url;
+            arg.mPostData = postData;
+            mWebViewCore.sendMessage(EventHub.POST_URL, arg);
+            clearHelpers();
+        } else {
+            loadUrlImpl(url);
+        }
+    }
+
+    /**
+     * Load the given data into the WebView using a 'data' scheme URL.
+     * <p>
+     * Note that JavaScript's same origin policy means that script running in a
+     * page loaded using this method will be unable to access content loaded
+     * using any scheme other than 'data', including 'http(s)'. To avoid this
+     * restriction, use {@link
+     * #loadDataWithBaseURL(String,String,String,String,String)
+     * loadDataWithBaseURL()} with an appropriate base URL.
+     * <p>
+     * If the value of the encoding parameter is 'base64', then the data must
+     * be encoded as base64. Otherwise, the data must use ASCII encoding for
+     * octets inside the range of safe URL characters and use the standard %xx
+     * hex encoding of URLs for octets outside that range. For example,
+     * '#', '%', '\', '?' should be replaced by %23, %25, %27, %3f respectively.
+     * <p>
+     * The 'data' scheme URL formed by this method uses the default US-ASCII
+     * charset. If you need need to set a different charset, you should form a
+     * 'data' scheme URL which explicitly specifies a charset parameter in the
+     * mediatype portion of the URL and call {@link #loadUrl(String)} instead.
+     * Note that the charset obtained from the mediatype portion of a data URL
+     * always overrides that specified in the HTML or XML document itself.
+     * @param data A String of data in the given encoding.
+     * @param mimeType The MIME type of the data, e.g. 'text/html'.
+     * @param encoding The encoding of the data.
+     */
+    public void loadData(String data, String mimeType, String encoding) {
+        checkThread();
+        loadDataImpl(data, mimeType, encoding);
+    }
+
+    private void loadDataImpl(String data, String mimeType, String encoding) {
+        StringBuilder dataUrl = new StringBuilder("data:");
+        dataUrl.append(mimeType);
+        if ("base64".equals(encoding)) {
+            dataUrl.append(";base64");
+        }
+        dataUrl.append(",");
+        dataUrl.append(data);
+        loadUrlImpl(dataUrl.toString());
+    }
+
+    /**
+     * Load the given data into the WebView, using baseUrl as the base URL for
+     * the content. The base URL is used both to resolve relative URLs and when
+     * applying JavaScript's same origin policy. The historyUrl is used for the
+     * history entry.
+     * <p>
+     * Note that content specified in this way can access local device files
+     * (via 'file' scheme URLs) only if baseUrl specifies a scheme other than
+     * 'http', 'https', 'ftp', 'ftps', 'about' or 'javascript'.
+     * <p>
+     * If the base URL uses the data scheme, this method is equivalent to
+     * calling {@link #loadData(String,String,String) loadData()} and the
+     * historyUrl is ignored.
+     * @param baseUrl URL to use as the page's base URL. If null defaults to
+     *            'about:blank'
+     * @param data A String of data in the given encoding.
+     * @param mimeType The MIMEType of the data, e.g. 'text/html'. If null,
+     *            defaults to 'text/html'.
+     * @param encoding The encoding of the data.
+     * @param historyUrl URL to use as the history entry, if null defaults to
+     *            'about:blank'.
+     */
+    public void loadDataWithBaseURL(String baseUrl, String data,
+            String mimeType, String encoding, String historyUrl) {
+        checkThread();
+
+        if (baseUrl != null && baseUrl.toLowerCase().startsWith("data:")) {
+            loadDataImpl(data, mimeType, encoding);
+            return;
+        }
+        switchOutDrawHistory();
+        WebViewCore.BaseUrlData arg = new WebViewCore.BaseUrlData();
+        arg.mBaseUrl = baseUrl;
+        arg.mData = data;
+        arg.mMimeType = mimeType;
+        arg.mEncoding = encoding;
+        arg.mHistoryUrl = historyUrl;
+        mWebViewCore.sendMessage(EventHub.LOAD_DATA, arg);
+        clearHelpers();
+    }
+
+    /**
+     * Saves the current view as a web archive.
+     *
+     * @param filename The filename where the archive should be placed.
+     */
+    public void saveWebArchive(String filename) {
+        checkThread();
+        saveWebArchiveImpl(filename, false, null);
+    }
+
+    /* package */ static class SaveWebArchiveMessage {
+        SaveWebArchiveMessage (String basename, boolean autoname, ValueCallback<String> callback) {
+            mBasename = basename;
+            mAutoname = autoname;
+            mCallback = callback;
+        }
+
+        /* package */ final String mBasename;
+        /* package */ final boolean mAutoname;
+        /* package */ final ValueCallback<String> mCallback;
+        /* package */ String mResultFile;
+    }
+
+    /**
+     * Saves the current view as a web archive.
+     *
+     * @param basename The filename where the archive should be placed.
+     * @param autoname If false, takes basename to be a file. If true, basename
+     *                 is assumed to be a directory in which a filename will be
+     *                 chosen according to the url of the current page.
+     * @param callback Called after the web archive has been saved. The
+     *                 parameter for onReceiveValue will either be the filename
+     *                 under which the file was saved, or null if saving the
+     *                 file failed.
+     */
+    public void saveWebArchive(String basename, boolean autoname, ValueCallback<String> callback) {
+        checkThread();
+        saveWebArchiveImpl(basename, autoname, callback);
+    }
+
+    private void saveWebArchiveImpl(String basename, boolean autoname,
+            ValueCallback<String> callback) {
+        mWebViewCore.sendMessage(EventHub.SAVE_WEBARCHIVE,
+            new SaveWebArchiveMessage(basename, autoname, callback));
+    }
+
+    /**
+     * Stop the current load.
+     */
+    public void stopLoading() {
+        checkThread();
+        // TODO: should we clear all the messages in the queue before sending
+        // STOP_LOADING?
+        switchOutDrawHistory();
+        mWebViewCore.sendMessage(EventHub.STOP_LOADING);
+    }
+
+    /**
+     * Reload the current url.
+     */
+    public void reload() {
+        checkThread();
+        clearHelpers();
+        switchOutDrawHistory();
+        mWebViewCore.sendMessage(EventHub.RELOAD);
+    }
+
+    /**
+     * Return true if this WebView has a back history item.
+     * @return True iff this WebView has a back history item.
+     */
+    public boolean canGoBack() {
+        checkThread();
+        WebBackForwardList l = mCallbackProxy.getBackForwardList();
+        synchronized (l) {
+            if (l.getClearPending()) {
+                return false;
+            } else {
+                return l.getCurrentIndex() > 0;
+            }
+        }
+    }
+
+    /**
+     * Go back in the history of this WebView.
+     */
+    public void goBack() {
+        checkThread();
+        goBackOrForwardImpl(-1);
+    }
+
+    /**
+     * Return true if this WebView has a forward history item.
+     * @return True iff this Webview has a forward history item.
+     */
+    public boolean canGoForward() {
+        checkThread();
+        WebBackForwardList l = mCallbackProxy.getBackForwardList();
+        synchronized (l) {
+            if (l.getClearPending()) {
+                return false;
+            } else {
+                return l.getCurrentIndex() < l.getSize() - 1;
+            }
+        }
+    }
+
+    /**
+     * Go forward in the history of this WebView.
+     */
+    public void goForward() {
+        checkThread();
+        goBackOrForwardImpl(1);
+    }
+
+    /**
+     * Return true if the page can go back or forward the given
+     * number of steps.
+     * @param steps The negative or positive number of steps to move the
+     *              history.
+     */
+    public boolean canGoBackOrForward(int steps) {
+        checkThread();
+        WebBackForwardList l = mCallbackProxy.getBackForwardList();
+        synchronized (l) {
+            if (l.getClearPending()) {
+                return false;
+            } else {
+                int newIndex = l.getCurrentIndex() + steps;
+                return newIndex >= 0 && newIndex < l.getSize();
+            }
+        }
+    }
+
+    /**
+     * Go to the history item that is the number of steps away from
+     * the current item. Steps is negative if backward and positive
+     * if forward.
+     * @param steps The number of steps to take back or forward in the back
+     *              forward list.
+     */
+    public void goBackOrForward(int steps) {
+        checkThread();
+        goBackOrForwardImpl(steps);
+    }
+
+    private void goBackOrForwardImpl(int steps) {
+        goBackOrForward(steps, false);
+    }
+
+    private void goBackOrForward(int steps, boolean ignoreSnapshot) {
+        if (steps != 0) {
+            clearHelpers();
+            mWebViewCore.sendMessage(EventHub.GO_BACK_FORWARD, steps,
+                    ignoreSnapshot ? 1 : 0);
+        }
+    }
+
+    /**
+     * Returns true if private browsing is enabled in this WebView.
+     */
+    public boolean isPrivateBrowsingEnabled() {
+        checkThread();
+        return getSettings().isPrivateBrowsingEnabled();
+    }
+
+    private void startPrivateBrowsing() {
+        getSettings().setPrivateBrowsingEnabled(true);
+    }
+
+    private boolean extendScroll(int y) {
+        int finalY = mScroller.getFinalY();
+        int newY = pinLocY(finalY + y);
+        if (newY == finalY) return false;
+        mScroller.setFinalY(newY);
+        mScroller.extendDuration(computeDuration(0, y));
+        return true;
+    }
+
+    /**
+     * Scroll the contents of the view up by half the view size
+     * @param top true to jump to the top of the page
+     * @return true if the page was scrolled
+     */
+    public boolean pageUp(boolean top) {
+        checkThread();
+        if (mNativeClass == 0) {
+            return false;
+        }
+        if (top) {
+            // go to the top of the document
+            return pinScrollTo(getScrollX(), 0, true, 0);
+        }
+        // Page up
+        int h = getHeight();
+        int y;
+        if (h > 2 * PAGE_SCROLL_OVERLAP) {
+            y = -h + PAGE_SCROLL_OVERLAP;
+        } else {
+            y = -h / 2;
+        }
+        return mScroller.isFinished() ? pinScrollBy(0, y, true, 0)
+                : extendScroll(y);
+    }
+
+    /**
+     * Scroll the contents of the view down by half the page size
+     * @param bottom true to jump to bottom of page
+     * @return true if the page was scrolled
+     */
+    public boolean pageDown(boolean bottom) {
+        checkThread();
+        if (mNativeClass == 0) {
+            return false;
+        }
+        if (bottom) {
+            return pinScrollTo(getScrollX(), computeRealVerticalScrollRange(), true, 0);
+        }
+        // Page down.
+        int h = getHeight();
+        int y;
+        if (h > 2 * PAGE_SCROLL_OVERLAP) {
+            y = h - PAGE_SCROLL_OVERLAP;
+        } else {
+            y = h / 2;
+        }
+        return mScroller.isFinished() ? pinScrollBy(0, y, true, 0)
+                : extendScroll(y);
+    }
+
+    /**
+     * Clear the view so that onDraw() will draw nothing but white background,
+     * and onMeasure() will return 0 if MeasureSpec is not MeasureSpec.EXACTLY
+     */
+    public void clearView() {
+        checkThread();
+        mContentWidth = 0;
+        mContentHeight = 0;
+        setBaseLayer(0, null, false, false);
+        mWebViewCore.sendMessage(EventHub.CLEAR_CONTENT);
+    }
+
+    /**
+     * Return a new picture that captures the current display of the webview.
+     * This is a copy of the display, and will be unaffected if the webview
+     * later loads a different URL.
+     *
+     * @return a picture containing the current contents of the view. Note this
+     *         picture is of the entire document, and is not restricted to the
+     *         bounds of the view.
+     */
+    public Picture capturePicture() {
+        checkThread();
+        if (mNativeClass == 0) return null;
+        Picture result = new Picture();
+        nativeCopyBaseContentToPicture(result);
+        return result;
+    }
+
+    /**
+     * Return the current scale of the WebView
+     * @return The current scale.
+     */
+    public float getScale() {
+        checkThread();
+        return mZoomManager.getScale();
+    }
+
+    /**
+     * Compute the reading level scale of the WebView
+     * @param scale The current scale.
+     * @return The reading level scale.
+     */
+    /*package*/ float computeReadingLevelScale(float scale) {
+        return mZoomManager.computeReadingLevelScale(scale);
+    }
+
+    /**
+     * Set the initial scale for the WebView. 0 means default. If
+     * {@link WebSettings#getUseWideViewPort()} is true, it zooms out all the
+     * way. Otherwise it starts with 100%. If initial scale is greater than 0,
+     * WebView starts with this value as initial scale.
+     * Please note that unlike the scale properties in the viewport meta tag,
+     * this method doesn't take the screen density into account.
+     *
+     * @param scaleInPercent The initial scale in percent.
+     */
+    public void setInitialScale(int scaleInPercent) {
+        checkThread();
+        mZoomManager.setInitialScaleInPercent(scaleInPercent);
+    }
+
+    /**
+     * Invoke the graphical zoom picker widget for this WebView. This will
+     * result in the zoom widget appearing on the screen to control the zoom
+     * level of this WebView.
+     */
+    public void invokeZoomPicker() {
+        checkThread();
+        if (!getSettings().supportZoom()) {
+            Log.w(LOGTAG, "This WebView doesn't support zoom.");
+            return;
+        }
+        clearHelpers();
+        mZoomManager.invokeZoomPicker();
+    }
+
+    /**
+     * Return a HitTestResult based on the current cursor node. If a HTML::a tag
+     * is found and the anchor has a non-JavaScript url, the HitTestResult type
+     * is set to SRC_ANCHOR_TYPE and the url is set in the "extra" field. If the
+     * anchor does not have a url or if it is a JavaScript url, the type will
+     * be UNKNOWN_TYPE and the url has to be retrieved through
+     * {@link #requestFocusNodeHref} asynchronously. If a HTML::img tag is
+     * found, the HitTestResult type is set to IMAGE_TYPE and the url is set in
+     * the "extra" field. A type of
+     * SRC_IMAGE_ANCHOR_TYPE indicates an anchor with a url that has an image as
+     * a child node. If a phone number is found, the HitTestResult type is set
+     * to PHONE_TYPE and the phone number is set in the "extra" field of
+     * HitTestResult. If a map address is found, the HitTestResult type is set
+     * to GEO_TYPE and the address is set in the "extra" field of HitTestResult.
+     * If an email address is found, the HitTestResult type is set to EMAIL_TYPE
+     * and the email is set in the "extra" field of HitTestResult. Otherwise,
+     * HitTestResult type is set to UNKNOWN_TYPE.
+     */
+    public HitTestResult getHitTestResult() {
+        checkThread();
+        return mInitialHitTestResult;
+    }
+
+    // No left edge for double-tap zoom alignment
+    static final int NO_LEFTEDGE = -1;
+
+    int getBlockLeftEdge(int x, int y, float readingScale) {
+        float invReadingScale = 1.0f / readingScale;
+        int readingWidth = (int) (getViewWidth() * invReadingScale);
+        int left = NO_LEFTEDGE;
+        if (mFocusedNode != null) {
+            final int length = mFocusedNode.mEnclosingParentRects.length;
+            for (int i = 0; i < length; i++) {
+                Rect rect = mFocusedNode.mEnclosingParentRects[i];
+                if (rect.width() < mFocusedNode.mHitTestSlop) {
+                    // ignore bounding boxes that are too small
+                    continue;
+                } else if (left != NO_LEFTEDGE && rect.width() > readingWidth) {
+                    // stop when bounding box doesn't fit the screen width
+                    // at reading scale
+                    break;
+                }
+
+                left = rect.left;
+            }
+        }
+
+        return left;
+    }
+
+    /**
+     * Request the anchor or image element URL at the last tapped point.
+     * If hrefMsg is null, this method returns immediately and does not
+     * dispatch hrefMsg to its target. If the tapped point hits an image,
+     * an anchor, or an image in an anchor, the message associates
+     * strings in named keys in its data. The value paired with the key
+     * may be an empty string.
+     *
+     * @param hrefMsg This message will be dispatched with the result of the
+     *                request. The message data contains three keys:
+     *                - "url" returns the anchor's href attribute.
+     *                - "title" returns the anchor's text.
+     *                - "src" returns the image's src attribute.
+     */
+    public void requestFocusNodeHref(Message hrefMsg) {
+        checkThread();
+        if (hrefMsg == null) {
+            return;
+        }
+        int contentX = viewToContentX(mLastTouchX + getScrollX());
+        int contentY = viewToContentY(mLastTouchY + getScrollY());
+        if (mFocusedNode != null && mFocusedNode.mHitTestX == contentX
+                && mFocusedNode.mHitTestY == contentY) {
+            hrefMsg.getData().putString(FocusNodeHref.URL, mFocusedNode.mLinkUrl);
+            hrefMsg.getData().putString(FocusNodeHref.TITLE, mFocusedNode.mAnchorText);
+            hrefMsg.getData().putString(FocusNodeHref.SRC, mFocusedNode.mImageUrl);
+            hrefMsg.sendToTarget();
+            return;
+        }
+        mWebViewCore.sendMessage(EventHub.REQUEST_CURSOR_HREF,
+                contentX, contentY, hrefMsg);
+    }
+
+    /**
+     * Request the url of the image last touched by the user. msg will be sent
+     * to its target with a String representing the url as its object.
+     *
+     * @param msg This message will be dispatched with the result of the request
+     *            as the data member with "url" as key. The result can be null.
+     */
+    public void requestImageRef(Message msg) {
+        checkThread();
+        if (0 == mNativeClass) return; // client isn't initialized
+        String url = mFocusedNode != null ? mFocusedNode.mImageUrl : null;
+        Bundle data = msg.getData();
+        data.putString("url", url);
+        msg.setData(data);
+        msg.sendToTarget();
+    }
+
+    static int pinLoc(int x, int viewMax, int docMax) {
+//        Log.d(LOGTAG, "-- pinLoc " + x + " " + viewMax + " " + docMax);
+        if (docMax < viewMax) {   // the doc has room on the sides for "blank"
+            // pin the short document to the top/left of the screen
+            x = 0;
+//            Log.d(LOGTAG, "--- center " + x);
+        } else if (x < 0) {
+            x = 0;
+//            Log.d(LOGTAG, "--- zero");
+        } else if (x + viewMax > docMax) {
+            x = docMax - viewMax;
+//            Log.d(LOGTAG, "--- pin " + x);
+        }
+        return x;
+    }
+
+    // Expects x in view coordinates
+    int pinLocX(int x) {
+        if (mInOverScrollMode) return x;
+        return pinLoc(x, getViewWidth(), computeRealHorizontalScrollRange());
+    }
+
+    // Expects y in view coordinates
+    int pinLocY(int y) {
+        if (mInOverScrollMode) return y;
+        return pinLoc(y, getViewHeightWithTitle(),
+                      computeRealVerticalScrollRange() + getTitleHeight());
+    }
+
+    /**
+     * A title bar which is embedded in this WebView, and scrolls along with it
+     * vertically, but not horizontally.
+     */
+    private View mTitleBar;
+
+    /**
+     * the title bar rendering gravity
+     */
+    private int mTitleGravity;
+
+    /**
+     * Add or remove a title bar to be embedded into the WebView, and scroll
+     * along with it vertically, while remaining in view horizontally. Pass
+     * null to remove the title bar from the WebView, and return to drawing
+     * the WebView normally without translating to account for the title bar.
+     * @hide
+     */
+    public void setEmbeddedTitleBar(View v) {
+        if (mWebView instanceof TitleBarDelegate) {
+            ((TitleBarDelegate) mWebView).onSetEmbeddedTitleBar(v);
+        }
+        if (mTitleBar == v) return;
+        if (mTitleBar != null) {
+            mWebView.removeView(mTitleBar);
+        }
+        if (null != v) {
+            mWebView.addView(v, new AbsoluteLayout.LayoutParams(
+                    ViewGroup.LayoutParams.MATCH_PARENT,
+                    ViewGroup.LayoutParams.WRAP_CONTENT, 0, 0));
+        }
+        mTitleBar = v;
+    }
+
+    /**
+     * Set where to render the embedded title bar
+     * NO_GRAVITY at the top of the page
+     * TOP        at the top of the screen
+     * @hide
+     */
+    public void setTitleBarGravity(int gravity) {
+        mTitleGravity = gravity;
+        // force refresh
+        invalidate();
+    }
+
+    /**
+     * Given a distance in view space, convert it to content space. Note: this
+     * does not reflect translation, just scaling, so this should not be called
+     * with coordinates, but should be called for dimensions like width or
+     * height.
+     */
+    private int viewToContentDimension(int d) {
+        return Math.round(d * mZoomManager.getInvScale());
+    }
+
+    /**
+     * Given an x coordinate in view space, convert it to content space.  Also
+     * may be used for absolute heights.
+     */
+    /*package*/ int viewToContentX(int x) {
+        return viewToContentDimension(x);
+    }
+
+    /**
+     * Given a y coordinate in view space, convert it to content space.
+     * Takes into account the height of the title bar if there is one
+     * embedded into the WebView.
+     */
+    /*package*/ int viewToContentY(int y) {
+        return viewToContentDimension(y - getTitleHeight());
+    }
+
+    /**
+     * Given a x coordinate in view space, convert it to content space.
+     * Returns the result as a float.
+     */
+    private float viewToContentXf(int x) {
+        return x * mZoomManager.getInvScale();
+    }
+
+    /**
+     * Given a y coordinate in view space, convert it to content space.
+     * Takes into account the height of the title bar if there is one
+     * embedded into the WebView. Returns the result as a float.
+     */
+    private float viewToContentYf(int y) {
+        return (y - getTitleHeight()) * mZoomManager.getInvScale();
+    }
+
+    /**
+     * Given a distance in content space, convert it to view space. Note: this
+     * does not reflect translation, just scaling, so this should not be called
+     * with coordinates, but should be called for dimensions like width or
+     * height.
+     */
+    /*package*/ int contentToViewDimension(int d) {
+        return Math.round(d * mZoomManager.getScale());
+    }
+
+    /**
+     * Given an x coordinate in content space, convert it to view
+     * space.
+     */
+    /*package*/ int contentToViewX(int x) {
+        return contentToViewDimension(x);
+    }
+
+    /**
+     * Given a y coordinate in content space, convert it to view
+     * space.  Takes into account the height of the title bar.
+     */
+    /*package*/ int contentToViewY(int y) {
+        return contentToViewDimension(y) + getTitleHeight();
+    }
+
+    private Rect contentToViewRect(Rect x) {
+        return new Rect(contentToViewX(x.left), contentToViewY(x.top),
+                        contentToViewX(x.right), contentToViewY(x.bottom));
+    }
+
+    /*  To invalidate a rectangle in content coordinates, we need to transform
+        the rect into view coordinates, so we can then call invalidate(...).
+
+        Normally, we would just call contentToView[XY](...), which eventually
+        calls Math.round(coordinate * mActualScale). However, for invalidates,
+        we need to account for the slop that occurs with antialiasing. To
+        address that, we are a little more liberal in the size of the rect that
+        we invalidate.
+
+        This liberal calculation calls floor() for the top/left, and ceil() for
+        the bottom/right coordinates. This catches the possible extra pixels of
+        antialiasing that we might have missed with just round().
+     */
+
+    // Called by JNI to invalidate the View, given rectangle coordinates in
+    // content space
+    private void viewInvalidate(int l, int t, int r, int b) {
+        final float scale = mZoomManager.getScale();
+        final int dy = getTitleHeight();
+        mWebView.invalidate((int)Math.floor(l * scale),
+                (int)Math.floor(t * scale) + dy,
+                (int)Math.ceil(r * scale),
+                (int)Math.ceil(b * scale) + dy);
+    }
+
+    // Called by JNI to invalidate the View after a delay, given rectangle
+    // coordinates in content space
+    private void viewInvalidateDelayed(long delay, int l, int t, int r, int b) {
+        final float scale = mZoomManager.getScale();
+        final int dy = getTitleHeight();
+        mWebView.postInvalidateDelayed(delay,
+                (int)Math.floor(l * scale),
+                (int)Math.floor(t * scale) + dy,
+                (int)Math.ceil(r * scale),
+                (int)Math.ceil(b * scale) + dy);
+    }
+
+    private void invalidateContentRect(Rect r) {
+        viewInvalidate(r.left, r.top, r.right, r.bottom);
+    }
+
+    // stop the scroll animation, and don't let a subsequent fling add
+    // to the existing velocity
+    private void abortAnimation() {
+        mScroller.abortAnimation();
+        mLastVelocity = 0;
+    }
+
+    /* call from webcoreview.draw(), so we're still executing in the UI thread
+    */
+    private void recordNewContentSize(int w, int h, boolean updateLayout) {
+
+        // premature data from webkit, ignore
+        if ((w | h) == 0) {
+            return;
+        }
+
+        // don't abort a scroll animation if we didn't change anything
+        if (mContentWidth != w || mContentHeight != h) {
+            // record new dimensions
+            mContentWidth = w;
+            mContentHeight = h;
+            // If history Picture is drawn, don't update scroll. They will be
+            // updated when we get out of that mode.
+            if (!mDrawHistory) {
+                // repin our scroll, taking into account the new content size
+                updateScrollCoordinates(pinLocX(getScrollX()), pinLocY(getScrollY()));
+                if (!mScroller.isFinished()) {
+                    // We are in the middle of a scroll.  Repin the final scroll
+                    // position.
+                    mScroller.setFinalX(pinLocX(mScroller.getFinalX()));
+                    mScroller.setFinalY(pinLocY(mScroller.getFinalY()));
+                }
+            }
+        }
+        contentSizeChanged(updateLayout);
+    }
+
+    // Used to avoid sending many visible rect messages.
+    private Rect mLastVisibleRectSent = new Rect();
+    private Rect mLastGlobalRect = new Rect();
+    private Rect mVisibleRect = new Rect();
+    private Rect mGlobalVisibleRect = new Rect();
+    private Point mScrollOffset = new Point();
+
+    Rect sendOurVisibleRect() {
+        if (mZoomManager.isPreventingWebkitUpdates()) return mLastVisibleRectSent;
+        calcOurContentVisibleRect(mVisibleRect);
+        // Rect.equals() checks for null input.
+        if (!mVisibleRect.equals(mLastVisibleRectSent)) {
+            if (!mBlockWebkitViewMessages) {
+                mScrollOffset.set(mVisibleRect.left, mVisibleRect.top);
+                mWebViewCore.removeMessages(EventHub.SET_SCROLL_OFFSET);
+                mWebViewCore.sendMessage(EventHub.SET_SCROLL_OFFSET,
+                        mSendScrollEvent ? 1 : 0, mScrollOffset);
+            }
+            mLastVisibleRectSent.set(mVisibleRect);
+            mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+        }
+        if (mWebView.getGlobalVisibleRect(mGlobalVisibleRect)
+                && !mGlobalVisibleRect.equals(mLastGlobalRect)) {
+            if (DebugFlags.WEB_VIEW) {
+                Log.v(LOGTAG, "sendOurVisibleRect=(" + mGlobalVisibleRect.left + ","
+                        + mGlobalVisibleRect.top + ",r=" + mGlobalVisibleRect.right + ",b="
+                        + mGlobalVisibleRect.bottom);
+            }
+            // TODO: the global offset is only used by windowRect()
+            // in ChromeClientAndroid ; other clients such as touch
+            // and mouse events could return view + screen relative points.
+            if (!mBlockWebkitViewMessages) {
+                mWebViewCore.sendMessage(EventHub.SET_GLOBAL_BOUNDS, mGlobalVisibleRect);
+            }
+            mLastGlobalRect.set(mGlobalVisibleRect);
+        }
+        return mVisibleRect;
+    }
+
+    private Point mGlobalVisibleOffset = new Point();
+    // Sets r to be the visible rectangle of our webview in view coordinates
+    private void calcOurVisibleRect(Rect r) {
+        mWebView.getGlobalVisibleRect(r, mGlobalVisibleOffset);
+        r.offset(-mGlobalVisibleOffset.x, -mGlobalVisibleOffset.y);
+    }
+
+    // Sets r to be our visible rectangle in content coordinates
+    private void calcOurContentVisibleRect(Rect r) {
+        calcOurVisibleRect(r);
+        r.left = viewToContentX(r.left);
+        // viewToContentY will remove the total height of the title bar.  Add
+        // the visible height back in to account for the fact that if the title
+        // bar is partially visible, the part of the visible rect which is
+        // displaying our content is displaced by that amount.
+        r.top = viewToContentY(r.top + getVisibleTitleHeightImpl());
+        r.right = viewToContentX(r.right);
+        r.bottom = viewToContentY(r.bottom);
+    }
+
+    private Rect mContentVisibleRect = new Rect();
+    // Sets r to be our visible rectangle in content coordinates. We use this
+    // method on the native side to compute the position of the fixed layers.
+    // Uses floating coordinates (necessary to correctly place elements when
+    // the scale factor is not 1)
+    private void calcOurContentVisibleRectF(RectF r) {
+        calcOurVisibleRect(mContentVisibleRect);
+        r.left = viewToContentXf(mContentVisibleRect.left);
+        // viewToContentY will remove the total height of the title bar.  Add
+        // the visible height back in to account for the fact that if the title
+        // bar is partially visible, the part of the visible rect which is
+        // displaying our content is displaced by that amount.
+        r.top = viewToContentYf(mContentVisibleRect.top + getVisibleTitleHeightImpl());
+        r.right = viewToContentXf(mContentVisibleRect.right);
+        r.bottom = viewToContentYf(mContentVisibleRect.bottom);
+    }
+
+    static class ViewSizeData {
+        int mWidth;
+        int mHeight;
+        float mHeightWidthRatio;
+        int mActualViewHeight;
+        int mTextWrapWidth;
+        int mAnchorX;
+        int mAnchorY;
+        float mScale;
+        boolean mIgnoreHeight;
+    }
+
+    /**
+     * Compute unzoomed width and height, and if they differ from the last
+     * values we sent, send them to webkit (to be used as new viewport)
+     *
+     * @param force ensures that the message is sent to webkit even if the width
+     * or height has not changed since the last message
+     *
+     * @return true if new values were sent
+     */
+    boolean sendViewSizeZoom(boolean force) {
+        if (mBlockWebkitViewMessages) return false;
+        if (mZoomManager.isPreventingWebkitUpdates()) return false;
+
+        int viewWidth = getViewWidth();
+        int newWidth = Math.round(viewWidth * mZoomManager.getInvScale());
+        // This height could be fixed and be different from actual visible height.
+        int viewHeight = getViewHeightWithTitle() - getTitleHeight();
+        int newHeight = Math.round(viewHeight * mZoomManager.getInvScale());
+        // Make the ratio more accurate than (newHeight / newWidth), since the
+        // latter both are calculated and rounded.
+        float heightWidthRatio = (float) viewHeight / viewWidth;
+        /*
+         * Because the native side may have already done a layout before the
+         * View system was able to measure us, we have to send a height of 0 to
+         * remove excess whitespace when we grow our width. This will trigger a
+         * layout and a change in content size. This content size change will
+         * mean that contentSizeChanged will either call this method directly or
+         * indirectly from onSizeChanged.
+         */
+        if (newWidth > mLastWidthSent && mWrapContent) {
+            newHeight = 0;
+            heightWidthRatio = 0;
+        }
+        // Actual visible content height.
+        int actualViewHeight = Math.round(getViewHeight() * mZoomManager.getInvScale());
+        // Avoid sending another message if the dimensions have not changed.
+        if (newWidth != mLastWidthSent || newHeight != mLastHeightSent || force ||
+                actualViewHeight != mLastActualHeightSent) {
+            ViewSizeData data = new ViewSizeData();
+            data.mWidth = newWidth;
+            data.mHeight = newHeight;
+            data.mHeightWidthRatio = heightWidthRatio;
+            data.mActualViewHeight = actualViewHeight;
+            data.mTextWrapWidth = Math.round(viewWidth / mZoomManager.getTextWrapScale());
+            data.mScale = mZoomManager.getScale();
+            data.mIgnoreHeight = mZoomManager.isFixedLengthAnimationInProgress()
+                    && !mHeightCanMeasure;
+            data.mAnchorX = mZoomManager.getDocumentAnchorX();
+            data.mAnchorY = mZoomManager.getDocumentAnchorY();
+            mWebViewCore.sendMessage(EventHub.VIEW_SIZE_CHANGED, data);
+            mLastWidthSent = newWidth;
+            mLastHeightSent = newHeight;
+            mLastActualHeightSent = actualViewHeight;
+            mZoomManager.clearDocumentAnchor();
+            return true;
+        }
+        return false;
+    }
+
+    /**
+     * Update the double-tap zoom.
+     */
+    /* package */ void updateDoubleTapZoom(int doubleTapZoom) {
+        mZoomManager.updateDoubleTapZoom(doubleTapZoom);
+    }
+
+    private int computeRealHorizontalScrollRange() {
+        if (mDrawHistory) {
+            return mHistoryWidth;
+        } else {
+            // to avoid rounding error caused unnecessary scrollbar, use floor
+            return (int) Math.floor(mContentWidth * mZoomManager.getScale());
+        }
+    }
+
+    @Override
+    public int computeHorizontalScrollRange() {
+        int range = computeRealHorizontalScrollRange();
+
+        // Adjust reported range if overscrolled to compress the scroll bars
+        final int scrollX = getScrollX();
+        final int overscrollRight = computeMaxScrollX();
+        if (scrollX < 0) {
+            range -= scrollX;
+        } else if (scrollX > overscrollRight) {
+            range += scrollX - overscrollRight;
+        }
+
+        return range;
+    }
+
+    @Override
+    public int computeHorizontalScrollOffset() {
+        return Math.max(getScrollX(), 0);
+    }
+
+    private int computeRealVerticalScrollRange() {
+        if (mDrawHistory) {
+            return mHistoryHeight;
+        } else {
+            // to avoid rounding error caused unnecessary scrollbar, use floor
+            return (int) Math.floor(mContentHeight * mZoomManager.getScale());
+        }
+    }
+
+    @Override
+    public int computeVerticalScrollRange() {
+        int range = computeRealVerticalScrollRange();
+
+        // Adjust reported range if overscrolled to compress the scroll bars
+        final int scrollY = getScrollY();
+        final int overscrollBottom = computeMaxScrollY();
+        if (scrollY < 0) {
+            range -= scrollY;
+        } else if (scrollY > overscrollBottom) {
+            range += scrollY - overscrollBottom;
+        }
+
+        return range;
+    }
+
+    @Override
+    public int computeVerticalScrollOffset() {
+        return Math.max(getScrollY() - getTitleHeight(), 0);
+    }
+
+    @Override
+    public int computeVerticalScrollExtent() {
+        return getViewHeight();
+    }
+
+    /** @hide */
+    @Override
+    public void onDrawVerticalScrollBar(Canvas canvas,
+                                           Drawable scrollBar,
+                                           int l, int t, int r, int b) {
+        if (getScrollY() < 0) {
+            t -= getScrollY();
+        }
+        scrollBar.setBounds(l, t + getVisibleTitleHeightImpl(), r, b);
+        scrollBar.draw(canvas);
+    }
+
+    @Override
+    public void onOverScrolled(int scrollX, int scrollY, boolean clampedX,
+            boolean clampedY) {
+        // Special-case layer scrolling so that we do not trigger normal scroll
+        // updating.
+        if (mTouchMode == TOUCH_DRAG_LAYER_MODE) {
+            scrollLayerTo(scrollX, scrollY);
+            return;
+        }
+        mInOverScrollMode = false;
+        int maxX = computeMaxScrollX();
+        int maxY = computeMaxScrollY();
+        if (maxX == 0) {
+            // do not over scroll x if the page just fits the screen
+            scrollX = pinLocX(scrollX);
+        } else if (scrollX < 0 || scrollX > maxX) {
+            mInOverScrollMode = true;
+        }
+        if (scrollY < 0 || scrollY > maxY) {
+            mInOverScrollMode = true;
+        }
+
+        int oldX = getScrollX();
+        int oldY = getScrollY();
+
+        mWebViewPrivate.super_scrollTo(scrollX, scrollY);
+
+        if (mOverScrollGlow != null) {
+            mOverScrollGlow.pullGlow(getScrollX(), getScrollY(), oldX, oldY, maxX, maxY);
+        }
+    }
+
+    /**
+     * Get the url for the current page. This is not always the same as the url
+     * passed to WebViewClient.onPageStarted because although the load for
+     * that url has begun, the current page may not have changed.
+     * @return The url for the current page.
+     */
+    public String getUrl() {
+        checkThread();
+        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
+        return h != null ? h.getUrl() : null;
+    }
+
+    /**
+     * Get the original url for the current page. This is not always the same
+     * as the url passed to WebViewClient.onPageStarted because although the
+     * load for that url has begun, the current page may not have changed.
+     * Also, there may have been redirects resulting in a different url to that
+     * originally requested.
+     * @return The url that was originally requested for the current page.
+     */
+    public String getOriginalUrl() {
+        checkThread();
+        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
+        return h != null ? h.getOriginalUrl() : null;
+    }
+
+    /**
+     * Get the title for the current page. This is the title of the current page
+     * until WebViewClient.onReceivedTitle is called.
+     * @return The title for the current page.
+     */
+    public String getTitle() {
+        checkThread();
+        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
+        return h != null ? h.getTitle() : null;
+    }
+
+    /**
+     * Get the favicon for the current page. This is the favicon of the current
+     * page until WebViewClient.onReceivedIcon is called.
+     * @return The favicon for the current page.
+     */
+    public Bitmap getFavicon() {
+        checkThread();
+        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
+        return h != null ? h.getFavicon() : null;
+    }
+
+    /**
+     * Get the touch icon url for the apple-touch-icon <link> element, or
+     * a URL on this site's server pointing to the standard location of a
+     * touch icon.
+     * @hide
+     */
+    public String getTouchIconUrl() {
+        WebHistoryItem h = mCallbackProxy.getBackForwardList().getCurrentItem();
+        return h != null ? h.getTouchIconUrl() : null;
+    }
+
+    /**
+     * Get the progress for the current page.
+     * @return The progress for the current page between 0 and 100.
+     */
+    public int getProgress() {
+        checkThread();
+        return mCallbackProxy.getProgress();
+    }
+
+    /**
+     * @return the height of the HTML content.
+     */
+    public int getContentHeight() {
+        checkThread();
+        return mContentHeight;
+    }
+
+    /**
+     * @return the width of the HTML content.
+     * @hide
+     */
+    public int getContentWidth() {
+        return mContentWidth;
+    }
+
+    /**
+     * @hide
+     */
+    public int getPageBackgroundColor() {
+        return nativeGetBackgroundColor();
+    }
+
+    /**
+     * Pause all layout, parsing, and JavaScript timers for all webviews. This
+     * is a global requests, not restricted to just this webview. This can be
+     * useful if the application has been paused.
+     */
+    public void pauseTimers() {
+        checkThread();
+        mWebViewCore.sendMessage(EventHub.PAUSE_TIMERS);
+    }
+
+    /**
+     * Resume all layout, parsing, and JavaScript timers for all webviews.
+     * This will resume dispatching all timers.
+     */
+    public void resumeTimers() {
+        checkThread();
+        mWebViewCore.sendMessage(EventHub.RESUME_TIMERS);
+    }
+
+    /**
+     * Call this to pause any extra processing associated with this WebView and
+     * its associated DOM, plugins, JavaScript etc. For example, if the WebView
+     * is taken offscreen, this could be called to reduce unnecessary CPU or
+     * network traffic. When the WebView is again "active", call onResume().
+     *
+     * Note that this differs from pauseTimers(), which affects all WebViews.
+     */
+    public void onPause() {
+        checkThread();
+        if (!mIsPaused) {
+            mIsPaused = true;
+            mWebViewCore.sendMessage(EventHub.ON_PAUSE);
+            // We want to pause the current playing video when switching out
+            // from the current WebView/tab.
+            if (mHTML5VideoViewProxy != null) {
+                mHTML5VideoViewProxy.pauseAndDispatch();
+            }
+            if (mNativeClass != 0) {
+                nativeSetPauseDrawing(mNativeClass, true);
+            }
+
+            cancelSelectDialog();
+            WebCoreThreadWatchdog.pause();
+        }
+    }
+
+    @Override
+    public void onWindowVisibilityChanged(int visibility) {
+        updateDrawingState();
+    }
+
+    void updateDrawingState() {
+        if (mNativeClass == 0 || mIsPaused) return;
+        if (mWebView.getWindowVisibility() != View.VISIBLE) {
+            nativeSetPauseDrawing(mNativeClass, true);
+        } else if (mWebView.getVisibility() != View.VISIBLE) {
+            nativeSetPauseDrawing(mNativeClass, true);
+        } else {
+            nativeSetPauseDrawing(mNativeClass, false);
+        }
+    }
+
+    /**
+     * Call this to resume a WebView after a previous call to onPause().
+     */
+    public void onResume() {
+        checkThread();
+        if (mIsPaused) {
+            mIsPaused = false;
+            mWebViewCore.sendMessage(EventHub.ON_RESUME);
+            if (mNativeClass != 0) {
+                nativeSetPauseDrawing(mNativeClass, false);
+            }
+        }
+        // Ensure that the watchdog has a currently valid Context to be able to display
+        // a prompt dialog. For example, if the Activity was finished whilst the WebCore
+        // thread was blocked and the Activity is started again, we may reuse the blocked
+        // thread, but we'll have a new Activity.
+        WebCoreThreadWatchdog.updateContext(mContext);
+        // We get a call to onResume for new WebViews (i.e. mIsPaused will be false). We need
+        // to ensure that the Watchdog thread is running for the new WebView, so call
+        // it outside the if block above.
+        WebCoreThreadWatchdog.resume();
+    }
+
+    /**
+     * Returns true if the view is paused, meaning onPause() was called. Calling
+     * onResume() sets the paused state back to false.
+     * @hide
+     */
+    public boolean isPaused() {
+        return mIsPaused;
+    }
+
+    /**
+     * Call this to inform the view that memory is low so that it can
+     * free any available memory.
+     */
+    public void freeMemory() {
+        checkThread();
+        mWebViewCore.sendMessage(EventHub.FREE_MEMORY);
+    }
+
+    /**
+     * Clear the resource cache. Note that the cache is per-application, so
+     * this will clear the cache for all WebViews used.
+     *
+     * @param includeDiskFiles If false, only the RAM cache is cleared.
+     */
+    public void clearCache(boolean includeDiskFiles) {
+        checkThread();
+        // Note: this really needs to be a static method as it clears cache for all
+        // WebView. But we need mWebViewCore to send message to WebCore thread, so
+        // we can't make this static.
+        mWebViewCore.sendMessage(EventHub.CLEAR_CACHE,
+                includeDiskFiles ? 1 : 0, 0);
+    }
+
+    /**
+     * Make sure that clearing the form data removes the adapter from the
+     * currently focused textfield if there is one.
+     */
+    public void clearFormData() {
+        checkThread();
+        // TODO: Implement b/6083041
+    }
+
+    /**
+     * Tell the WebView to clear its internal back/forward list.
+     */
+    public void clearHistory() {
+        checkThread();
+        mCallbackProxy.getBackForwardList().setClearPending();
+        mWebViewCore.sendMessage(EventHub.CLEAR_HISTORY);
+    }
+
+    /**
+     * Clear the SSL preferences table stored in response to proceeding with SSL
+     * certificate errors.
+     */
+    public void clearSslPreferences() {
+        checkThread();
+        mWebViewCore.sendMessage(EventHub.CLEAR_SSL_PREF_TABLE);
+    }
+
+    /**
+     * Return the WebBackForwardList for this WebView. This contains the
+     * back/forward list for use in querying each item in the history stack.
+     * This is a copy of the private WebBackForwardList so it contains only a
+     * snapshot of the current state. Multiple calls to this method may return
+     * different objects. The object returned from this method will not be
+     * updated to reflect any new state.
+     */
+    public WebBackForwardList copyBackForwardList() {
+        checkThread();
+        return mCallbackProxy.getBackForwardList().clone();
+    }
+
+    /*
+     * Highlight and scroll to the next occurance of String in findAll.
+     * Wraps the page infinitely, and scrolls.  Must be called after
+     * calling findAll.
+     *
+     * @param forward Direction to search.
+     */
+    public void findNext(boolean forward) {
+        checkThread();
+        if (0 == mNativeClass) return; // client isn't initialized
+        mWebViewCore.sendMessage(EventHub.FIND_NEXT, forward ? 1 : 0);
+    }
+
+    /*
+     * Find all instances of find on the page and highlight them.
+     * @param find  String to find.
+     * @return int  The number of occurances of the String "find"
+     *              that were found.
+     */
+    public int findAll(String find) {
+        return findAllBody(find, false);
+    }
+
+    /**
+     * @hide
+     */
+    public void findAllAsync(String find) {
+        findAllBody(find, true);
+    }
+
+    private int findAllBody(String find, boolean isAsync) {
+        checkThread();
+        if (0 == mNativeClass) return 0; // client isn't initialized
+        mLastFind = find;
+        mWebViewCore.removeMessages(EventHub.FIND_ALL);
+        WebViewCore.FindAllRequest request = new
+            WebViewCore.FindAllRequest(find);
+        if (isAsync) {
+            mWebViewCore.sendMessage(EventHub.FIND_ALL, request);
+            return 0; // no need to wait for response
+        }
+        synchronized(request) {
+            try {
+                mWebViewCore.sendMessageAtFrontOfQueue(EventHub.FIND_ALL,
+                    request);
+                while (request.mMatchCount == -1) {
+                    request.wait();
+                }
+            }
+            catch (InterruptedException e) {
+                return 0;
+            }
+        }
+        return request.mMatchCount;
+    }
+
+    /**
+     * Start an ActionMode for finding text in this WebView.  Only works if this
+     *              WebView is attached to the view system.
+     * @param text If non-null, will be the initial text to search for.
+     *             Otherwise, the last String searched for in this WebView will
+     *             be used to start.
+     * @param showIme If true, show the IME, assuming the user will begin typing.
+     *             If false and text is non-null, perform a find all.
+     * @return boolean True if the find dialog is shown, false otherwise.
+     */
+    public boolean showFindDialog(String text, boolean showIme) {
+        checkThread();
+        FindActionModeCallback callback = new FindActionModeCallback(mContext);
+        if (mWebView.getParent() == null || mWebView.startActionMode(callback) == null) {
+            // Could not start the action mode, so end Find on page
+            return false;
+        }
+        mCachedOverlappingActionModeHeight = -1;
+        mFindCallback = callback;
+        setFindIsUp(true);
+        mFindCallback.setWebView(this);
+        if (showIme) {
+            mFindCallback.showSoftInput();
+        } else if (text != null) {
+            mFindCallback.setText(text);
+            mFindCallback.findAll();
+            return true;
+        }
+        if (text == null) {
+            text = mLastFind;
+        }
+        if (text != null) {
+            mFindCallback.setText(text);
+            mFindCallback.findAll();
+        }
+        return true;
+    }
+
+    /**
+     * Keep track of the find callback so that we can remove its titlebar if
+     * necessary.
+     */
+    private FindActionModeCallback mFindCallback;
+
+    /**
+     * Toggle whether the find dialog is showing, for both native and Java.
+     */
+    private void setFindIsUp(boolean isUp) {
+        mFindIsUp = isUp;
+    }
+
+    // Used to know whether the find dialog is open.  Affects whether
+    // or not we draw the highlights for matches.
+    private boolean mFindIsUp;
+
+    // Keep track of the last string sent, so we can search again when find is
+    // reopened.
+    private String mLastFind;
+
+    /**
+     * Return the first substring consisting of the address of a physical
+     * location. Currently, only addresses in the United States are detected,
+     * and consist of:
+     * - a house number
+     * - a street name
+     * - a street type (Road, Circle, etc), either spelled out or abbreviated
+     * - a city name
+     * - a state or territory, either spelled out or two-letter abbr.
+     * - an optional 5 digit or 9 digit zip code.
+     *
+     * All names must be correctly capitalized, and the zip code, if present,
+     * must be valid for the state. The street type must be a standard USPS
+     * spelling or abbreviation. The state or territory must also be spelled
+     * or abbreviated using USPS standards. The house number may not exceed
+     * five digits.
+     * @param addr The string to search for addresses.
+     *
+     * @return the address, or if no address is found, return null.
+     */
+    public static String findAddress(String addr) {
+        checkThread();
+        return findAddress(addr, false);
+    }
+
+    /**
+     * @hide
+     * Return the first substring consisting of the address of a physical
+     * location. Currently, only addresses in the United States are detected,
+     * and consist of:
+     * - a house number
+     * - a street name
+     * - a street type (Road, Circle, etc), either spelled out or abbreviated
+     * - a city name
+     * - a state or territory, either spelled out or two-letter abbr.
+     * - an optional 5 digit or 9 digit zip code.
+     *
+     * Names are optionally capitalized, and the zip code, if present,
+     * must be valid for the state. The street type must be a standard USPS
+     * spelling or abbreviation. The state or territory must also be spelled
+     * or abbreviated using USPS standards. The house number may not exceed
+     * five digits.
+     * @param addr The string to search for addresses.
+     * @param caseInsensitive addr Set to true to make search ignore case.
+     *
+     * @return the address, or if no address is found, return null.
+     */
+    public static String findAddress(String addr, boolean caseInsensitive) {
+        return WebViewCore.nativeFindAddress(addr, caseInsensitive);
+    }
+
+    /*
+     * Clear the highlighting surrounding text matches created by findAll.
+     */
+    public void clearMatches() {
+        checkThread();
+        if (mNativeClass == 0)
+            return;
+        mWebViewCore.removeMessages(EventHub.FIND_ALL);
+        mWebViewCore.sendMessage(EventHub.FIND_ALL, null);
+    }
+
+
+    /**
+     * Called when the find ActionMode ends.
+     */
+    void notifyFindDialogDismissed() {
+        mFindCallback = null;
+        mCachedOverlappingActionModeHeight = -1;
+        if (mWebViewCore == null) {
+            return;
+        }
+        clearMatches();
+        setFindIsUp(false);
+        // Now that the dialog has been removed, ensure that we scroll to a
+        // location that is not beyond the end of the page.
+        pinScrollTo(getScrollX(), getScrollY(), false, 0);
+        invalidate();
+    }
+
+    /**
+     * Query the document to see if it contains any image references. The
+     * message object will be dispatched with arg1 being set to 1 if images
+     * were found and 0 if the document does not reference any images.
+     * @param response The message that will be dispatched with the result.
+     */
+    public void documentHasImages(Message response) {
+        checkThread();
+        if (response == null) {
+            return;
+        }
+        mWebViewCore.sendMessage(EventHub.DOC_HAS_IMAGES, response);
+    }
+
+    /**
+     * Request the scroller to abort any ongoing animation
+     *
+     * @hide
+     */
+    public void stopScroll() {
+        mScroller.forceFinished(true);
+        mLastVelocity = 0;
+    }
+
+    @Override
+    public void computeScroll() {
+        if (mScroller.computeScrollOffset()) {
+            int oldX = getScrollX();
+            int oldY = getScrollY();
+            int x = mScroller.getCurrX();
+            int y = mScroller.getCurrY();
+            invalidate();  // So we draw again
+
+            if (!mScroller.isFinished()) {
+                int rangeX = computeMaxScrollX();
+                int rangeY = computeMaxScrollY();
+                int overflingDistance = mOverflingDistance;
+
+                // Use the layer's scroll data if needed.
+                if (mTouchMode == TOUCH_DRAG_LAYER_MODE) {
+                    oldX = mScrollingLayerRect.left;
+                    oldY = mScrollingLayerRect.top;
+                    rangeX = mScrollingLayerRect.right;
+                    rangeY = mScrollingLayerRect.bottom;
+                    // No overscrolling for layers.
+                    overflingDistance = 0;
+                }
+
+                mWebViewPrivate.overScrollBy(x - oldX, y - oldY, oldX, oldY,
+                        rangeX, rangeY,
+                        overflingDistance, overflingDistance, false);
+
+                if (mOverScrollGlow != null) {
+                    mOverScrollGlow.absorbGlow(x, y, oldX, oldY, rangeX, rangeY);
+                }
+            } else {
+                if (mTouchMode != TOUCH_DRAG_LAYER_MODE) {
+                    setScrollXRaw(x);
+                    setScrollYRaw(y);
+                } else {
+                    // Update the layer position instead of WebView.
+                    scrollLayerTo(x, y);
+                }
+                abortAnimation();
+                nativeSetIsScrolling(false);
+                if (!mBlockWebkitViewMessages) {
+                    WebViewCore.resumePriority();
+                    if (!mSelectingText) {
+                        WebViewCore.resumeUpdatePicture(mWebViewCore);
+                    }
+                }
+                if (oldX != getScrollX() || oldY != getScrollY()) {
+                    sendOurVisibleRect();
+                }
+            }
+        } else {
+            mWebViewPrivate.super_computeScroll();
+        }
+    }
+
+    private void scrollLayerTo(int x, int y) {
+        if (x == mScrollingLayerRect.left && y == mScrollingLayerRect.top) {
+            return;
+        }
+        if (mSelectingText) {
+            int dx = mScrollingLayerRect.left - x;
+            int dy = mScrollingLayerRect.top - y;
+            if (mSelectCursorBaseLayerId == mCurrentScrollingLayerId) {
+                mSelectCursorBase.offset(dx, dy);
+            }
+            if (mSelectCursorExtentLayerId == mCurrentScrollingLayerId) {
+                mSelectCursorExtent.offset(dx, dy);
+            }
+        }
+        nativeScrollLayer(mCurrentScrollingLayerId, x, y);
+        mScrollingLayerRect.left = x;
+        mScrollingLayerRect.top = y;
+        mWebViewCore.sendMessage(WebViewCore.EventHub.SCROLL_LAYER, mCurrentScrollingLayerId,
+                mScrollingLayerRect);
+        mWebViewPrivate.onScrollChanged(getScrollX(), getScrollY(), getScrollX(), getScrollY());
+        invalidate();
+    }
+
+    private static int computeDuration(int dx, int dy) {
+        int distance = Math.max(Math.abs(dx), Math.abs(dy));
+        int duration = distance * 1000 / STD_SPEED;
+        return Math.min(duration, MAX_DURATION);
+    }
+
+    // helper to pin the scrollBy parameters (already in view coordinates)
+    // returns true if the scroll was changed
+    private boolean pinScrollBy(int dx, int dy, boolean animate, int animationDuration) {
+        return pinScrollTo(getScrollX() + dx, getScrollY() + dy, animate, animationDuration);
+    }
+    // helper to pin the scrollTo parameters (already in view coordinates)
+    // returns true if the scroll was changed
+    private boolean pinScrollTo(int x, int y, boolean animate, int animationDuration) {
+        x = pinLocX(x);
+        y = pinLocY(y);
+        int dx = x - getScrollX();
+        int dy = y - getScrollY();
+
+        if ((dx | dy) == 0) {
+            return false;
+        }
+        abortAnimation();
+        if (animate) {
+            //        Log.d(LOGTAG, "startScroll: " + dx + " " + dy);
+            mScroller.startScroll(getScrollX(), getScrollY(), dx, dy,
+                    animationDuration > 0 ? animationDuration : computeDuration(dx, dy));
+            mWebViewPrivate.awakenScrollBars(mScroller.getDuration());
+            invalidate();
+        } else {
+            mWebView.scrollTo(x, y);
+        }
+        return true;
+    }
+
+    // Scale from content to view coordinates, and pin.
+    // Also called by jni webview.cpp
+    private boolean setContentScrollBy(int cx, int cy, boolean animate) {
+        if (mDrawHistory) {
+            // disallow WebView to change the scroll position as History Picture
+            // is used in the view system.
+            // TODO: as we switchOutDrawHistory when trackball or navigation
+            // keys are hit, this should be safe. Right?
+            return false;
+        }
+        cx = contentToViewDimension(cx);
+        cy = contentToViewDimension(cy);
+        if (mHeightCanMeasure) {
+            // move our visible rect according to scroll request
+            if (cy != 0) {
+                Rect tempRect = new Rect();
+                calcOurVisibleRect(tempRect);
+                tempRect.offset(cx, cy);
+                mWebView.requestRectangleOnScreen(tempRect);
+            }
+            // FIXME: We scroll horizontally no matter what because currently
+            // ScrollView and ListView will not scroll horizontally.
+            // FIXME: Why do we only scroll horizontally if there is no
+            // vertical scroll?
+//                Log.d(LOGTAG, "setContentScrollBy cy=" + cy);
+            return cy == 0 && cx != 0 && pinScrollBy(cx, 0, animate, 0);
+        } else {
+            return pinScrollBy(cx, cy, animate, 0);
+        }
+    }
+
+    /**
+     * Called by CallbackProxy when the page starts loading.
+     * @param url The URL of the page which has started loading.
+     */
+    /* package */ void onPageStarted(String url) {
+        // every time we start a new page, we want to reset the
+        // WebView certificate:  if the new site is secure, we
+        // will reload it and get a new certificate set;
+        // if the new site is not secure, the certificate must be
+        // null, and that will be the case
+        mWebView.setCertificate(null);
+
+        // reset the flag since we set to true in if need after
+        // loading is see onPageFinished(Url)
+        mAccessibilityScriptInjected = false;
+    }
+
+    /**
+     * Called by CallbackProxy when the page finishes loading.
+     * @param url The URL of the page which has finished loading.
+     */
+    /* package */ void onPageFinished(String url) {
+        if (mPageThatNeedsToSlideTitleBarOffScreen != null) {
+            // If the user is now on a different page, or has scrolled the page
+            // past the point where the title bar is offscreen, ignore the
+            // scroll request.
+            if (mPageThatNeedsToSlideTitleBarOffScreen.equals(url)
+                    && getScrollX() == 0 && getScrollY() == 0) {
+                pinScrollTo(0, mYDistanceToSlideTitleOffScreen, true,
+                        SLIDE_TITLE_DURATION);
+            }
+            mPageThatNeedsToSlideTitleBarOffScreen = null;
+        }
+        mZoomManager.onPageFinished(url);
+        injectAccessibilityForUrl(url);
+    }
+
+    /**
+     * This method injects accessibility in the loaded document if accessibility
+     * is enabled. If JavaScript is enabled we try to inject a URL specific script.
+     * If no URL specific script is found or JavaScript is disabled we fallback to
+     * the default {@link AccessibilityInjector} implementation.
+     * </p>
+     * If the URL has the "axs" paramter set to 1 it has already done the
+     * script injection so we do nothing. If the parameter is set to 0
+     * the URL opts out accessibility script injection so we fall back to
+     * the default {@link AccessibilityInjector}.
+     * </p>
+     * Note: If the user has not opted-in the accessibility script injection no scripts
+     * are injected rather the default {@link AccessibilityInjector} implementation
+     * is used.
+     *
+     * @param url The URL loaded by this {@link WebView}.
+     */
+    private void injectAccessibilityForUrl(String url) {
+        if (mWebViewCore == null) {
+            return;
+        }
+        AccessibilityManager accessibilityManager = AccessibilityManager.getInstance(mContext);
+
+        if (!accessibilityManager.isEnabled()) {
+            // it is possible that accessibility was turned off between reloads
+            ensureAccessibilityScriptInjectorInstance(false);
+            return;
+        }
+
+        if (!getSettings().getJavaScriptEnabled()) {
+            // no JS so we fallback to the basic buil-in support
+            ensureAccessibilityScriptInjectorInstance(true);
+            return;
+        }
+
+        // check the URL "axs" parameter to choose appropriate action
+        int axsParameterValue = getAxsUrlParameterValue(url);
+        if (axsParameterValue == ACCESSIBILITY_SCRIPT_INJECTION_UNDEFINED) {
+            boolean onDeviceScriptInjectionEnabled = (Settings.Secure.getInt(mContext
+                    .getContentResolver(), Settings.Secure.ACCESSIBILITY_SCRIPT_INJECTION, 0) == 1);
+            if (onDeviceScriptInjectionEnabled) {
+                ensureAccessibilityScriptInjectorInstance(false);
+                // neither script injected nor script injection opted out => we inject
+                mWebView.loadUrl(getScreenReaderInjectingJs());
+                // TODO: Set this flag after successfull script injection. Maybe upon injection
+                // the chooser should update the meta tag and we check it to declare success
+                mAccessibilityScriptInjected = true;
+            } else {
+                // injection disabled so we fallback to the basic built-in support
+                ensureAccessibilityScriptInjectorInstance(true);
+            }
+        } else if (axsParameterValue == ACCESSIBILITY_SCRIPT_INJECTION_OPTED_OUT) {
+            // injection opted out so we fallback to the basic buil-in support
+            ensureAccessibilityScriptInjectorInstance(true);
+        } else if (axsParameterValue == ACCESSIBILITY_SCRIPT_INJECTION_PROVIDED) {
+            ensureAccessibilityScriptInjectorInstance(false);
+            // the URL provides accessibility but we still need to add our generic script
+            mWebView.loadUrl(getScreenReaderInjectingJs());
+        } else {
+            Log.e(LOGTAG, "Unknown URL value for the \"axs\" URL parameter: " + axsParameterValue);
+        }
+    }
+
+    /**
+     * Ensures the instance of the {@link AccessibilityInjector} to be present ot not.
+     *
+     * @param present True to ensure an insance, false to ensure no instance.
+     */
+    private void ensureAccessibilityScriptInjectorInstance(boolean present) {
+        if (present) {
+            if (mAccessibilityInjector == null) {
+                mAccessibilityInjector = new AccessibilityInjector(this);
+            }
+        } else {
+            mAccessibilityInjector = null;
+        }
+    }
+
+    /**
+     * Gets JavaScript that injects a screen-reader.
+     *
+     * @return The JavaScript snippet.
+     */
+    private String getScreenReaderInjectingJs() {
+        String screenReaderUrl = Settings.Secure.getString(mContext.getContentResolver(),
+                Settings.Secure.ACCESSIBILITY_SCREEN_READER_URL);
+        return String.format(ACCESSIBILITY_SCREEN_READER_JAVASCRIPT_TEMPLATE, screenReaderUrl);
+    }
+
+    /**
+     * Gets the "axs" URL parameter value.
+     *
+     * @param url A url to fetch the paramter from.
+     * @return The parameter value if such, -1 otherwise.
+     */
+    private int getAxsUrlParameterValue(String url) {
+        if (mMatchAxsUrlParameterPattern == null) {
+            mMatchAxsUrlParameterPattern = Pattern.compile(PATTERN_MATCH_AXS_URL_PARAMETER);
+        }
+        Matcher matcher = mMatchAxsUrlParameterPattern.matcher(url);
+        if (matcher.find()) {
+            String keyValuePair = url.substring(matcher.start(), matcher.end());
+            return Integer.parseInt(keyValuePair.split("=")[1]);
+        }
+        return -1;
+    }
+
+    /**
+     * The URL of a page that sent a message to scroll the title bar off screen.
+     *
+     * Many mobile sites tell the page to scroll to (0,1) in order to scroll the
+     * title bar off the screen.  Sometimes, the scroll position is set before
+     * the page finishes loading.  Rather than scrolling while the page is still
+     * loading, keep track of the URL and new scroll position so we can perform
+     * the scroll once the page finishes loading.
+     */
+    private String mPageThatNeedsToSlideTitleBarOffScreen;
+
+    /**
+     * The destination Y scroll position to be used when the page finishes
+     * loading.  See mPageThatNeedsToSlideTitleBarOffScreen.
+     */
+    private int mYDistanceToSlideTitleOffScreen;
+
+    // scale from content to view coordinates, and pin
+    // return true if pin caused the final x/y different than the request cx/cy,
+    // and a future scroll may reach the request cx/cy after our size has
+    // changed
+    // return false if the view scroll to the exact position as it is requested,
+    // where negative numbers are taken to mean 0
+    private boolean setContentScrollTo(int cx, int cy) {
+        if (mDrawHistory) {
+            // disallow WebView to change the scroll position as History Picture
+            // is used in the view system.
+            // One known case where this is called is that WebCore tries to
+            // restore the scroll position. As history Picture already uses the
+            // saved scroll position, it is ok to skip this.
+            return false;
+        }
+        int vx;
+        int vy;
+        if ((cx | cy) == 0) {
+            // If the page is being scrolled to (0,0), do not add in the title
+            // bar's height, and simply scroll to (0,0). (The only other work
+            // in contentToView_ is to multiply, so this would not change 0.)
+            vx = 0;
+            vy = 0;
+        } else {
+            vx = contentToViewX(cx);
+            vy = contentToViewY(cy);
+        }
+//        Log.d(LOGTAG, "content scrollTo [" + cx + " " + cy + "] view=[" +
+//                      vx + " " + vy + "]");
+        // Some mobile sites attempt to scroll the title bar off the page by
+        // scrolling to (0,1).  If we are at the top left corner of the
+        // page, assume this is an attempt to scroll off the title bar, and
+        // animate the title bar off screen slowly enough that the user can see
+        // it.
+        if (cx == 0 && cy == 1 && getScrollX() == 0 && getScrollY() == 0
+                && mTitleBar != null) {
+            // FIXME: 100 should be defined somewhere as our max progress.
+            if (getProgress() < 100) {
+                // Wait to scroll the title bar off screen until the page has
+                // finished loading.  Keep track of the URL and the destination
+                // Y position
+                mPageThatNeedsToSlideTitleBarOffScreen = getUrl();
+                mYDistanceToSlideTitleOffScreen = vy;
+            } else {
+                pinScrollTo(vx, vy, true, SLIDE_TITLE_DURATION);
+            }
+            // Since we are animating, we have not yet reached the desired
+            // scroll position.  Do not return true to request another attempt
+            return false;
+        }
+        pinScrollTo(vx, vy, false, 0);
+        // If the request was to scroll to a negative coordinate, treat it as if
+        // it was a request to scroll to 0
+        if ((getScrollX() != vx && cx >= 0) || (getScrollY() != vy && cy >= 0)) {
+            return true;
+        } else {
+            return false;
+        }
+    }
+
+    // scale from content to view coordinates, and pin
+    private void spawnContentScrollTo(int cx, int cy) {
+        if (mDrawHistory) {
+            // disallow WebView to change the scroll position as History Picture
+            // is used in the view system.
+            return;
+        }
+        int vx = contentToViewX(cx);
+        int vy = contentToViewY(cy);
+        pinScrollTo(vx, vy, true, 0);
+    }
+
+    /**
+     * These are from webkit, and are in content coordinate system (unzoomed)
+     */
+    private void contentSizeChanged(boolean updateLayout) {
+        // suppress 0,0 since we usually see real dimensions soon after
+        // this avoids drawing the prev content in a funny place. If we find a
+        // way to consolidate these notifications, this check may become
+        // obsolete
+        if ((mContentWidth | mContentHeight) == 0) {
+            return;
+        }
+
+        if (mHeightCanMeasure) {
+            if (mWebView.getMeasuredHeight() != contentToViewDimension(mContentHeight)
+                    || updateLayout) {
+                mWebView.requestLayout();
+            }
+        } else if (mWidthCanMeasure) {
+            if (mWebView.getMeasuredWidth() != contentToViewDimension(mContentWidth)
+                    || updateLayout) {
+                mWebView.requestLayout();
+            }
+        } else {
+            // If we don't request a layout, try to send our view size to the
+            // native side to ensure that WebCore has the correct dimensions.
+            sendViewSizeZoom(false);
+        }
+    }
+
+    /**
+     * Set the WebViewClient that will receive various notifications and
+     * requests. This will replace the current handler.
+     * @param client An implementation of WebViewClient.
+     */
+    public void setWebViewClient(WebViewClient client) {
+        checkThread();
+        mCallbackProxy.setWebViewClient(client);
+    }
+
+    /**
+     * Gets the WebViewClient
+     * @return the current WebViewClient instance.
+     *
+     * @hide This is an implementation detail.
+     */
+    public WebViewClient getWebViewClient() {
+        return mCallbackProxy.getWebViewClient();
+    }
+
+    /**
+     * Register the interface to be used when content can not be handled by
+     * the rendering engine, and should be downloaded instead. This will replace
+     * the current handler.
+     * @param listener An implementation of DownloadListener.
+     */
+    public void setDownloadListener(DownloadListener listener) {
+        checkThread();
+        mCallbackProxy.setDownloadListener(listener);
+    }
+
+    /**
+     * Set the chrome handler. This is an implementation of WebChromeClient for
+     * use in handling JavaScript dialogs, favicons, titles, and the progress.
+     * This will replace the current handler.
+     * @param client An implementation of WebChromeClient.
+     */
+    public void setWebChromeClient(WebChromeClient client) {
+        checkThread();
+        mCallbackProxy.setWebChromeClient(client);
+    }
+
+    /**
+     * Gets the chrome handler.
+     * @return the current WebChromeClient instance.
+     *
+     * @hide This is an implementation detail.
+     */
+    public WebChromeClient getWebChromeClient() {
+        return mCallbackProxy.getWebChromeClient();
+    }
+
+    /**
+     * Set the back/forward list client. This is an implementation of
+     * WebBackForwardListClient for handling new items and changes in the
+     * history index.
+     * @param client An implementation of WebBackForwardListClient.
+     * {@hide}
+     */
+    public void setWebBackForwardListClient(WebBackForwardListClient client) {
+        mCallbackProxy.setWebBackForwardListClient(client);
+    }
+
+    /**
+     * Gets the WebBackForwardListClient.
+     * {@hide}
+     */
+    public WebBackForwardListClient getWebBackForwardListClient() {
+        return mCallbackProxy.getWebBackForwardListClient();
+    }
+
+    /**
+     * Set the Picture listener. This is an interface used to receive
+     * notifications of a new Picture.
+     * @param listener An implementation of WebView.PictureListener.
+     * @deprecated This method is now obsolete.
+     */
+    @Deprecated
+    public void setPictureListener(PictureListener listener) {
+        checkThread();
+        mPictureListener = listener;
+    }
+
+    /**
+     * {@hide}
+     */
+    /* FIXME: Debug only! Remove for SDK! */
+    public void externalRepresentation(Message callback) {
+        mWebViewCore.sendMessage(EventHub.REQUEST_EXT_REPRESENTATION, callback);
+    }
+
+    /**
+     * {@hide}
+     */
+    /* FIXME: Debug only! Remove for SDK! */
+    public void documentAsText(Message callback) {
+        mWebViewCore.sendMessage(EventHub.REQUEST_DOC_AS_TEXT, callback);
+    }
+
+    /**
+     * This method injects the supplied Java object into the WebView. The
+     * object is injected into the JavaScript context of the main frame, using
+     * the supplied name. This allows the Java object to be accessed from
+     * JavaScript. Note that that injected objects will not appear in
+     * JavaScript until the page is next (re)loaded. For example:
+     * <pre> webView.addJavascriptInterface(new Object(), "injectedObject");
+     * webView.loadData("<!DOCTYPE html><title></title>", "text/html", null);
+     * webView.loadUrl("javascript:alert(injectedObject.toString())");</pre>
+     * <p><strong>IMPORTANT:</strong>
+     * <ul>
+     * <li> addJavascriptInterface() can be used to allow JavaScript to control
+     * the host application. This is a powerful feature, but also presents a
+     * security risk. Use of this method in a WebView containing untrusted
+     * content could allow an attacker to manipulate the host application in
+     * unintended ways, executing Java code with the permissions of the host
+     * application. Use extreme care when using this method in a WebView which
+     * could contain untrusted content.
+     * <li> JavaScript interacts with Java object on a private, background
+     * thread of the WebView. Care is therefore required to maintain thread
+     * safety.</li>
+     * </ul></p>
+     * @param object The Java object to inject into the WebView's JavaScript
+     *               context. Null values are ignored.
+     * @param name The name used to expose the instance in JavaScript.
+     */
+    public void addJavascriptInterface(Object object, String name) {
+        checkThread();
+        if (object == null) {
+            return;
+        }
+        WebViewCore.JSInterfaceData arg = new WebViewCore.JSInterfaceData();
+        arg.mObject = object;
+        arg.mInterfaceName = name;
+        mWebViewCore.sendMessage(EventHub.ADD_JS_INTERFACE, arg);
+    }
+
+    /**
+     * Removes a previously added JavaScript interface with the given name.
+     * @param interfaceName The name of the interface to remove.
+     */
+    public void removeJavascriptInterface(String interfaceName) {
+        checkThread();
+        if (mWebViewCore != null) {
+            WebViewCore.JSInterfaceData arg = new WebViewCore.JSInterfaceData();
+            arg.mInterfaceName = interfaceName;
+            mWebViewCore.sendMessage(EventHub.REMOVE_JS_INTERFACE, arg);
+        }
+    }
+
+    /**
+     * Return the WebSettings object used to control the settings for this
+     * WebView.
+     * @return A WebSettings object that can be used to control this WebView's
+     *         settings.
+     */
+    public WebSettingsClassic getSettings() {
+        checkThread();
+        return (mWebViewCore != null) ? mWebViewCore.getSettings() : null;
+    }
+
+   /**
+    * Return the list of currently loaded plugins.
+    * @return The list of currently loaded plugins.
+    *
+    * @hide
+    * @deprecated This was used for Gears, which has been deprecated.
+    */
+    @Deprecated
+    public static synchronized PluginList getPluginList() {
+        checkThread();
+        return new PluginList();
+    }
+
+   /**
+    * @hide
+    * @deprecated This was used for Gears, which has been deprecated.
+    */
+    @Deprecated
+    public void refreshPlugins(boolean reloadOpenPages) {
+        checkThread();
+    }
+
+    //-------------------------------------------------------------------------
+    // Override View methods
+    //-------------------------------------------------------------------------
+
+    @Override
+    protected void finalize() throws Throwable {
+        try {
+            if (mNativeClass != 0) {
+                mPrivateHandler.post(new Runnable() {
+                    @Override
+                    public void run() {
+                        destroy();
+                    }
+                });
+            }
+        } finally {
+            super.finalize();
+        }
+    }
+
+    @Override
+    public boolean drawChild(Canvas canvas, View child, long drawingTime) {
+        if (child == mTitleBar) {
+            // When drawing the title bar, move it horizontally to always show
+            // at the top of the WebView.
+            mTitleBar.offsetLeftAndRight(getScrollX() - mTitleBar.getLeft());
+            int newTop = 0;
+            if (mTitleGravity == Gravity.NO_GRAVITY) {
+                newTop = Math.min(0, getScrollY());
+            } else if (mTitleGravity == Gravity.TOP) {
+                newTop = getScrollY();
+            }
+            mTitleBar.setBottom(newTop + mTitleBar.getHeight());
+            mTitleBar.setTop(newTop);
+        }
+        return false;  // We never call invalidate(), so unconditionally returning false.
+    }
+
+    private void drawContent(Canvas canvas) {
+        if (mDrawHistory) {
+            canvas.scale(mZoomManager.getScale(), mZoomManager.getScale());
+            canvas.drawPicture(mHistoryPicture);
+            return;
+        }
+        if (mNativeClass == 0) return;
+
+        boolean animateZoom = mZoomManager.isFixedLengthAnimationInProgress();
+        boolean animateScroll = ((!mScroller.isFinished()
+                || mVelocityTracker != null)
+                && (mTouchMode != TOUCH_DRAG_MODE ||
+                mHeldMotionless != MOTIONLESS_TRUE))
+                || mDeferTouchMode == TOUCH_DRAG_MODE;
+        if (mTouchMode == TOUCH_DRAG_MODE) {
+            if (mHeldMotionless == MOTIONLESS_PENDING) {
+                mPrivateHandler.removeMessages(DRAG_HELD_MOTIONLESS);
+                mPrivateHandler.removeMessages(AWAKEN_SCROLL_BARS);
+                mHeldMotionless = MOTIONLESS_FALSE;
+            }
+            if (mHeldMotionless == MOTIONLESS_FALSE) {
+                mPrivateHandler.sendMessageDelayed(mPrivateHandler
+                        .obtainMessage(DRAG_HELD_MOTIONLESS), MOTIONLESS_TIME);
+                mPrivateHandler.sendMessageDelayed(mPrivateHandler
+                        .obtainMessage(AWAKEN_SCROLL_BARS),
+                            ViewConfiguration.getScrollDefaultDelay());
+                mHeldMotionless = MOTIONLESS_PENDING;
+            }
+        }
+        int saveCount = canvas.save();
+        if (animateZoom) {
+            mZoomManager.animateZoom(canvas);
+        } else if (!canvas.isHardwareAccelerated()) {
+            canvas.scale(mZoomManager.getScale(), mZoomManager.getScale());
+        }
+
+        boolean UIAnimationsRunning = false;
+        // Currently for each draw we compute the animation values;
+        // We may in the future decide to do that independently.
+        if (mNativeClass != 0 && !canvas.isHardwareAccelerated()
+                && nativeEvaluateLayersAnimations(mNativeClass)) {
+            UIAnimationsRunning = true;
+            // If we have unfinished (or unstarted) animations,
+            // we ask for a repaint. We only need to do this in software
+            // rendering (with hardware rendering we already have a different
+            // method of requesting a repaint)
+            mWebViewCore.sendMessage(EventHub.NOTIFY_ANIMATION_STARTED);
+            invalidate();
+        }
+
+        // decide which adornments to draw
+        int extras = DRAW_EXTRAS_NONE;
+        if (!mFindIsUp && mSelectingText) {
+            extras = DRAW_EXTRAS_SELECTION;
+        }
+
+        calcOurContentVisibleRectF(mVisibleContentRect);
+        if (canvas.isHardwareAccelerated()) {
+            Rect glRectViewport = mGLViewportEmpty ? null : mGLRectViewport;
+            Rect viewRectViewport = mGLViewportEmpty ? null : mViewRectViewport;
+
+            int functor = nativeGetDrawGLFunction(mNativeClass, glRectViewport,
+                    viewRectViewport, mVisibleContentRect, getScale(), extras);
+            ((HardwareCanvas) canvas).callDrawGLFunction(functor);
+            if (mHardwareAccelSkia != getSettings().getHardwareAccelSkiaEnabled()) {
+                mHardwareAccelSkia = getSettings().getHardwareAccelSkiaEnabled();
+                nativeUseHardwareAccelSkia(mHardwareAccelSkia);
+            }
+
+        } else {
+            DrawFilter df = null;
+            if (mZoomManager.isZoomAnimating() || UIAnimationsRunning) {
+                df = mZoomFilter;
+            } else if (animateScroll) {
+                df = mScrollFilter;
+            }
+            canvas.setDrawFilter(df);
+            // XXX: Revisit splitting content.  Right now it causes a
+            // synchronization problem with layers.
+            int content = nativeDraw(canvas, mVisibleContentRect, mBackgroundColor,
+                    extras, false);
+            canvas.setDrawFilter(null);
+            if (!mBlockWebkitViewMessages && content != 0) {
+                mWebViewCore.sendMessage(EventHub.SPLIT_PICTURE_SET, content, 0);
+            }
+        }
+
+        canvas.restoreToCount(saveCount);
+        if (mSelectingText) {
+            drawTextSelectionHandles(canvas);
+        }
+
+        if (extras == DRAW_EXTRAS_CURSOR_RING) {
+            if (mTouchMode == TOUCH_SHORTPRESS_START_MODE) {
+                mTouchMode = TOUCH_SHORTPRESS_MODE;
+            }
+        }
+    }
+
+    /**
+     * Draw the background when beyond bounds
+     * @param canvas Canvas to draw into
+     */
+    private void drawOverScrollBackground(Canvas canvas) {
+        if (mOverScrollBackground == null) {
+            mOverScrollBackground = new Paint();
+            Bitmap bm = BitmapFactory.decodeResource(
+                    mContext.getResources(),
+                    com.android.internal.R.drawable.status_bar_background);
+            mOverScrollBackground.setShader(new BitmapShader(bm,
+                    Shader.TileMode.REPEAT, Shader.TileMode.REPEAT));
+            mOverScrollBorder = new Paint();
+            mOverScrollBorder.setStyle(Paint.Style.STROKE);
+            mOverScrollBorder.setStrokeWidth(0);
+            mOverScrollBorder.setColor(0xffbbbbbb);
+        }
+
+        int top = 0;
+        int right = computeRealHorizontalScrollRange();
+        int bottom = top + computeRealVerticalScrollRange();
+        // first draw the background and anchor to the top of the view
+        canvas.save();
+        canvas.translate(getScrollX(), getScrollY());
+        canvas.clipRect(-getScrollX(), top - getScrollY(), right - getScrollX(), bottom
+                - getScrollY(), Region.Op.DIFFERENCE);
+        canvas.drawPaint(mOverScrollBackground);
+        canvas.restore();
+        // then draw the border
+        canvas.drawRect(-1, top - 1, right, bottom, mOverScrollBorder);
+        // next clip the region for the content
+        canvas.clipRect(0, top, right, bottom);
+    }
+
+    @Override
+    public void onDraw(Canvas canvas) {
+        if (inFullScreenMode()) {
+            return; // no need to draw anything if we aren't visible.
+        }
+        // if mNativeClass is 0, the WebView is either destroyed or not
+        // initialized. In either case, just draw the background color and return
+        if (mNativeClass == 0) {
+            canvas.drawColor(mBackgroundColor);
+            return;
+        }
+
+        // if both mContentWidth and mContentHeight are 0, it means there is no
+        // valid Picture passed to WebView yet. This can happen when WebView
+        // just starts. Draw the background and return.
+        if ((mContentWidth | mContentHeight) == 0 && mHistoryPicture == null) {
+            canvas.drawColor(mBackgroundColor);
+            return;
+        }
+
+        if (canvas.isHardwareAccelerated()) {
+            mZoomManager.setHardwareAccelerated();
+        } else {
+            mWebViewCore.resumeWebKitDraw();
+        }
+
+        int saveCount = canvas.save();
+        if (mInOverScrollMode && !getSettings()
+                .getUseWebViewBackgroundForOverscrollBackground()) {
+            drawOverScrollBackground(canvas);
+        }
+        if (mTitleBar != null) {
+            canvas.translate(0, getTitleHeight());
+        }
+        drawContent(canvas);
+        canvas.restoreToCount(saveCount);
+
+        if (AUTO_REDRAW_HACK && mAutoRedraw) {
+            invalidate();
+        }
+        mWebViewCore.signalRepaintDone();
+
+        if (mOverScrollGlow != null && mOverScrollGlow.drawEdgeGlows(canvas)) {
+            invalidate();
+        }
+
+        if (mFocusTransition != null) {
+            mFocusTransition.draw(canvas);
+        } else if (shouldDrawHighlightRect()) {
+            RegionIterator iter = new RegionIterator(mTouchHighlightRegion);
+            Rect r = new Rect();
+            while (iter.next(r)) {
+                canvas.drawRect(r, mTouchHightlightPaint);
+            }
+        }
+        if (DEBUG_TOUCH_HIGHLIGHT) {
+            if (getSettings().getNavDump()) {
+                if ((mTouchHighlightX | mTouchHighlightY) != 0) {
+                    if (mTouchCrossHairColor == null) {
+                        mTouchCrossHairColor = new Paint();
+                        mTouchCrossHairColor.setColor(Color.RED);
+                    }
+                    canvas.drawLine(mTouchHighlightX - mNavSlop,
+                            mTouchHighlightY - mNavSlop, mTouchHighlightX
+                                    + mNavSlop + 1, mTouchHighlightY + mNavSlop
+                                    + 1, mTouchCrossHairColor);
+                    canvas.drawLine(mTouchHighlightX + mNavSlop + 1,
+                            mTouchHighlightY - mNavSlop, mTouchHighlightX
+                                    - mNavSlop,
+                            mTouchHighlightY + mNavSlop + 1,
+                            mTouchCrossHairColor);
+                }
+            }
+        }
+    }
+
+    private void removeTouchHighlight() {
+        mWebViewCore.removeMessages(EventHub.HIT_TEST);
+        mPrivateHandler.removeMessages(HIT_TEST_RESULT);
+        setTouchHighlightRects(null);
+    }
+
+    @Override
+    public void setLayoutParams(ViewGroup.LayoutParams params) {
+        if (params.height == AbsoluteLayout.LayoutParams.WRAP_CONTENT) {
+            mWrapContent = true;
+        }
+        mWebViewPrivate.super_setLayoutParams(params);
+    }
+
+    @Override
+    public boolean performLongClick() {
+        // performLongClick() is the result of a delayed message. If we switch
+        // to windows overview, the WebView will be temporarily removed from the
+        // view system. In that case, do nothing.
+        if (mWebView.getParent() == null) return false;
+
+        // A multi-finger gesture can look like a long press; make sure we don't take
+        // long press actions if we're scaling.
+        final ScaleGestureDetector detector = mZoomManager.getMultiTouchGestureDetector();
+        if (detector != null && detector.isInProgress()) {
+            return false;
+        }
+
+        if (mSelectingText) return false; // long click does nothing on selection
+        /* if long click brings up a context menu, the super function
+         * returns true and we're done. Otherwise, nothing happened when
+         * the user clicked. */
+        if (mWebViewPrivate.super_performLongClick()) {
+            return true;
+        }
+        /* In the case where the application hasn't already handled the long
+         * click action, look for a word under the  click. If one is found,
+         * animate the text selection into view.
+         * FIXME: no animation code yet */
+        final boolean isSelecting = selectText();
+        if (isSelecting) {
+            mWebView.performHapticFeedback(HapticFeedbackConstants.LONG_PRESS);
+        } else if (focusCandidateIsEditableText()) {
+            mSelectCallback = new SelectActionModeCallback();
+            mSelectCallback.setWebView(this);
+            mSelectCallback.setTextSelected(false);
+            mWebView.startActionMode(mSelectCallback);
+        }
+        return isSelecting;
+    }
+
+    /**
+     * Select the word at the last click point.
+     *
+     * @hide This is an implementation detail.
+     */
+    public boolean selectText() {
+        int x = viewToContentX(mLastTouchX + getScrollX());
+        int y = viewToContentY(mLastTouchY + getScrollY());
+        return selectText(x, y);
+    }
+
+    /**
+     * Select the word at the indicated content coordinates.
+     */
+    boolean selectText(int x, int y) {
+        mWebViewCore.sendMessage(EventHub.SELECT_WORD_AT, x, y);
+        return true;
+    }
+
+    private int mOrientation = Configuration.ORIENTATION_UNDEFINED;
+
+    @Override
+    public void onConfigurationChanged(Configuration newConfig) {
+        mCachedOverlappingActionModeHeight = -1;
+        if (mSelectingText && mOrientation != newConfig.orientation) {
+            selectionDone();
+        }
+        mOrientation = newConfig.orientation;
+        if (mWebViewCore != null && !mBlockWebkitViewMessages) {
+            mWebViewCore.sendMessage(EventHub.CLEAR_CONTENT);
+        }
+    }
+
+    /**
+     * Keep track of the Callback so we can end its ActionMode or remove its
+     * titlebar.
+     */
+    private SelectActionModeCallback mSelectCallback;
+
+    void setBaseLayer(int layer, Region invalRegion, boolean showVisualIndicator,
+            boolean isPictureAfterFirstLayout) {
+        if (mNativeClass == 0)
+            return;
+        boolean queueFull;
+        queueFull = nativeSetBaseLayer(mNativeClass, layer, invalRegion,
+                                       showVisualIndicator, isPictureAfterFirstLayout);
+
+        if (layer == 0 || isPictureAfterFirstLayout) {
+            mWebViewCore.resumeWebKitDraw();
+        } else if (queueFull) {
+            // temporarily disable webkit draw throttling
+            // TODO: re-enable
+            // mWebViewCore.pauseWebKitDraw();
+        }
+
+        if (mHTML5VideoViewProxy != null) {
+            mHTML5VideoViewProxy.setBaseLayer(layer);
+        }
+    }
+
+    int getBaseLayer() {
+        if (mNativeClass == 0) {
+            return 0;
+        }
+        return nativeGetBaseLayer();
+    }
+
+    private void onZoomAnimationStart() {
+    }
+
+    private void onZoomAnimationEnd() {
+    }
+
+    void onFixedLengthZoomAnimationStart() {
+        WebViewCore.pauseUpdatePicture(getWebViewCore());
+        onZoomAnimationStart();
+    }
+
+    void onFixedLengthZoomAnimationEnd() {
+        if (!mBlockWebkitViewMessages && !mSelectingText) {
+            WebViewCore.resumeUpdatePicture(mWebViewCore);
+        }
+        onZoomAnimationEnd();
+    }
+
+    private static final int ZOOM_BITS = Paint.FILTER_BITMAP_FLAG |
+                                         Paint.DITHER_FLAG |
+                                         Paint.SUBPIXEL_TEXT_FLAG;
+    private static final int SCROLL_BITS = Paint.FILTER_BITMAP_FLAG |
+                                           Paint.DITHER_FLAG;
+
+    private final DrawFilter mZoomFilter =
+            new PaintFlagsDrawFilter(ZOOM_BITS, Paint.LINEAR_TEXT_FLAG);
+    // If we need to trade better quality for speed, set mScrollFilter to null
+    private final DrawFilter mScrollFilter =
+            new PaintFlagsDrawFilter(SCROLL_BITS, 0);
+
+    private void ensureSelectionHandles() {
+        if (mSelectHandleCenter == null) {
+            mSelectHandleCenter = mContext.getResources().getDrawable(
+                    com.android.internal.R.drawable.text_select_handle_middle);
+            mSelectHandleLeft = mContext.getResources().getDrawable(
+                    com.android.internal.R.drawable.text_select_handle_left);
+            mSelectHandleRight = mContext.getResources().getDrawable(
+                    com.android.internal.R.drawable.text_select_handle_right);
+        }
+    }
+
+    private void drawTextSelectionHandles(Canvas canvas) {
+        ensureSelectionHandles();
+        int[] handles = new int[4];
+        getSelectionHandles(handles);
+        int start_x = contentToViewDimension(handles[0]);
+        int start_y = contentToViewDimension(handles[1]);
+        int end_x = contentToViewDimension(handles[2]);
+        int end_y = contentToViewDimension(handles[3]);
+
+        if (mIsCaretSelection) {
+            // Caret handle is centered
+            start_x -= (mSelectHandleCenter.getIntrinsicWidth() / 2);
+            mSelectHandleCenter.setBounds(start_x, start_y,
+                    start_x + mSelectHandleCenter.getIntrinsicWidth(),
+                    start_y + mSelectHandleCenter.getIntrinsicHeight());
+            mSelectHandleCenter.draw(canvas);
+        } else {
+            // Magic formula copied from TextView
+            start_x -= (mSelectHandleLeft.getIntrinsicWidth() * 3) / 4;
+            mSelectHandleLeft.setBounds(start_x, start_y,
+                    start_x + mSelectHandleLeft.getIntrinsicWidth(),
+                    start_y + mSelectHandleLeft.getIntrinsicHeight());
+            end_x -= mSelectHandleRight.getIntrinsicWidth() / 4;
+            mSelectHandleRight.setBounds(end_x, end_y,
+                    end_x + mSelectHandleRight.getIntrinsicWidth(),
+                    end_y + mSelectHandleRight.getIntrinsicHeight());
+            mSelectHandleLeft.draw(canvas);
+            mSelectHandleRight.draw(canvas);
+        }
+    }
+
+    /**
+     * Takes an int[4] array as an output param with the values being
+     * startX, startY, endX, endY
+     */
+    private void getSelectionHandles(int[] handles) {
+        handles[0] = mSelectCursorBase.right;
+        handles[1] = mSelectCursorBase.bottom -
+                (mSelectCursorBase.height() / 4);
+        handles[2] = mSelectCursorExtent.left;
+        handles[3] = mSelectCursorExtent.bottom
+                - (mSelectCursorExtent.height() / 4);
+        if (!nativeIsBaseFirst(mNativeClass)) {
+            int swap = handles[0];
+            handles[0] = handles[2];
+            handles[2] = swap;
+            swap = handles[1];
+            handles[1] = handles[3];
+            handles[3] = swap;
+        }
+    }
+
+    // draw history
+    private boolean mDrawHistory = false;
+    private Picture mHistoryPicture = null;
+    private int mHistoryWidth = 0;
+    private int mHistoryHeight = 0;
+
+    // Only check the flag, can be called from WebCore thread
+    boolean drawHistory() {
+        return mDrawHistory;
+    }
+
+    int getHistoryPictureWidth() {
+        return (mHistoryPicture != null) ? mHistoryPicture.getWidth() : 0;
+    }
+
+    // Should only be called in UI thread
+    void switchOutDrawHistory() {
+        if (null == mWebViewCore) return; // CallbackProxy may trigger this
+        if (mDrawHistory && (getProgress() == 100 || nativeHasContent())) {
+            mDrawHistory = false;
+            mHistoryPicture = null;
+            invalidate();
+            int oldScrollX = getScrollX();
+            int oldScrollY = getScrollY();
+            setScrollXRaw(pinLocX(getScrollX()));
+            setScrollYRaw(pinLocY(getScrollY()));
+            if (oldScrollX != getScrollX() || oldScrollY != getScrollY()) {
+                mWebViewPrivate.onScrollChanged(getScrollX(), getScrollY(), oldScrollX, oldScrollY);
+            } else {
+                sendOurVisibleRect();
+            }
+        }
+    }
+
+    /**
+     *  Delete text from start to end in the focused textfield. If there is no
+     *  focus, or if start == end, silently fail.  If start and end are out of
+     *  order, swap them.
+     *  @param  start   Beginning of selection to delete.
+     *  @param  end     End of selection to delete.
+     */
+    /* package */ void deleteSelection(int start, int end) {
+        mTextGeneration++;
+        WebViewCore.TextSelectionData data
+                = new WebViewCore.TextSelectionData(start, end, 0);
+        mWebViewCore.sendMessage(EventHub.DELETE_SELECTION, mTextGeneration, 0,
+                data);
+    }
+
+    /**
+     *  Set the selection to (start, end) in the focused textfield. If start and
+     *  end are out of order, swap them.
+     *  @param  start   Beginning of selection.
+     *  @param  end     End of selection.
+     */
+    /* package */ void setSelection(int start, int end) {
+        if (mWebViewCore != null) {
+            mWebViewCore.sendMessage(EventHub.SET_SELECTION, start, end);
+        }
+    }
+
+    @Override
+    public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
+        if (mInputConnection == null) {
+            mInputConnection = new WebViewInputConnection();
+        }
+        mInputConnection.setupEditorInfo(outAttrs);
+        return mInputConnection;
+    }
+
+    /**
+     * Called in response to a message from webkit telling us that the soft
+     * keyboard should be launched.
+     */
+    private void displaySoftKeyboard(boolean isTextView) {
+        InputMethodManager imm = (InputMethodManager)
+                mContext.getSystemService(Context.INPUT_METHOD_SERVICE);
+
+        // bring it back to the default level scale so that user can enter text
+        boolean zoom = mZoomManager.getScale() < mZoomManager.getDefaultScale();
+        if (zoom) {
+            mZoomManager.setZoomCenter(mLastTouchX, mLastTouchY);
+            mZoomManager.setZoomScale(mZoomManager.getDefaultScale(), false);
+        }
+        // Used by plugins and contentEditable.
+        // Also used if the navigation cache is out of date, and
+        // does not recognize that a textfield is in focus.  In that
+        // case, use WebView as the targeted view.
+        // see http://b/issue?id=2457459
+        imm.showSoftInput(mWebView, 0);
+    }
+
+    // Called by WebKit to instruct the UI to hide the keyboard
+    private void hideSoftKeyboard() {
+        InputMethodManager imm = InputMethodManager.peekInstance();
+        if (imm != null && (imm.isActive(mWebView))) {
+            imm.hideSoftInputFromWindow(mWebView.getWindowToken(), 0);
+        }
+    }
+
+    /**
+     * Dump the display tree to "/sdcard/displayTree.txt"
+     *
+     * @hide debug only
+     */
+    public void dumpDisplayTree() {
+        nativeDumpDisplayTree(getUrl());
+    }
+
+    /**
+     * Dump the dom tree to adb shell if "toFile" is False, otherwise dump it to
+     * "/sdcard/domTree.txt"
+     *
+     * @hide debug only
+     */
+    public void dumpDomTree(boolean toFile) {
+        mWebViewCore.sendMessage(EventHub.DUMP_DOMTREE, toFile ? 1 : 0, 0);
+    }
+
+    /**
+     * Dump the render tree to adb shell if "toFile" is False, otherwise dump it
+     * to "/sdcard/renderTree.txt"
+     *
+     * @hide debug only
+     */
+    public void dumpRenderTree(boolean toFile) {
+        mWebViewCore.sendMessage(EventHub.DUMP_RENDERTREE, toFile ? 1 : 0, 0);
+    }
+
+    /**
+     * Called by DRT on UI thread, need to proxy to WebCore thread.
+     *
+     * @hide debug only
+     */
+    public void useMockDeviceOrientation() {
+        mWebViewCore.sendMessage(EventHub.USE_MOCK_DEVICE_ORIENTATION);
+    }
+
+    /**
+     * Called by DRT on WebCore thread.
+     *
+     * @hide debug only
+     */
+    public void setMockDeviceOrientation(boolean canProvideAlpha, double alpha,
+            boolean canProvideBeta, double beta, boolean canProvideGamma, double gamma) {
+        mWebViewCore.setMockDeviceOrientation(canProvideAlpha, alpha, canProvideBeta, beta,
+                canProvideGamma, gamma);
+    }
+
+    // This is used to determine long press with the center key.  Does not
+    // affect long press with the trackball/touch.
+    private boolean mGotCenterDown = false;
+
+    @Override
+    public boolean onKeyMultiple(int keyCode, int repeatCount, KeyEvent event) {
+        if (mBlockWebkitViewMessages) {
+            return false;
+        }
+        // send complex characters to webkit for use by JS and plugins
+        if (keyCode == KeyEvent.KEYCODE_UNKNOWN && event.getCharacters() != null) {
+            // pass the key to DOM
+            mWebViewCore.sendMessage(EventHub.KEY_DOWN, event);
+            mWebViewCore.sendMessage(EventHub.KEY_UP, event);
+            // return true as DOM handles the key
+            return true;
+        }
+        return false;
+    }
+
+    private boolean isEnterActionKey(int keyCode) {
+        return keyCode == KeyEvent.KEYCODE_DPAD_CENTER
+                || keyCode == KeyEvent.KEYCODE_ENTER
+                || keyCode == KeyEvent.KEYCODE_NUMPAD_ENTER;
+    }
+
+    @Override
+    public boolean onKeyDown(int keyCode, KeyEvent event) {
+        if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, "keyDown at " + System.currentTimeMillis()
+                    + "keyCode=" + keyCode
+                    + ", " + event + ", unicode=" + event.getUnicodeChar());
+        }
+        if (mIsCaretSelection) {
+            selectionDone();
+        }
+        if (mBlockWebkitViewMessages) {
+            return false;
+        }
+
+        // don't implement accelerator keys here; defer to host application
+        if (event.isCtrlPressed()) {
+            return false;
+        }
+
+        if (mNativeClass == 0) {
+            return false;
+        }
+
+        // do this hack up front, so it always works, regardless of touch-mode
+        if (AUTO_REDRAW_HACK && (keyCode == KeyEvent.KEYCODE_CALL)) {
+            mAutoRedraw = !mAutoRedraw;
+            if (mAutoRedraw) {
+                invalidate();
+            }
+            return true;
+        }
+
+        // Bubble up the key event if
+        // 1. it is a system key; or
+        // 2. the host application wants to handle it;
+        if (event.isSystem()
+                || mCallbackProxy.uiOverrideKeyEvent(event)) {
+            return false;
+        }
+
+        // accessibility support
+        if (accessibilityScriptInjected()) {
+            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
+                // if an accessibility script is injected we delegate to it the key handling.
+                // this script is a screen reader which is a fully fledged solution for blind
+                // users to navigate in and interact with web pages.
+                mWebViewCore.sendMessage(EventHub.KEY_DOWN, event);
+                return true;
+            } else {
+                // Clean up if accessibility was disabled after loading the current URL.
+                mAccessibilityScriptInjected = false;
+            }
+        } else if (mAccessibilityInjector != null) {
+            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
+                if (mAccessibilityInjector.onKeyEvent(event)) {
+                    // if an accessibility injector is present (no JavaScript enabled or the site
+                    // opts out injecting our JavaScript screen reader) we let it decide whether
+                    // to act on and consume the event.
+                    return true;
+                }
+            } else {
+                // Clean up if accessibility was disabled after loading the current URL.
+                mAccessibilityInjector = null;
+            }
+        }
+
+        if (keyCode == KeyEvent.KEYCODE_PAGE_UP) {
+            if (event.hasNoModifiers()) {
+                pageUp(false);
+                return true;
+            } else if (event.hasModifiers(KeyEvent.META_ALT_ON)) {
+                pageUp(true);
+                return true;
+            }
+        }
+
+        if (keyCode == KeyEvent.KEYCODE_PAGE_DOWN) {
+            if (event.hasNoModifiers()) {
+                pageDown(false);
+                return true;
+            } else if (event.hasModifiers(KeyEvent.META_ALT_ON)) {
+                pageDown(true);
+                return true;
+            }
+        }
+
+        if (keyCode == KeyEvent.KEYCODE_MOVE_HOME && event.hasNoModifiers()) {
+            pageUp(true);
+            return true;
+        }
+
+        if (keyCode == KeyEvent.KEYCODE_MOVE_END && event.hasNoModifiers()) {
+            pageDown(true);
+            return true;
+        }
+
+        if (keyCode >= KeyEvent.KEYCODE_DPAD_UP
+                && keyCode <= KeyEvent.KEYCODE_DPAD_RIGHT) {
+            switchOutDrawHistory();
+            letPageHandleNavKey(keyCode, event.getEventTime(), true, event.getMetaState());
+            return true;
+        }
+
+        if (isEnterActionKey(keyCode)) {
+            switchOutDrawHistory();
+            if (event.getRepeatCount() == 0) {
+                if (mSelectingText) {
+                    return true; // discard press if copy in progress
+                }
+                mGotCenterDown = true;
+                mPrivateHandler.sendMessageDelayed(mPrivateHandler
+                        .obtainMessage(LONG_PRESS_CENTER), LONG_PRESS_TIMEOUT);
+            }
+        }
+
+        if (getSettings().getNavDump()) {
+            switch (keyCode) {
+                case KeyEvent.KEYCODE_4:
+                    dumpDisplayTree();
+                    break;
+                case KeyEvent.KEYCODE_5:
+                case KeyEvent.KEYCODE_6:
+                    dumpDomTree(keyCode == KeyEvent.KEYCODE_5);
+                    break;
+                case KeyEvent.KEYCODE_7:
+                case KeyEvent.KEYCODE_8:
+                    dumpRenderTree(keyCode == KeyEvent.KEYCODE_7);
+                    break;
+            }
+        }
+
+        // pass the key to DOM
+        mWebViewCore.sendMessage(EventHub.KEY_DOWN, event);
+        // return true as DOM handles the key
+        return true;
+    }
+
+    @Override
+    public boolean onKeyUp(int keyCode, KeyEvent event) {
+        if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, "keyUp at " + System.currentTimeMillis()
+                    + ", " + event + ", unicode=" + event.getUnicodeChar());
+        }
+        if (mBlockWebkitViewMessages) {
+            return false;
+        }
+
+        if (mNativeClass == 0) {
+            return false;
+        }
+
+        // special CALL handling when cursor node's href is "tel:XXX"
+        if (keyCode == KeyEvent.KEYCODE_CALL
+                && mInitialHitTestResult != null
+                && mInitialHitTestResult.getType() == HitTestResult.PHONE_TYPE) {
+            String text = mInitialHitTestResult.getExtra();
+            Intent intent = new Intent(Intent.ACTION_DIAL, Uri.parse(text));
+            mContext.startActivity(intent);
+            return true;
+        }
+
+        // Bubble up the key event if
+        // 1. it is a system key; or
+        // 2. the host application wants to handle it;
+        if (event.isSystem()
+                || mCallbackProxy.uiOverrideKeyEvent(event)) {
+            return false;
+        }
+
+        // accessibility support
+        if (accessibilityScriptInjected()) {
+            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
+                // if an accessibility script is injected we delegate to it the key handling.
+                // this script is a screen reader which is a fully fledged solution for blind
+                // users to navigate in and interact with web pages.
+                mWebViewCore.sendMessage(EventHub.KEY_UP, event);
+                return true;
+            } else {
+                // Clean up if accessibility was disabled after loading the current URL.
+                mAccessibilityScriptInjected = false;
+            }
+        } else if (mAccessibilityInjector != null) {
+            if (AccessibilityManager.getInstance(mContext).isEnabled()) {
+                if (mAccessibilityInjector.onKeyEvent(event)) {
+                    // if an accessibility injector is present (no JavaScript enabled or the site
+                    // opts out injecting our JavaScript screen reader) we let it decide whether to
+                    // act on and consume the event.
+                    return true;
+                }
+            } else {
+                // Clean up if accessibility was disabled after loading the current URL.
+                mAccessibilityInjector = null;
+            }
+        }
+
+        if (keyCode >= KeyEvent.KEYCODE_DPAD_UP
+                && keyCode <= KeyEvent.KEYCODE_DPAD_RIGHT) {
+            letPageHandleNavKey(keyCode, event.getEventTime(), false, event.getMetaState());
+            return true;
+        }
+
+        if (isEnterActionKey(keyCode)) {
+            // remove the long press message first
+            mPrivateHandler.removeMessages(LONG_PRESS_CENTER);
+            mGotCenterDown = false;
+
+            if (mSelectingText) {
+                copySelection();
+                selectionDone();
+                return true; // discard press if copy in progress
+            }
+        }
+
+        // pass the key to DOM
+        mWebViewCore.sendMessage(EventHub.KEY_UP, event);
+        // return true as DOM handles the key
+        return true;
+    }
+
+    private boolean startSelectActionMode() {
+        mSelectCallback = new SelectActionModeCallback();
+        mSelectCallback.setTextSelected(!mIsCaretSelection);
+        mSelectCallback.setWebView(this);
+        if (mWebView.startActionMode(mSelectCallback) == null) {
+            // There is no ActionMode, so do not allow the user to modify a
+            // selection.
+            selectionDone();
+            return false;
+        }
+        mWebView.performHapticFeedback(HapticFeedbackConstants.LONG_PRESS);
+        return true;
+    }
+
+    private void showPasteWindow() {
+        ClipboardManager cm = (ClipboardManager)(mContext
+                .getSystemService(Context.CLIPBOARD_SERVICE));
+        if (cm.hasPrimaryClip()) {
+            Rect cursorRect = contentToViewRect(mSelectCursorBase);
+            int[] location = new int[2];
+            mWebView.getLocationInWindow(location);
+            cursorRect.offset(location[0] - getScrollX(), location[1] - getScrollY());
+            if (mPasteWindow == null) {
+                mPasteWindow = new PastePopupWindow();
+            }
+            mPasteWindow.show(cursorRect, location[0], location[1]);
+        }
+    }
+
+    private void hidePasteButton() {
+        if (mPasteWindow != null) {
+            mPasteWindow.hide();
+        }
+    }
+
+    private void syncSelectionCursors() {
+        mSelectCursorBaseLayerId =
+                nativeGetHandleLayerId(mNativeClass, HANDLE_ID_BASE, mSelectCursorBase);
+        mSelectCursorExtentLayerId =
+                nativeGetHandleLayerId(mNativeClass, HANDLE_ID_EXTENT, mSelectCursorExtent);
+    }
+
+    private boolean setupWebkitSelect() {
+        syncSelectionCursors();
+        if (mIsCaretSelection) {
+            showPasteWindow();
+        } else if (!startSelectActionMode()) {
+            selectionDone();
+            return false;
+        }
+        mSelectingText = true;
+        mTouchMode = TOUCH_DRAG_MODE;
+        return true;
+    }
+
+    private void updateWebkitSelection() {
+        int[] handles = null;
+        if (mIsCaretSelection) {
+            mSelectCursorExtent.set(mSelectCursorBase);
+        }
+        if (mSelectingText) {
+            handles = new int[4];
+            handles[0] = mSelectCursorBase.centerX();
+            handles[1] = mSelectCursorBase.centerY();
+            handles[2] = mSelectCursorExtent.centerX();
+            handles[3] = mSelectCursorExtent.centerY();
+        } else {
+            nativeSetTextSelection(mNativeClass, 0);
+        }
+        mWebViewCore.removeMessages(EventHub.SELECT_TEXT);
+        mWebViewCore.sendMessageAtFrontOfQueue(EventHub.SELECT_TEXT, handles);
+    }
+
+    private void resetCaretTimer() {
+        mPrivateHandler.removeMessages(CLEAR_CARET_HANDLE);
+        if (!mSelectionStarted) {
+            mPrivateHandler.sendEmptyMessageDelayed(CLEAR_CARET_HANDLE,
+                    CARET_HANDLE_STAMINA_MS);
+        }
+    }
+
+    /**
+     * Use this method to put the WebView into text selection mode.
+     * Do not rely on this functionality; it will be deprecated in the future.
+     * @deprecated This method is now obsolete.
+     */
+    @Deprecated
+    public void emulateShiftHeld() {
+        checkThread();
+    }
+
+    /**
+     * Select all of the text in this WebView.
+     *
+     * @hide This is an implementation detail.
+     */
+    public void selectAll() {
+        mWebViewCore.sendMessage(EventHub.SELECT_ALL);
+    }
+
+    /**
+     * Called when the selection has been removed.
+     */
+    void selectionDone() {
+        if (mSelectingText) {
+            hidePasteButton();
+            mSelectingText = false;
+            // finish is idempotent, so this is fine even if selectionDone was
+            // called by mSelectCallback.onDestroyActionMode
+            if (mSelectCallback != null) {
+                mSelectCallback.finish();
+                mSelectCallback = null;
+            }
+            if (!mIsCaretSelection) {
+                updateWebkitSelection();
+            }
+            mIsCaretSelection = false;
+            invalidate(); // redraw without selection
+            mAutoScrollX = 0;
+            mAutoScrollY = 0;
+            mSentAutoScrollMessage = false;
+        }
+    }
+
+    /**
+     * Copy the selection to the clipboard
+     *
+     * @hide This is an implementation detail.
+     */
+    public boolean copySelection() {
+        boolean copiedSomething = false;
+        String selection = getSelection();
+        if (selection != null && selection != "") {
+            if (DebugFlags.WEB_VIEW) {
+                Log.v(LOGTAG, "copySelection \"" + selection + "\"");
+            }
+            Toast.makeText(mContext
+                    , com.android.internal.R.string.text_copied
+                    , Toast.LENGTH_SHORT).show();
+            copiedSomething = true;
+            ClipboardManager cm = (ClipboardManager)mContext
+                    .getSystemService(Context.CLIPBOARD_SERVICE);
+            cm.setText(selection);
+            int[] handles = new int[4];
+            getSelectionHandles(handles);
+            mWebViewCore.sendMessage(EventHub.COPY_TEXT, handles);
+        }
+        invalidate(); // remove selection region and pointer
+        return copiedSomething;
+    }
+
+    /**
+     * Cut the selected text into the clipboard
+     *
+     * @hide This is an implementation detail
+     */
+    public void cutSelection() {
+        copySelection();
+        int[] handles = new int[4];
+        getSelectionHandles(handles);
+        mWebViewCore.sendMessage(EventHub.DELETE_TEXT, handles);
+    }
+
+    /**
+     * Paste text from the clipboard to the cursor position.
+     *
+     * @hide This is an implementation detail
+     */
+    public void pasteFromClipboard() {
+        ClipboardManager cm = (ClipboardManager)mContext
+                .getSystemService(Context.CLIPBOARD_SERVICE);
+        ClipData clipData = cm.getPrimaryClip();
+        if (clipData != null) {
+            ClipData.Item clipItem = clipData.getItemAt(0);
+            CharSequence pasteText = clipItem.getText();
+            if (mInputConnection != null) {
+                mInputConnection.replaceSelection(pasteText);
+            }
+        }
+    }
+
+    /**
+     * @hide This is an implementation detail.
+     */
+    public SearchBox getSearchBox() {
+        if ((mWebViewCore == null) || (mWebViewCore.getBrowserFrame() == null)) {
+            return null;
+        }
+        return mWebViewCore.getBrowserFrame().getSearchBox();
+    }
+
+    /**
+     * Returns the currently highlighted text as a string.
+     */
+    String getSelection() {
+        if (mNativeClass == 0) return "";
+        return nativeGetSelection();
+    }
+
+    @Override
+    public void onAttachedToWindow() {
+        if (mWebView.hasWindowFocus()) setActive(true);
+        final ViewTreeObserver treeObserver = mWebView.getViewTreeObserver();
+        if (mGlobalLayoutListener == null) {
+            mGlobalLayoutListener = new InnerGlobalLayoutListener();
+            treeObserver.addOnGlobalLayoutListener(mGlobalLayoutListener);
+        }
+        if (mScrollChangedListener == null) {
+            mScrollChangedListener = new InnerScrollChangedListener();
+            treeObserver.addOnScrollChangedListener(mScrollChangedListener);
+        }
+
+        addAccessibilityApisToJavaScript();
+
+        mTouchEventQueue.reset();
+    }
+
+    @Override
+    public void onDetachedFromWindow() {
+        clearHelpers();
+        mZoomManager.dismissZoomPicker();
+        if (mWebView.hasWindowFocus()) setActive(false);
+
+        final ViewTreeObserver treeObserver = mWebView.getViewTreeObserver();
+        if (mGlobalLayoutListener != null) {
+            treeObserver.removeGlobalOnLayoutListener(mGlobalLayoutListener);
+            mGlobalLayoutListener = null;
+        }
+        if (mScrollChangedListener != null) {
+            treeObserver.removeOnScrollChangedListener(mScrollChangedListener);
+            mScrollChangedListener = null;
+        }
+
+        removeAccessibilityApisFromJavaScript();
+    }
+
+    @Override
+    public void onVisibilityChanged(View changedView, int visibility) {
+        // The zoomManager may be null if the webview is created from XML that
+        // specifies the view's visibility param as not visible (see http://b/2794841)
+        if (visibility != View.VISIBLE && mZoomManager != null) {
+            mZoomManager.dismissZoomPicker();
+        }
+        updateDrawingState();
+    }
+
+    void setActive(boolean active) {
+        if (active) {
+            if (mWebView.hasFocus()) {
+                // If our window regained focus, and we have focus, then begin
+                // drawing the cursor ring
+                mDrawCursorRing = true;
+                setFocusControllerActive(true);
+            } else {
+                mDrawCursorRing = false;
+                setFocusControllerActive(false);
+            }
+        } else {
+            if (!mZoomManager.isZoomPickerVisible()) {
+                /*
+                 * The external zoom controls come in their own window, so our
+                 * window loses focus. Our policy is to not draw the cursor ring
+                 * if our window is not focused, but this is an exception since
+                 * the user can still navigate the web page with the zoom
+                 * controls showing.
+                 */
+                mDrawCursorRing = false;
+            }
+            mKeysPressed.clear();
+            mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+            mTouchMode = TOUCH_DONE_MODE;
+            setFocusControllerActive(false);
+        }
+        invalidate();
+    }
+
+    // To avoid drawing the cursor ring, and remove the TextView when our window
+    // loses focus.
+    @Override
+    public void onWindowFocusChanged(boolean hasWindowFocus) {
+        setActive(hasWindowFocus);
+        if (hasWindowFocus) {
+            JWebCoreJavaBridge.setActiveWebView(this);
+            if (mPictureUpdatePausedForFocusChange) {
+                WebViewCore.resumeUpdatePicture(mWebViewCore);
+                mPictureUpdatePausedForFocusChange = false;
+            }
+        } else {
+            JWebCoreJavaBridge.removeActiveWebView(this);
+            final WebSettings settings = getSettings();
+            if (settings != null && settings.enableSmoothTransition() &&
+                    mWebViewCore != null && !WebViewCore.isUpdatePicturePaused(mWebViewCore)) {
+                WebViewCore.pauseUpdatePicture(mWebViewCore);
+                mPictureUpdatePausedForFocusChange = true;
+            }
+        }
+    }
+
+    /*
+     * Pass a message to WebCore Thread, telling the WebCore::Page's
+     * FocusController to be  "inactive" so that it will
+     * not draw the blinking cursor.  It gets set to "active" to draw the cursor
+     * in WebViewCore.cpp, when the WebCore thread receives key events/clicks.
+     */
+    /* package */ void setFocusControllerActive(boolean active) {
+        if (mWebViewCore == null) return;
+        mWebViewCore.sendMessage(EventHub.SET_ACTIVE, active ? 1 : 0, 0);
+        // Need to send this message after the document regains focus.
+        if (active && mListBoxMessage != null) {
+            mWebViewCore.sendMessage(mListBoxMessage);
+            mListBoxMessage = null;
+        }
+    }
+
+    @Override
+    public void onFocusChanged(boolean focused, int direction,
+            Rect previouslyFocusedRect) {
+        if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, "MT focusChanged " + focused + ", " + direction);
+        }
+        if (focused) {
+            mDrawCursorRing = true;
+            setFocusControllerActive(true);
+        } else {
+            mDrawCursorRing = false;
+            setFocusControllerActive(false);
+            mKeysPressed.clear();
+        }
+    }
+
+    void setGLRectViewport() {
+        // Use the getGlobalVisibleRect() to get the intersection among the parents
+        // visible == false means we're clipped - send a null rect down to indicate that
+        // we should not draw
+        boolean visible = mWebView.getGlobalVisibleRect(mGLRectViewport);
+        if (visible) {
+            // Then need to invert the Y axis, just for GL
+            View rootView = mWebView.getRootView();
+            int rootViewHeight = rootView.getHeight();
+            mViewRectViewport.set(mGLRectViewport);
+            int savedWebViewBottom = mGLRectViewport.bottom;
+            mGLRectViewport.bottom = rootViewHeight - mGLRectViewport.top - getVisibleTitleHeightImpl();
+            mGLRectViewport.top = rootViewHeight - savedWebViewBottom;
+            mGLViewportEmpty = false;
+        } else {
+            mGLViewportEmpty = true;
+        }
+        calcOurContentVisibleRectF(mVisibleContentRect);
+        nativeUpdateDrawGLFunction(mGLViewportEmpty ? null : mGLRectViewport,
+                mGLViewportEmpty ? null : mViewRectViewport,
+                mVisibleContentRect, getScale());
+    }
+
+    /**
+     * @hide
+     */
+    @Override
+    public boolean setFrame(int left, int top, int right, int bottom) {
+        boolean changed = mWebViewPrivate.super_setFrame(left, top, right, bottom);
+        if (!changed && mHeightCanMeasure) {
+            // When mHeightCanMeasure is true, we will set mLastHeightSent to 0
+            // in WebViewCore after we get the first layout. We do call
+            // requestLayout() when we get contentSizeChanged(). But the View
+            // system won't call onSizeChanged if the dimension is not changed.
+            // In this case, we need to call sendViewSizeZoom() explicitly to
+            // notify the WebKit about the new dimensions.
+            sendViewSizeZoom(false);
+        }
+        setGLRectViewport();
+        return changed;
+    }
+
+    @Override
+    public void onSizeChanged(int w, int h, int ow, int oh) {
+        // adjust the max viewport width depending on the view dimensions. This
+        // is to ensure the scaling is not going insane. So do not shrink it if
+        // the view size is temporarily smaller, e.g. when soft keyboard is up.
+        int newMaxViewportWidth = (int) (Math.max(w, h) / mZoomManager.getDefaultMinZoomScale());
+        if (newMaxViewportWidth > sMaxViewportWidth) {
+            sMaxViewportWidth = newMaxViewportWidth;
+        }
+
+        mZoomManager.onSizeChanged(w, h, ow, oh);
+
+        if (mLoadedPicture != null && mDelaySetPicture == null) {
+            // Size changes normally result in a new picture
+            // Re-set the loaded picture to simulate that
+            // However, do not update the base layer as that hasn't changed
+            setNewPicture(mLoadedPicture, false);
+        }
+    }
+
+    @Override
+    public void onScrollChanged(int l, int t, int oldl, int oldt) {
+        if (!mInOverScrollMode) {
+            sendOurVisibleRect();
+            // update WebKit if visible title bar height changed. The logic is same
+            // as getVisibleTitleHeightImpl.
+            int titleHeight = getTitleHeight();
+            if (Math.max(titleHeight - t, 0) != Math.max(titleHeight - oldt, 0)) {
+                sendViewSizeZoom(false);
+            }
+        }
+    }
+
+    @Override
+    public boolean dispatchKeyEvent(KeyEvent event) {
+        switch (event.getAction()) {
+            case KeyEvent.ACTION_DOWN:
+                mKeysPressed.add(Integer.valueOf(event.getKeyCode()));
+                break;
+            case KeyEvent.ACTION_MULTIPLE:
+                // Always accept the action.
+                break;
+            case KeyEvent.ACTION_UP:
+                int location = mKeysPressed.indexOf(Integer.valueOf(event.getKeyCode()));
+                if (location == -1) {
+                    // We did not receive the key down for this key, so do not
+                    // handle the key up.
+                    return false;
+                } else {
+                    // We did receive the key down.  Handle the key up, and
+                    // remove it from our pressed keys.
+                    mKeysPressed.remove(location);
+                }
+                break;
+            default:
+                // Accept the action.  This should not happen, unless a new
+                // action is added to KeyEvent.
+                break;
+        }
+        return mWebViewPrivate.super_dispatchKeyEvent(event);
+    }
+
+    /*
+     * Here is the snap align logic:
+     * 1. If it starts nearly horizontally or vertically, snap align;
+     * 2. If there is a dramitic direction change, let it go;
+     *
+     * Adjustable parameters. Angle is the radians on a unit circle, limited
+     * to quadrant 1. Values range from 0f (horizontal) to PI/2 (vertical)
+     */
+    private static final float HSLOPE_TO_START_SNAP = .25f;
+    private static final float HSLOPE_TO_BREAK_SNAP = .4f;
+    private static final float VSLOPE_TO_START_SNAP = 1.25f;
+    private static final float VSLOPE_TO_BREAK_SNAP = .95f;
+    /*
+     *  These values are used to influence the average angle when entering
+     *  snap mode. If is is the first movement entering snap, we set the average
+     *  to the appropriate ideal. If the user is entering into snap after the
+     *  first movement, then we average the average angle with these values.
+     */
+    private static final float ANGLE_VERT = 2f;
+    private static final float ANGLE_HORIZ = 0f;
+    /*
+     *  The modified moving average weight.
+     *  Formula: MAV[t]=MAV[t-1] + (P[t]-MAV[t-1])/n
+     */
+    private static final float MMA_WEIGHT_N = 5;
+
+    private boolean hitFocusedPlugin(int contentX, int contentY) {
+        // TODO: Figure out what to do with this (b/6111517)
+        return false;
+    }
+
+    private boolean shouldForwardTouchEvent() {
+        if (mFullScreenHolder != null) return true;
+        if (mBlockWebkitViewMessages) return false;
+        return mForwardTouchEvents
+                && !mSelectingText
+                && mPreventDefault != PREVENT_DEFAULT_IGNORE
+                && mPreventDefault != PREVENT_DEFAULT_NO;
+    }
+
+    private boolean inFullScreenMode() {
+        return mFullScreenHolder != null;
+    }
+
+    private void dismissFullScreenMode() {
+        if (inFullScreenMode()) {
+            mFullScreenHolder.hide();
+            mFullScreenHolder = null;
+            invalidate();
+        }
+    }
+
+    void onPinchToZoomAnimationStart() {
+        // cancel the single touch handling
+        cancelTouch();
+        onZoomAnimationStart();
+    }
+
+    void onPinchToZoomAnimationEnd(ScaleGestureDetector detector) {
+        onZoomAnimationEnd();
+        // start a drag, TOUCH_PINCH_DRAG, can't use TOUCH_INIT_MODE as
+        // it may trigger the unwanted click, can't use TOUCH_DRAG_MODE
+        // as it may trigger the unwanted fling.
+        mTouchMode = TOUCH_PINCH_DRAG;
+        mConfirmMove = true;
+        startTouch(detector.getFocusX(), detector.getFocusY(), mLastTouchTime);
+    }
+
+    // See if there is a layer at x, y and switch to TOUCH_DRAG_LAYER_MODE if a
+    // layer is found.
+    private void startScrollingLayer(float x, float y) {
+        int contentX = viewToContentX((int) x + getScrollX());
+        int contentY = viewToContentY((int) y + getScrollY());
+        mCurrentScrollingLayerId = nativeScrollableLayer(contentX, contentY,
+                mScrollingLayerRect, mScrollingLayerBounds);
+        if (mCurrentScrollingLayerId != 0) {
+            mTouchMode = TOUCH_DRAG_LAYER_MODE;
+        }
+    }
+
+    // 1/(density * density) used to compute the distance between points.
+    // Computed in init().
+    private float DRAG_LAYER_INVERSE_DENSITY_SQUARED;
+
+    // The distance between two points reported in onTouchEvent scaled by the
+    // density of the screen.
+    private static final int DRAG_LAYER_FINGER_DISTANCE = 20000;
+
+    @Override
+    public boolean onHoverEvent(MotionEvent event) {
+        if (mNativeClass == 0) {
+            return false;
+        }
+        int x = viewToContentX((int) event.getX() + getScrollX());
+        int y = viewToContentY((int) event.getY() + getScrollY());
+        mWebViewCore.sendMessage(EventHub.SET_MOVE_MOUSE, x, y);
+        return true;
+    }
+
+    @Override
+    public boolean onTouchEvent(MotionEvent ev) {
+        if (mNativeClass == 0 || (!mWebView.isClickable() && !mWebView.isLongClickable())) {
+            return false;
+        }
+
+        if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, ev + " at " + ev.getEventTime()
+                + " mTouchMode=" + mTouchMode
+                + " numPointers=" + ev.getPointerCount());
+        }
+
+        // If WebKit wasn't interested in this multitouch gesture, enqueue
+        // the event for handling directly rather than making the round trip
+        // to WebKit and back.
+        if (ev.getPointerCount() > 1 && mPreventDefault != PREVENT_DEFAULT_NO) {
+            passMultiTouchToWebKit(ev, mTouchEventQueue.nextTouchSequence());
+        } else {
+            mTouchEventQueue.enqueueTouchEvent(ev);
+        }
+
+        // Since all events are handled asynchronously, we always want the gesture stream.
+        return true;
+    }
+
+    private float calculateDragAngle(int dx, int dy) {
+        dx = Math.abs(dx);
+        dy = Math.abs(dy);
+        return (float) Math.atan2(dy, dx);
+    }
+
+    /*
+     * Common code for single touch and multi-touch.
+     * (x, y) denotes current focus point, which is the touch point for single touch
+     * and the middle point for multi-touch.
+     */
+    private boolean handleTouchEventCommon(MotionEvent ev, int action, int x, int y) {
+        long eventTime = ev.getEventTime();
+
+        // Due to the touch screen edge effect, a touch closer to the edge
+        // always snapped to the edge. As getViewWidth() can be different from
+        // getWidth() due to the scrollbar, adjusting the point to match
+        // getViewWidth(). Same applied to the height.
+        x = Math.min(x, getViewWidth() - 1);
+        y = Math.min(y, getViewHeightWithTitle() - 1);
+
+        int deltaX = mLastTouchX - x;
+        int deltaY = mLastTouchY - y;
+        int contentX = viewToContentX(x + getScrollX());
+        int contentY = viewToContentY(y + getScrollY());
+
+        switch (action) {
+            case MotionEvent.ACTION_DOWN: {
+                mPreventDefault = PREVENT_DEFAULT_NO;
+                mConfirmMove = false;
+                mInitialHitTestResult = null;
+                if (!mScroller.isFinished()) {
+                    // stop the current scroll animation, but if this is
+                    // the start of a fling, allow it to add to the current
+                    // fling's velocity
+                    mScroller.abortAnimation();
+                    mTouchMode = TOUCH_DRAG_START_MODE;
+                    mConfirmMove = true;
+                    nativeSetIsScrolling(false);
+                } else if (mPrivateHandler.hasMessages(RELEASE_SINGLE_TAP)) {
+                    mPrivateHandler.removeMessages(RELEASE_SINGLE_TAP);
+                    removeTouchHighlight();
+                    if (deltaX * deltaX + deltaY * deltaY < mDoubleTapSlopSquare) {
+                        mTouchMode = TOUCH_DOUBLE_TAP_MODE;
+                    } else {
+                        // commit the short press action for the previous tap
+                        doShortPress();
+                        mTouchMode = TOUCH_INIT_MODE;
+                        mDeferTouchProcess = !mBlockWebkitViewMessages
+                                && (!inFullScreenMode() && mForwardTouchEvents)
+                                ? hitFocusedPlugin(contentX, contentY)
+                                : false;
+                    }
+                } else { // the normal case
+                    mTouchMode = TOUCH_INIT_MODE;
+                    mDeferTouchProcess = !mBlockWebkitViewMessages
+                            && (!inFullScreenMode() && mForwardTouchEvents)
+                            ? hitFocusedPlugin(contentX, contentY)
+                            : false;
+                    TouchHighlightData data = new TouchHighlightData();
+                    data.mX = contentX;
+                    data.mY = contentY;
+                    data.mNativeLayerRect = new Rect();
+                    data.mNativeLayer = nativeScrollableLayer(
+                            contentX, contentY, data.mNativeLayerRect, null);
+                    data.mSlop = viewToContentDimension(mNavSlop);
+                    mTouchHighlightRegion.setEmpty();
+                    if (!mBlockWebkitViewMessages) {
+                        mTouchHighlightRequested = System.currentTimeMillis();
+                        mWebViewCore.sendMessageAtFrontOfQueue(
+                                EventHub.HIT_TEST, data);
+                    }
+                    if (DEBUG_TOUCH_HIGHLIGHT) {
+                        if (getSettings().getNavDump()) {
+                            mTouchHighlightX = x + getScrollX();
+                            mTouchHighlightY = y + getScrollY();
+                            mPrivateHandler.postDelayed(new Runnable() {
+                                @Override
+                                public void run() {
+                                    mTouchHighlightX = mTouchHighlightY = 0;
+                                    invalidate();
+                                }
+                            }, TOUCH_HIGHLIGHT_ELAPSE_TIME);
+                        }
+                    }
+                    if (mLogEvent && eventTime - mLastTouchUpTime < 1000) {
+                        EventLog.writeEvent(EventLogTags.BROWSER_DOUBLE_TAP_DURATION,
+                                (eventTime - mLastTouchUpTime), eventTime);
+                    }
+                    mSelectionStarted = false;
+                    if (mSelectingText) {
+                        int shiftedY = y - getTitleHeight() + getScrollY();
+                        int shiftedX = x + getScrollX();
+                        if (mSelectHandleCenter != null && mSelectHandleCenter.getBounds()
+                                .contains(shiftedX, shiftedY)) {
+                            mSelectionStarted = true;
+                            mSelectDraggingCursor = mSelectCursorBase;
+                            mPrivateHandler.removeMessages(CLEAR_CARET_HANDLE);
+                            hidePasteButton();
+                        } else if (mSelectHandleLeft != null
+                                && mSelectHandleLeft.getBounds()
+                                    .contains(shiftedX, shiftedY)) {
+                                mSelectionStarted = true;
+                                mSelectDraggingCursor = mSelectCursorBase;
+                        } else if (mSelectHandleRight != null
+                                && mSelectHandleRight.getBounds()
+                                .contains(shiftedX, shiftedY)) {
+                            mSelectionStarted = true;
+                            mSelectDraggingCursor = mSelectCursorExtent;
+                        } else if (mIsCaretSelection) {
+                            selectionDone();
+                        }
+                        if (mSelectDraggingCursor != null) {
+                            mSelectDraggingOffset.set(
+                                    mSelectDraggingCursor.left - contentX,
+                                    mSelectDraggingCursor.top - contentY);
+                        }
+                        if (DebugFlags.WEB_VIEW) {
+                            Log.v(LOGTAG, "select=" + contentX + "," + contentY);
+                        }
+                    }
+                }
+                // Trigger the link
+                if (!mSelectingText && (mTouchMode == TOUCH_INIT_MODE
+                        || mTouchMode == TOUCH_DOUBLE_TAP_MODE)) {
+                    mPrivateHandler.sendEmptyMessageDelayed(
+                            SWITCH_TO_SHORTPRESS, TAP_TIMEOUT);
+                    mPrivateHandler.sendEmptyMessageDelayed(
+                            SWITCH_TO_LONGPRESS, LONG_PRESS_TIMEOUT);
+                    if (inFullScreenMode() || mDeferTouchProcess) {
+                        mPreventDefault = PREVENT_DEFAULT_YES;
+                    } else if (!mBlockWebkitViewMessages && mForwardTouchEvents) {
+                        mPreventDefault = PREVENT_DEFAULT_MAYBE_YES;
+                    } else {
+                        mPreventDefault = PREVENT_DEFAULT_NO;
+                    }
+                    // pass the touch events from UI thread to WebCore thread
+                    if (shouldForwardTouchEvent()) {
+                        TouchEventData ted = new TouchEventData();
+                        ted.mAction = action;
+                        ted.mIds = new int[1];
+                        ted.mIds[0] = ev.getPointerId(0);
+                        ted.mPoints = new Point[1];
+                        ted.mPoints[0] = new Point(contentX, contentY);
+                        ted.mPointsInView = new Point[1];
+                        ted.mPointsInView[0] = new Point(x, y);
+                        ted.mMetaState = ev.getMetaState();
+                        ted.mReprocess = mDeferTouchProcess;
+                        ted.mNativeLayer = nativeScrollableLayer(
+                                contentX, contentY, ted.mNativeLayerRect, null);
+                        ted.mSequence = mTouchEventQueue.nextTouchSequence();
+                        mTouchEventQueue.preQueueTouchEventData(ted);
+                        mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
+                        if (mDeferTouchProcess) {
+                            // still needs to set them for compute deltaX/Y
+                            mLastTouchX = x;
+                            mLastTouchY = y;
+                            break;
+                        }
+                        if (!inFullScreenMode()) {
+                            mPrivateHandler.removeMessages(PREVENT_DEFAULT_TIMEOUT);
+                            mPrivateHandler.sendMessageDelayed(mPrivateHandler
+                                    .obtainMessage(PREVENT_DEFAULT_TIMEOUT,
+                                            action, 0), TAP_TIMEOUT);
+                        }
+                    }
+                }
+                startTouch(x, y, eventTime);
+                break;
+            }
+            case MotionEvent.ACTION_MOVE: {
+                boolean firstMove = false;
+                if (!mConfirmMove && (deltaX * deltaX + deltaY * deltaY)
+                        >= mTouchSlopSquare) {
+                    mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
+                    mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+                    mConfirmMove = true;
+                    firstMove = true;
+                    if (mTouchMode == TOUCH_DOUBLE_TAP_MODE) {
+                        mTouchMode = TOUCH_INIT_MODE;
+                    }
+                    removeTouchHighlight();
+                }
+                if (mSelectingText && mSelectionStarted) {
+                    if (DebugFlags.WEB_VIEW) {
+                        Log.v(LOGTAG, "extend=" + contentX + "," + contentY);
+                    }
+                    ViewParent parent = mWebView.getParent();
+                    if (parent != null) {
+                        parent.requestDisallowInterceptTouchEvent(true);
+                    }
+                    if (deltaX != 0 || deltaY != 0) {
+                        mSelectDraggingCursor.offsetTo(
+                                contentX + mSelectDraggingOffset.x,
+                                contentY + mSelectDraggingOffset.y);
+                        updateWebkitSelection();
+                        mLastTouchX = x;
+                        mLastTouchY = y;
+                        invalidate();
+                    }
+                    break;
+                }
+
+                // pass the touch events from UI thread to WebCore thread
+                if (shouldForwardTouchEvent() && mConfirmMove && (firstMove
+                        || eventTime - mLastSentTouchTime > mCurrentTouchInterval)) {
+                    TouchEventData ted = new TouchEventData();
+                    ted.mAction = action;
+                    ted.mIds = new int[1];
+                    ted.mIds[0] = ev.getPointerId(0);
+                    ted.mPoints = new Point[1];
+                    ted.mPoints[0] = new Point(contentX, contentY);
+                    ted.mPointsInView = new Point[1];
+                    ted.mPointsInView[0] = new Point(x, y);
+                    ted.mMetaState = ev.getMetaState();
+                    ted.mReprocess = mDeferTouchProcess;
+                    ted.mNativeLayer = mCurrentScrollingLayerId;
+                    ted.mNativeLayerRect.set(mScrollingLayerRect);
+                    ted.mSequence = mTouchEventQueue.nextTouchSequence();
+                    mTouchEventQueue.preQueueTouchEventData(ted);
+                    mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
+                    mLastSentTouchTime = eventTime;
+                    if (mDeferTouchProcess) {
+                        break;
+                    }
+                    if (firstMove && !inFullScreenMode()) {
+                        mPrivateHandler.sendMessageDelayed(mPrivateHandler
+                                .obtainMessage(PREVENT_DEFAULT_TIMEOUT,
+                                        action, 0), TAP_TIMEOUT);
+                    }
+                }
+                if (mTouchMode == TOUCH_DONE_MODE
+                        || mPreventDefault == PREVENT_DEFAULT_YES) {
+                    // no dragging during scroll zoom animation, or when prevent
+                    // default is yes
+                    break;
+                }
+                if (mVelocityTracker == null) {
+                    Log.e(LOGTAG, "Got null mVelocityTracker when "
+                            + "mPreventDefault = " + mPreventDefault
+                            + " mDeferTouchProcess = " + mDeferTouchProcess
+                            + " mTouchMode = " + mTouchMode);
+                } else {
+                    mVelocityTracker.addMovement(ev);
+                }
+
+                if (mTouchMode != TOUCH_DRAG_MODE &&
+                        mTouchMode != TOUCH_DRAG_LAYER_MODE) {
+
+                    if (!mConfirmMove) {
+                        break;
+                    }
+
+                    if (mPreventDefault == PREVENT_DEFAULT_MAYBE_YES
+                            || mPreventDefault == PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN) {
+                        // track mLastTouchTime as we may need to do fling at
+                        // ACTION_UP
+                        mLastTouchTime = eventTime;
+                        break;
+                    }
+
+                    // Only lock dragging to one axis if we don't have a scale in progress.
+                    // Scaling implies free-roaming movement. Note this is only ever a question
+                    // if mZoomManager.supportsPanDuringZoom() is true.
+                    final ScaleGestureDetector detector =
+                      mZoomManager.getMultiTouchGestureDetector();
+                    mAverageAngle = calculateDragAngle(deltaX, deltaY);
+                    if (detector == null || !detector.isInProgress()) {
+                        // if it starts nearly horizontal or vertical, enforce it
+                        if (mAverageAngle < HSLOPE_TO_START_SNAP) {
+                            mSnapScrollMode = SNAP_X;
+                            mSnapPositive = deltaX > 0;
+                            mAverageAngle = ANGLE_HORIZ;
+                        } else if (mAverageAngle > VSLOPE_TO_START_SNAP) {
+                            mSnapScrollMode = SNAP_Y;
+                            mSnapPositive = deltaY > 0;
+                            mAverageAngle = ANGLE_VERT;
+                        }
+                    }
+
+                    mTouchMode = TOUCH_DRAG_MODE;
+                    mLastTouchX = x;
+                    mLastTouchY = y;
+                    deltaX = 0;
+                    deltaY = 0;
+
+                    startScrollingLayer(x, y);
+                    startDrag();
+                }
+
+                // do pan
+                boolean done = false;
+                boolean keepScrollBarsVisible = false;
+                if (deltaX == 0 && deltaY == 0) {
+                    keepScrollBarsVisible = done = true;
+                } else {
+                    mAverageAngle +=
+                        (calculateDragAngle(deltaX, deltaY) - mAverageAngle)
+                        / MMA_WEIGHT_N;
+                    if (mSnapScrollMode != SNAP_NONE) {
+                        if (mSnapScrollMode == SNAP_Y) {
+                            // radical change means getting out of snap mode
+                            if (mAverageAngle < VSLOPE_TO_BREAK_SNAP) {
+                                mSnapScrollMode = SNAP_NONE;
+                            }
+                        }
+                        if (mSnapScrollMode == SNAP_X) {
+                            // radical change means getting out of snap mode
+                            if (mAverageAngle > HSLOPE_TO_BREAK_SNAP) {
+                                mSnapScrollMode = SNAP_NONE;
+                            }
+                        }
+                    } else {
+                        if (mAverageAngle < HSLOPE_TO_START_SNAP) {
+                            mSnapScrollMode = SNAP_X;
+                            mSnapPositive = deltaX > 0;
+                            mAverageAngle = (mAverageAngle + ANGLE_HORIZ) / 2;
+                        } else if (mAverageAngle > VSLOPE_TO_START_SNAP) {
+                            mSnapScrollMode = SNAP_Y;
+                            mSnapPositive = deltaY > 0;
+                            mAverageAngle = (mAverageAngle + ANGLE_VERT) / 2;
+                        }
+                    }
+                    if (mSnapScrollMode != SNAP_NONE) {
+                        if ((mSnapScrollMode & SNAP_X) == SNAP_X) {
+                            deltaY = 0;
+                        } else {
+                            deltaX = 0;
+                        }
+                    }
+                    mLastTouchX = x;
+                    mLastTouchY = y;
+
+                    if (deltaX * deltaX + deltaY * deltaY > mTouchSlopSquare) {
+                        mHeldMotionless = MOTIONLESS_FALSE;
+                        nativeSetIsScrolling(true);
+                    } else {
+                        mHeldMotionless = MOTIONLESS_TRUE;
+                        nativeSetIsScrolling(false);
+                        keepScrollBarsVisible = true;
+                    }
+
+                    mLastTouchTime = eventTime;
+                }
+
+                doDrag(deltaX, deltaY);
+
+                // Turn off scrollbars when dragging a layer.
+                if (keepScrollBarsVisible &&
+                        mTouchMode != TOUCH_DRAG_LAYER_MODE) {
+                    if (mHeldMotionless != MOTIONLESS_TRUE) {
+                        mHeldMotionless = MOTIONLESS_TRUE;
+                        invalidate();
+                    }
+                    // keep the scrollbar on the screen even there is no scroll
+                    mWebViewPrivate.awakenScrollBars(ViewConfiguration.getScrollDefaultDelay(),
+                            false);
+                    // Post a message so that we'll keep them alive while we're not scrolling.
+                    mPrivateHandler.sendMessageDelayed(mPrivateHandler
+                            .obtainMessage(AWAKEN_SCROLL_BARS),
+                            ViewConfiguration.getScrollDefaultDelay());
+                    // return false to indicate that we can't pan out of the
+                    // view space
+                    return !done;
+                } else {
+                    mPrivateHandler.removeMessages(AWAKEN_SCROLL_BARS);
+                }
+                break;
+            }
+            case MotionEvent.ACTION_UP: {
+                if (!mWebView.isFocused()) mWebView.requestFocus();
+                // pass the touch events from UI thread to WebCore thread
+                if (shouldForwardTouchEvent()) {
+                    TouchEventData ted = new TouchEventData();
+                    ted.mIds = new int[1];
+                    ted.mIds[0] = ev.getPointerId(0);
+                    ted.mAction = action;
+                    ted.mPoints = new Point[1];
+                    ted.mPoints[0] = new Point(contentX, contentY);
+                    ted.mPointsInView = new Point[1];
+                    ted.mPointsInView[0] = new Point(x, y);
+                    ted.mMetaState = ev.getMetaState();
+                    ted.mReprocess = mDeferTouchProcess;
+                    ted.mNativeLayer = mCurrentScrollingLayerId;
+                    ted.mNativeLayerRect.set(mScrollingLayerRect);
+                    ted.mSequence = mTouchEventQueue.nextTouchSequence();
+                    mTouchEventQueue.preQueueTouchEventData(ted);
+                    mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
+                }
+                mLastTouchUpTime = eventTime;
+                if (mSentAutoScrollMessage) {
+                    mAutoScrollX = mAutoScrollY = 0;
+                }
+                switch (mTouchMode) {
+                    case TOUCH_DOUBLE_TAP_MODE: // double tap
+                        mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
+                        mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+                        if (inFullScreenMode() || mDeferTouchProcess) {
+                            TouchEventData ted = new TouchEventData();
+                            ted.mIds = new int[1];
+                            ted.mIds[0] = ev.getPointerId(0);
+                            ted.mAction = WebViewCore.ACTION_DOUBLETAP;
+                            ted.mPoints = new Point[1];
+                            ted.mPoints[0] = new Point(contentX, contentY);
+                            ted.mPointsInView = new Point[1];
+                            ted.mPointsInView[0] = new Point(x, y);
+                            ted.mMetaState = ev.getMetaState();
+                            ted.mReprocess = mDeferTouchProcess;
+                            ted.mNativeLayer = nativeScrollableLayer(
+                                    contentX, contentY,
+                                    ted.mNativeLayerRect, null);
+                            ted.mSequence = mTouchEventQueue.nextTouchSequence();
+                            mTouchEventQueue.preQueueTouchEventData(ted);
+                            mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
+                        } else if (mPreventDefault != PREVENT_DEFAULT_YES){
+                            mZoomManager.handleDoubleTap(mLastTouchX, mLastTouchY);
+                            mTouchMode = TOUCH_DONE_MODE;
+                        }
+                        break;
+                    case TOUCH_INIT_MODE: // tap
+                    case TOUCH_SHORTPRESS_START_MODE:
+                    case TOUCH_SHORTPRESS_MODE:
+                        mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
+                        mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+                        if (mConfirmMove) {
+                            Log.w(LOGTAG, "Miss a drag as we are waiting for" +
+                                    " WebCore's response for touch down.");
+                            if (mPreventDefault != PREVENT_DEFAULT_YES
+                                    && (computeMaxScrollX() > 0
+                                            || computeMaxScrollY() > 0)) {
+                                // If the user has performed a very quick touch
+                                // sequence it is possible that we may get here
+                                // before WebCore has had a chance to process the events.
+                                // In this case, any call to preventDefault in the
+                                // JS touch handler will not have been executed yet.
+                                // Hence we will see both the UI (now) and WebCore
+                                // (when context switches) handling the event,
+                                // regardless of whether the web developer actually
+                                // doeses preventDefault in their touch handler. This
+                                // is the nature of our asynchronous touch model.
+
+                                // we will not rewrite drag code here, but we
+                                // will try fling if it applies.
+                                WebViewCore.reducePriority();
+                                // to get better performance, pause updating the
+                                // picture
+                                WebViewCore.pauseUpdatePicture(mWebViewCore);
+                                // fall through to TOUCH_DRAG_MODE
+                            } else {
+                                // WebKit may consume the touch event and modify
+                                // DOM. drawContentPicture() will be called with
+                                // animateSroll as true for better performance.
+                                // Force redraw in high-quality.
+                                invalidate();
+                                break;
+                            }
+                        } else {
+                            if (mSelectingText) {
+                                // tapping on selection or controls does nothing
+                                if (!mSelectionStarted) {
+                                    selectionDone();
+                                }
+                                break;
+                            }
+                            // only trigger double tap if the WebView is
+                            // scalable
+                            if (mTouchMode == TOUCH_INIT_MODE
+                                    && (canZoomIn() || canZoomOut())) {
+                                mPrivateHandler.sendEmptyMessageDelayed(
+                                        RELEASE_SINGLE_TAP, ViewConfiguration
+                                                .getDoubleTapTimeout());
+                            } else {
+                                doShortPress();
+                            }
+                            break;
+                        }
+                    case TOUCH_DRAG_MODE:
+                    case TOUCH_DRAG_LAYER_MODE:
+                        mPrivateHandler.removeMessages(DRAG_HELD_MOTIONLESS);
+                        mPrivateHandler.removeMessages(AWAKEN_SCROLL_BARS);
+                        // if the user waits a while w/o moving before the
+                        // up, we don't want to do a fling
+                        if (eventTime - mLastTouchTime <= MIN_FLING_TIME) {
+                            if (mVelocityTracker == null) {
+                                Log.e(LOGTAG, "Got null mVelocityTracker when "
+                                        + "mPreventDefault = "
+                                        + mPreventDefault
+                                        + " mDeferTouchProcess = "
+                                        + mDeferTouchProcess);
+                            } else {
+                                mVelocityTracker.addMovement(ev);
+                            }
+                            // set to MOTIONLESS_IGNORE so that it won't keep
+                            // removing and sending message in
+                            // drawCoreAndCursorRing()
+                            mHeldMotionless = MOTIONLESS_IGNORE;
+                            doFling();
+                            break;
+                        } else {
+                            if (mScroller.springBack(getScrollX(), getScrollY(), 0,
+                                    computeMaxScrollX(), 0,
+                                    computeMaxScrollY())) {
+                                invalidate();
+                            }
+                        }
+                        // redraw in high-quality, as we're done dragging
+                        mHeldMotionless = MOTIONLESS_TRUE;
+                        invalidate();
+                        // fall through
+                    case TOUCH_DRAG_START_MODE:
+                        // TOUCH_DRAG_START_MODE should not happen for the real
+                        // device as we almost certain will get a MOVE. But this
+                        // is possible on emulator.
+                        mLastVelocity = 0;
+                        WebViewCore.resumePriority();
+                        if (!mSelectingText) {
+                            WebViewCore.resumeUpdatePicture(mWebViewCore);
+                        }
+                        break;
+                }
+                stopTouch();
+                break;
+            }
+            case MotionEvent.ACTION_CANCEL: {
+                if (mTouchMode == TOUCH_DRAG_MODE) {
+                    mScroller.springBack(getScrollX(), getScrollY(), 0,
+                            computeMaxScrollX(), 0, computeMaxScrollY());
+                    invalidate();
+                }
+                cancelWebCoreTouchEvent(contentX, contentY, false);
+                cancelTouch();
+                break;
+            }
+        }
+        return true;
+    }
+
+    private void passMultiTouchToWebKit(MotionEvent ev, long sequence) {
+        TouchEventData ted = new TouchEventData();
+        ted.mAction = ev.getActionMasked();
+        final int count = ev.getPointerCount();
+        ted.mIds = new int[count];
+        ted.mPoints = new Point[count];
+        ted.mPointsInView = new Point[count];
+        for (int c = 0; c < count; c++) {
+            ted.mIds[c] = ev.getPointerId(c);
+            int x = viewToContentX((int) ev.getX(c) + getScrollX());
+            int y = viewToContentY((int) ev.getY(c) + getScrollY());
+            ted.mPoints[c] = new Point(x, y);
+            ted.mPointsInView[c] = new Point((int) ev.getX(c), (int) ev.getY(c));
+        }
+        if (ted.mAction == MotionEvent.ACTION_POINTER_DOWN
+            || ted.mAction == MotionEvent.ACTION_POINTER_UP) {
+            ted.mActionIndex = ev.getActionIndex();
+        }
+        ted.mMetaState = ev.getMetaState();
+        ted.mReprocess = true;
+        ted.mMotionEvent = MotionEvent.obtain(ev);
+        ted.mSequence = sequence;
+        mTouchEventQueue.preQueueTouchEventData(ted);
+        mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
+        mWebView.cancelLongPress();
+        mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+    }
+
+    void handleMultiTouchInWebView(MotionEvent ev) {
+        if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, "multi-touch: " + ev + " at " + ev.getEventTime()
+                + " mTouchMode=" + mTouchMode
+                + " numPointers=" + ev.getPointerCount()
+                + " scrolloffset=(" + getScrollX() + "," + getScrollY() + ")");
+        }
+
+        final ScaleGestureDetector detector =
+            mZoomManager.getMultiTouchGestureDetector();
+
+        // A few apps use WebView but don't instantiate gesture detector.
+        // We don't need to support multi touch for them.
+        if (detector == null) return;
+
+        float x = ev.getX();
+        float y = ev.getY();
+
+        if (mPreventDefault != PREVENT_DEFAULT_YES) {
+            detector.onTouchEvent(ev);
+
+            if (detector.isInProgress()) {
+                if (DebugFlags.WEB_VIEW) {
+                    Log.v(LOGTAG, "detector is in progress");
+                }
+                mLastTouchTime = ev.getEventTime();
+                x = detector.getFocusX();
+                y = detector.getFocusY();
+
+                mWebView.cancelLongPress();
+                mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+                if (!mZoomManager.supportsPanDuringZoom()) {
+                    return;
+                }
+                mTouchMode = TOUCH_DRAG_MODE;
+                if (mVelocityTracker == null) {
+                    mVelocityTracker = VelocityTracker.obtain();
+                }
+            }
+        }
+
+        int action = ev.getActionMasked();
+        if (action == MotionEvent.ACTION_POINTER_DOWN) {
+            cancelTouch();
+            action = MotionEvent.ACTION_DOWN;
+        } else if (action == MotionEvent.ACTION_POINTER_UP && ev.getPointerCount() >= 2) {
+            // set mLastTouchX/Y to the remaining points for multi-touch.
+            mLastTouchX = Math.round(x);
+            mLastTouchY = Math.round(y);
+        } else if (action == MotionEvent.ACTION_MOVE) {
+            // negative x or y indicate it is on the edge, skip it.
+            if (x < 0 || y < 0) {
+                return;
+            }
+        }
+
+        handleTouchEventCommon(ev, action, Math.round(x), Math.round(y));
+    }
+
+    private void cancelWebCoreTouchEvent(int x, int y, boolean removeEvents) {
+        if (shouldForwardTouchEvent()) {
+            if (removeEvents) {
+                mWebViewCore.removeMessages(EventHub.TOUCH_EVENT);
+            }
+            TouchEventData ted = new TouchEventData();
+            ted.mIds = new int[1];
+            ted.mIds[0] = 0;
+            ted.mPoints = new Point[1];
+            ted.mPoints[0] = new Point(x, y);
+            ted.mPointsInView = new Point[1];
+            int viewX = contentToViewX(x) - getScrollX();
+            int viewY = contentToViewY(y) - getScrollY();
+            ted.mPointsInView[0] = new Point(viewX, viewY);
+            ted.mAction = MotionEvent.ACTION_CANCEL;
+            ted.mNativeLayer = nativeScrollableLayer(
+                    x, y, ted.mNativeLayerRect, null);
+            ted.mSequence = mTouchEventQueue.nextTouchSequence();
+            mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
+            mPreventDefault = PREVENT_DEFAULT_IGNORE;
+
+            if (removeEvents) {
+                // Mark this after sending the message above; we should
+                // be willing to ignore the cancel event that we just sent.
+                mTouchEventQueue.ignoreCurrentlyMissingEvents();
+            }
+        }
+    }
+
+    private void startTouch(float x, float y, long eventTime) {
+        // Remember where the motion event started
+        mStartTouchX = mLastTouchX = Math.round(x);
+        mStartTouchY = mLastTouchY = Math.round(y);
+        mLastTouchTime = eventTime;
+        mVelocityTracker = VelocityTracker.obtain();
+        mSnapScrollMode = SNAP_NONE;
+    }
+
+    private void startDrag() {
+        WebViewCore.reducePriority();
+        // to get better performance, pause updating the picture
+        WebViewCore.pauseUpdatePicture(mWebViewCore);
+        nativeSetIsScrolling(true);
+
+        if (mHorizontalScrollBarMode != SCROLLBAR_ALWAYSOFF
+                || mVerticalScrollBarMode != SCROLLBAR_ALWAYSOFF) {
+            mZoomManager.invokeZoomPicker();
+        }
+    }
+
+    private void doDrag(int deltaX, int deltaY) {
+        if ((deltaX | deltaY) != 0) {
+            int oldX = getScrollX();
+            int oldY = getScrollY();
+            int rangeX = computeMaxScrollX();
+            int rangeY = computeMaxScrollY();
+            // Check for the original scrolling layer in case we change
+            // directions.  mTouchMode might be TOUCH_DRAG_MODE if we have
+            // reached the edge of a layer but mScrollingLayer will be non-zero
+            // if we initiated the drag on a layer.
+            if (mCurrentScrollingLayerId != 0) {
+                final int contentX = viewToContentDimension(deltaX);
+                final int contentY = viewToContentDimension(deltaY);
+
+                // Check the scrolling bounds to see if we will actually do any
+                // scrolling.  The rectangle is in document coordinates.
+                final int maxX = mScrollingLayerRect.right;
+                final int maxY = mScrollingLayerRect.bottom;
+                final int resultX = Math.max(0,
+                        Math.min(mScrollingLayerRect.left + contentX, maxX));
+                final int resultY = Math.max(0,
+                        Math.min(mScrollingLayerRect.top + contentY, maxY));
+
+                if (resultX != mScrollingLayerRect.left ||
+                        resultY != mScrollingLayerRect.top) {
+                    // In case we switched to dragging the page.
+                    mTouchMode = TOUCH_DRAG_LAYER_MODE;
+                    deltaX = contentX;
+                    deltaY = contentY;
+                    oldX = mScrollingLayerRect.left;
+                    oldY = mScrollingLayerRect.top;
+                    rangeX = maxX;
+                    rangeY = maxY;
+                } else {
+                    // Scroll the main page if we are not going to scroll the
+                    // layer.  This does not reset mScrollingLayer in case the
+                    // user changes directions and the layer can scroll the
+                    // other way.
+                    mTouchMode = TOUCH_DRAG_MODE;
+                }
+            }
+
+            if (mOverScrollGlow != null) {
+                mOverScrollGlow.setOverScrollDeltas(deltaX, deltaY);
+            }
+
+            mWebViewPrivate.overScrollBy(deltaX, deltaY, oldX, oldY,
+                    rangeX, rangeY,
+                    mOverscrollDistance, mOverscrollDistance, true);
+            if (mOverScrollGlow != null && mOverScrollGlow.isAnimating()) {
+                invalidate();
+            }
+        }
+        mZoomManager.keepZoomPickerVisible();
+    }
+
+    private void stopTouch() {
+        if (mScroller.isFinished() && !mSelectingText
+                && (mTouchMode == TOUCH_DRAG_MODE || mTouchMode == TOUCH_DRAG_LAYER_MODE)) {
+            WebViewCore.resumePriority();
+            WebViewCore.resumeUpdatePicture(mWebViewCore);
+            nativeSetIsScrolling(false);
+        }
+
+        // we also use mVelocityTracker == null to tell us that we are
+        // not "moving around", so we can take the slower/prettier
+        // mode in the drawing code
+        if (mVelocityTracker != null) {
+            mVelocityTracker.recycle();
+            mVelocityTracker = null;
+        }
+
+        // Release any pulled glows
+        if (mOverScrollGlow != null) {
+            mOverScrollGlow.releaseAll();
+        }
+
+        if (mSelectingText) {
+            mSelectionStarted = false;
+            syncSelectionCursors();
+            if (mIsCaretSelection) {
+                resetCaretTimer();
+                showPasteWindow();
+            }
+            invalidate();
+        }
+    }
+
+    private void cancelTouch() {
+        // we also use mVelocityTracker == null to tell us that we are
+        // not "moving around", so we can take the slower/prettier
+        // mode in the drawing code
+        if (mVelocityTracker != null) {
+            mVelocityTracker.recycle();
+            mVelocityTracker = null;
+        }
+
+        if ((mTouchMode == TOUCH_DRAG_MODE
+                || mTouchMode == TOUCH_DRAG_LAYER_MODE) && !mSelectingText) {
+            WebViewCore.resumePriority();
+            WebViewCore.resumeUpdatePicture(mWebViewCore);
+            nativeSetIsScrolling(false);
+        }
+        mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
+        mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+        mPrivateHandler.removeMessages(DRAG_HELD_MOTIONLESS);
+        mPrivateHandler.removeMessages(AWAKEN_SCROLL_BARS);
+        removeTouchHighlight();
+        mHeldMotionless = MOTIONLESS_TRUE;
+        mTouchMode = TOUCH_DONE_MODE;
+    }
+
+    @Override
+    public boolean onGenericMotionEvent(MotionEvent event) {
+        if ((event.getSource() & InputDevice.SOURCE_CLASS_POINTER) != 0) {
+            switch (event.getAction()) {
+                case MotionEvent.ACTION_SCROLL: {
+                    final float vscroll;
+                    final float hscroll;
+                    if ((event.getMetaState() & KeyEvent.META_SHIFT_ON) != 0) {
+                        vscroll = 0;
+                        hscroll = event.getAxisValue(MotionEvent.AXIS_VSCROLL);
+                    } else {
+                        vscroll = -event.getAxisValue(MotionEvent.AXIS_VSCROLL);
+                        hscroll = event.getAxisValue(MotionEvent.AXIS_HSCROLL);
+                    }
+                    if (hscroll != 0 || vscroll != 0) {
+                        final int vdelta = (int) (vscroll *
+                                mWebViewPrivate.getVerticalScrollFactor());
+                        final int hdelta = (int) (hscroll *
+                                mWebViewPrivate.getHorizontalScrollFactor());
+                        if (pinScrollBy(hdelta, vdelta, false, 0)) {
+                            return true;
+                        }
+                    }
+                }
+            }
+        }
+        return mWebViewPrivate.super_onGenericMotionEvent(event);
+    }
+
+    private long mTrackballFirstTime = 0;
+    private long mTrackballLastTime = 0;
+    private float mTrackballRemainsX = 0.0f;
+    private float mTrackballRemainsY = 0.0f;
+    private int mTrackballXMove = 0;
+    private int mTrackballYMove = 0;
+    private boolean mSelectingText = false;
+    private boolean mSelectionStarted = false;
+    private static final int TRACKBALL_KEY_TIMEOUT = 1000;
+    private static final int TRACKBALL_TIMEOUT = 200;
+    private static final int TRACKBALL_WAIT = 100;
+    private static final int TRACKBALL_SCALE = 400;
+    private static final int TRACKBALL_SCROLL_COUNT = 5;
+    private static final int TRACKBALL_MOVE_COUNT = 10;
+    private static final int TRACKBALL_MULTIPLIER = 3;
+    private static final int SELECT_CURSOR_OFFSET = 16;
+    private static final int SELECT_SCROLL = 5;
+    private int mSelectX = 0;
+    private int mSelectY = 0;
+    private boolean mTrackballDown = false;
+    private long mTrackballUpTime = 0;
+    private long mLastCursorTime = 0;
+    private Rect mLastCursorBounds;
+
+    // Set by default; BrowserActivity clears to interpret trackball data
+    // directly for movement. Currently, the framework only passes
+    // arrow key events, not trackball events, from one child to the next
+    private boolean mMapTrackballToArrowKeys = true;
+
+    private DrawData mDelaySetPicture;
+    private DrawData mLoadedPicture;
+
+    public void setMapTrackballToArrowKeys(boolean setMap) {
+        checkThread();
+        mMapTrackballToArrowKeys = setMap;
+    }
+
+    void resetTrackballTime() {
+        mTrackballLastTime = 0;
+    }
+
+    @Override
+    public boolean onTrackballEvent(MotionEvent ev) {
+        long time = ev.getEventTime();
+        if ((ev.getMetaState() & KeyEvent.META_ALT_ON) != 0) {
+            if (ev.getY() > 0) pageDown(true);
+            if (ev.getY() < 0) pageUp(true);
+            return true;
+        }
+        if (ev.getAction() == MotionEvent.ACTION_DOWN) {
+            if (mSelectingText) {
+                return true; // discard press if copy in progress
+            }
+            mTrackballDown = true;
+            if (mNativeClass == 0) {
+                return false;
+            }
+            if (DebugFlags.WEB_VIEW) {
+                Log.v(LOGTAG, "onTrackballEvent down ev=" + ev
+                        + " time=" + time
+                        + " mLastCursorTime=" + mLastCursorTime);
+            }
+            if (mWebView.isInTouchMode()) mWebView.requestFocusFromTouch();
+            return false; // let common code in onKeyDown at it
+        }
+        if (ev.getAction() == MotionEvent.ACTION_UP) {
+            // LONG_PRESS_CENTER is set in common onKeyDown
+            mPrivateHandler.removeMessages(LONG_PRESS_CENTER);
+            mTrackballDown = false;
+            mTrackballUpTime = time;
+            if (mSelectingText) {
+                copySelection();
+                selectionDone();
+                return true; // discard press if copy in progress
+            }
+            if (DebugFlags.WEB_VIEW) {
+                Log.v(LOGTAG, "onTrackballEvent up ev=" + ev
+                        + " time=" + time
+                );
+            }
+            return false; // let common code in onKeyUp at it
+        }
+        if ((mMapTrackballToArrowKeys && (ev.getMetaState() & KeyEvent.META_SHIFT_ON) == 0) ||
+                AccessibilityManager.getInstance(mContext).isEnabled()) {
+            if (DebugFlags.WEB_VIEW) Log.v(LOGTAG, "onTrackballEvent gmail quit");
+            return false;
+        }
+        if (mTrackballDown) {
+            if (DebugFlags.WEB_VIEW) Log.v(LOGTAG, "onTrackballEvent down quit");
+            return true; // discard move if trackball is down
+        }
+        if (time - mTrackballUpTime < TRACKBALL_TIMEOUT) {
+            if (DebugFlags.WEB_VIEW) Log.v(LOGTAG, "onTrackballEvent up timeout quit");
+            return true;
+        }
+        // TODO: alternatively we can do panning as touch does
+        switchOutDrawHistory();
+        if (time - mTrackballLastTime > TRACKBALL_TIMEOUT) {
+            if (DebugFlags.WEB_VIEW) {
+                Log.v(LOGTAG, "onTrackballEvent time="
+                        + time + " last=" + mTrackballLastTime);
+            }
+            mTrackballFirstTime = time;
+            mTrackballXMove = mTrackballYMove = 0;
+        }
+        mTrackballLastTime = time;
+        if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, "onTrackballEvent ev=" + ev + " time=" + time);
+        }
+        mTrackballRemainsX += ev.getX();
+        mTrackballRemainsY += ev.getY();
+        doTrackball(time, ev.getMetaState());
+        return true;
+    }
+
+    private int scaleTrackballX(float xRate, int width) {
+        int xMove = (int) (xRate / TRACKBALL_SCALE * width);
+        int nextXMove = xMove;
+        if (xMove > 0) {
+            if (xMove > mTrackballXMove) {
+                xMove -= mTrackballXMove;
+            }
+        } else if (xMove < mTrackballXMove) {
+            xMove -= mTrackballXMove;
+        }
+        mTrackballXMove = nextXMove;
+        return xMove;
+    }
+
+    private int scaleTrackballY(float yRate, int height) {
+        int yMove = (int) (yRate / TRACKBALL_SCALE * height);
+        int nextYMove = yMove;
+        if (yMove > 0) {
+            if (yMove > mTrackballYMove) {
+                yMove -= mTrackballYMove;
+            }
+        } else if (yMove < mTrackballYMove) {
+            yMove -= mTrackballYMove;
+        }
+        mTrackballYMove = nextYMove;
+        return yMove;
+    }
+
+    private int keyCodeToSoundsEffect(int keyCode) {
+        switch(keyCode) {
+            case KeyEvent.KEYCODE_DPAD_UP:
+                return SoundEffectConstants.NAVIGATION_UP;
+            case KeyEvent.KEYCODE_DPAD_RIGHT:
+                return SoundEffectConstants.NAVIGATION_RIGHT;
+            case KeyEvent.KEYCODE_DPAD_DOWN:
+                return SoundEffectConstants.NAVIGATION_DOWN;
+            case KeyEvent.KEYCODE_DPAD_LEFT:
+                return SoundEffectConstants.NAVIGATION_LEFT;
+        }
+        throw new IllegalArgumentException("keyCode must be one of " +
+                "{KEYCODE_DPAD_UP, KEYCODE_DPAD_RIGHT, KEYCODE_DPAD_DOWN, " +
+                "KEYCODE_DPAD_LEFT}.");
+    }
+
+    private void doTrackball(long time, int metaState) {
+        int elapsed = (int) (mTrackballLastTime - mTrackballFirstTime);
+        if (elapsed == 0) {
+            elapsed = TRACKBALL_TIMEOUT;
+        }
+        float xRate = mTrackballRemainsX * 1000 / elapsed;
+        float yRate = mTrackballRemainsY * 1000 / elapsed;
+        int viewWidth = getViewWidth();
+        int viewHeight = getViewHeight();
+        float ax = Math.abs(xRate);
+        float ay = Math.abs(yRate);
+        float maxA = Math.max(ax, ay);
+        if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, "doTrackball elapsed=" + elapsed
+                    + " xRate=" + xRate
+                    + " yRate=" + yRate
+                    + " mTrackballRemainsX=" + mTrackballRemainsX
+                    + " mTrackballRemainsY=" + mTrackballRemainsY);
+        }
+        int width = mContentWidth - viewWidth;
+        int height = mContentHeight - viewHeight;
+        if (width < 0) width = 0;
+        if (height < 0) height = 0;
+        ax = Math.abs(mTrackballRemainsX * TRACKBALL_MULTIPLIER);
+        ay = Math.abs(mTrackballRemainsY * TRACKBALL_MULTIPLIER);
+        maxA = Math.max(ax, ay);
+        int count = Math.max(0, (int) maxA);
+        int oldScrollX = getScrollX();
+        int oldScrollY = getScrollY();
+        if (count > 0) {
+            int selectKeyCode = ax < ay ? mTrackballRemainsY < 0 ?
+                    KeyEvent.KEYCODE_DPAD_UP : KeyEvent.KEYCODE_DPAD_DOWN :
+                    mTrackballRemainsX < 0 ? KeyEvent.KEYCODE_DPAD_LEFT :
+                    KeyEvent.KEYCODE_DPAD_RIGHT;
+            count = Math.min(count, TRACKBALL_MOVE_COUNT);
+            if (DebugFlags.WEB_VIEW) {
+                Log.v(LOGTAG, "doTrackball keyCode=" + selectKeyCode
+                        + " count=" + count
+                        + " mTrackballRemainsX=" + mTrackballRemainsX
+                        + " mTrackballRemainsY=" + mTrackballRemainsY);
+            }
+            if (mNativeClass != 0) {
+                for (int i = 0; i < count; i++) {
+                    letPageHandleNavKey(selectKeyCode, time, true, metaState);
+                }
+                letPageHandleNavKey(selectKeyCode, time, false, metaState);
+            }
+            mTrackballRemainsX = mTrackballRemainsY = 0;
+        }
+        if (count >= TRACKBALL_SCROLL_COUNT) {
+            int xMove = scaleTrackballX(xRate, width);
+            int yMove = scaleTrackballY(yRate, height);
+            if (DebugFlags.WEB_VIEW) {
+                Log.v(LOGTAG, "doTrackball pinScrollBy"
+                        + " count=" + count
+                        + " xMove=" + xMove + " yMove=" + yMove
+                        + " mScrollX-oldScrollX=" + (getScrollX()-oldScrollX)
+                        + " mScrollY-oldScrollY=" + (getScrollY()-oldScrollY)
+                        );
+            }
+            if (Math.abs(getScrollX() - oldScrollX) > Math.abs(xMove)) {
+                xMove = 0;
+            }
+            if (Math.abs(getScrollY() - oldScrollY) > Math.abs(yMove)) {
+                yMove = 0;
+            }
+            if (xMove != 0 || yMove != 0) {
+                pinScrollBy(xMove, yMove, true, 0);
+            }
+        }
+    }
+
+    /**
+     * Compute the maximum horizontal scroll position. Used by {@link OverScrollGlow}.
+     * @return Maximum horizontal scroll position within real content
+     */
+    int computeMaxScrollX() {
+        return Math.max(computeRealHorizontalScrollRange() - getViewWidth(), 0);
+    }
+
+    /**
+     * Compute the maximum vertical scroll position. Used by {@link OverScrollGlow}.
+     * @return Maximum vertical scroll position within real content
+     */
+    int computeMaxScrollY() {
+        return Math.max(computeRealVerticalScrollRange() + getTitleHeight()
+                - getViewHeightWithTitle(), 0);
+    }
+
+    boolean updateScrollCoordinates(int x, int y) {
+        int oldX = getScrollX();
+        int oldY = getScrollY();
+        setScrollXRaw(x);
+        setScrollYRaw(y);
+        if (oldX != getScrollX() || oldY != getScrollY()) {
+            mWebViewPrivate.onScrollChanged(getScrollX(), getScrollY(), oldX, oldY);
+            return true;
+        } else {
+            return false;
+        }
+    }
+
+    public void flingScroll(int vx, int vy) {
+        checkThread();
+        mScroller.fling(getScrollX(), getScrollY(), vx, vy, 0, computeMaxScrollX(), 0,
+                computeMaxScrollY(), mOverflingDistance, mOverflingDistance);
+        invalidate();
+    }
+
+    private void doFling() {
+        if (mVelocityTracker == null) {
+            return;
+        }
+        int maxX = computeMaxScrollX();
+        int maxY = computeMaxScrollY();
+
+        mVelocityTracker.computeCurrentVelocity(1000, mMaximumFling);
+        int vx = (int) mVelocityTracker.getXVelocity();
+        int vy = (int) mVelocityTracker.getYVelocity();
+
+        int scrollX = getScrollX();
+        int scrollY = getScrollY();
+        int overscrollDistance = mOverscrollDistance;
+        int overflingDistance = mOverflingDistance;
+
+        // Use the layer's scroll data if applicable.
+        if (mTouchMode == TOUCH_DRAG_LAYER_MODE) {
+            scrollX = mScrollingLayerRect.left;
+            scrollY = mScrollingLayerRect.top;
+            maxX = mScrollingLayerRect.right;
+            maxY = mScrollingLayerRect.bottom;
+            // No overscrolling for layers.
+            overscrollDistance = overflingDistance = 0;
+        }
+
+        if (mSnapScrollMode != SNAP_NONE) {
+            if ((mSnapScrollMode & SNAP_X) == SNAP_X) {
+                vy = 0;
+            } else {
+                vx = 0;
+            }
+        }
+        if ((maxX == 0 && vy == 0) || (maxY == 0 && vx == 0)) {
+            WebViewCore.resumePriority();
+            if (!mSelectingText) {
+                WebViewCore.resumeUpdatePicture(mWebViewCore);
+            }
+            if (mScroller.springBack(scrollX, scrollY, 0, maxX, 0, maxY)) {
+                invalidate();
+            }
+            return;
+        }
+        float currentVelocity = mScroller.getCurrVelocity();
+        float velocity = (float) Math.hypot(vx, vy);
+        if (mLastVelocity > 0 && currentVelocity > 0 && velocity
+                > mLastVelocity * MINIMUM_VELOCITY_RATIO_FOR_ACCELERATION) {
+            float deltaR = (float) (Math.abs(Math.atan2(mLastVelY, mLastVelX)
+                    - Math.atan2(vy, vx)));
+            final float circle = (float) (Math.PI) * 2.0f;
+            if (deltaR > circle * 0.9f || deltaR < circle * 0.1f) {
+                vx += currentVelocity * mLastVelX / mLastVelocity;
+                vy += currentVelocity * mLastVelY / mLastVelocity;
+                velocity = (float) Math.hypot(vx, vy);
+                if (DebugFlags.WEB_VIEW) {
+                    Log.v(LOGTAG, "doFling vx= " + vx + " vy=" + vy);
+                }
+            } else if (DebugFlags.WEB_VIEW) {
+                Log.v(LOGTAG, "doFling missed " + deltaR / circle);
+            }
+        } else if (DebugFlags.WEB_VIEW) {
+            Log.v(LOGTAG, "doFling start last=" + mLastVelocity
+                    + " current=" + currentVelocity
+                    + " vx=" + vx + " vy=" + vy
+                    + " maxX=" + maxX + " maxY=" + maxY
+                    + " scrollX=" + scrollX + " scrollY=" + scrollY
+                    + " layer=" + mCurrentScrollingLayerId);
+        }
+
+        // Allow sloppy flings without overscrolling at the edges.
+        if ((scrollX == 0 || scrollX == maxX) && Math.abs(vx) < Math.abs(vy)) {
+            vx = 0;
+        }
+        if ((scrollY == 0 || scrollY == maxY) && Math.abs(vy) < Math.abs(vx)) {
+            vy = 0;
+        }
+
+        if (overscrollDistance < overflingDistance) {
+            if ((vx > 0 && scrollX == -overscrollDistance) ||
+                    (vx < 0 && scrollX == maxX + overscrollDistance)) {
+                vx = 0;
+            }
+            if ((vy > 0 && scrollY == -overscrollDistance) ||
+                    (vy < 0 && scrollY == maxY + overscrollDistance)) {
+                vy = 0;
+            }
+        }
+
+        mLastVelX = vx;
+        mLastVelY = vy;
+        mLastVelocity = velocity;
+
+        // no horizontal overscroll if the content just fits
+        mScroller.fling(scrollX, scrollY, -vx, -vy, 0, maxX, 0, maxY,
+                maxX == 0 ? 0 : overflingDistance, overflingDistance);
+        // Duration is calculated based on velocity. With range boundaries and overscroll
+        // we may not know how long the final animation will take. (Hence the deprecation
+        // warning on the call below.) It's not a big deal for scroll bars but if webcore
+        // resumes during this effect we will take a performance hit. See computeScroll;
+        // we resume webcore there when the animation is finished.
+        final int time = mScroller.getDuration();
+
+        // Suppress scrollbars for layer scrolling.
+        if (mTouchMode != TOUCH_DRAG_LAYER_MODE) {
+            mWebViewPrivate.awakenScrollBars(time);
+        }
+
+        invalidate();
+    }
+
+    /**
+     * Returns a view containing zoom controls i.e. +/- buttons. The caller is
+     * in charge of installing this view to the view hierarchy. This view will
+     * become visible when the user starts scrolling via touch and fade away if
+     * the user does not interact with it.
+     * <p/>
+     * API version 3 introduces a built-in zoom mechanism that is shown
+     * automatically by the MapView. This is the preferred approach for
+     * showing the zoom UI.
+     *
+     * @deprecated The built-in zoom mechanism is preferred, see
+     *             {@link WebSettings#setBuiltInZoomControls(boolean)}.
+     */
+    @Deprecated
+    public View getZoomControls() {
+        checkThread();
+        if (!getSettings().supportZoom()) {
+            Log.w(LOGTAG, "This WebView doesn't support zoom.");
+            return null;
+        }
+        return mZoomManager.getExternalZoomPicker();
+    }
+
+    void dismissZoomControl() {
+        mZoomManager.dismissZoomPicker();
+    }
+
+    float getDefaultZoomScale() {
+        return mZoomManager.getDefaultScale();
+    }
+
+    /**
+     * Return the overview scale of the WebView
+     * @return The overview scale.
+     */
+    float getZoomOverviewScale() {
+        return mZoomManager.getZoomOverviewScale();
+    }
+
+    /**
+     * @return TRUE if the WebView can be zoomed in.
+     */
+    public boolean canZoomIn() {
+        checkThread();
+        return mZoomManager.canZoomIn();
+    }
+
+    /**
+     * @return TRUE if the WebView can be zoomed out.
+     */
+    public boolean canZoomOut() {
+        checkThread();
+        return mZoomManager.canZoomOut();
+    }
+
+    /**
+     * Perform zoom in in the webview
+     * @return TRUE if zoom in succeeds. FALSE if no zoom changes.
+     */
+    public boolean zoomIn() {
+        checkThread();
+        return mZoomManager.zoomIn();
+    }
+
+    /**
+     * Perform zoom out in the webview
+     * @return TRUE if zoom out succeeds. FALSE if no zoom changes.
+     */
+    public boolean zoomOut() {
+        checkThread();
+        return mZoomManager.zoomOut();
+    }
+
+    private void doShortPress() {
+        if (mNativeClass == 0) {
+            return;
+        }
+        if (mPreventDefault == PREVENT_DEFAULT_YES) {
+            return;
+        }
+        mTouchMode = TOUCH_DONE_MODE;
+        switchOutDrawHistory();
+        if (!mTouchHighlightRegion.isEmpty()) {
+            // set mTouchHighlightRequested to 0 to cause an immediate
+            // drawing of the touch rings
+            mTouchHighlightRequested = 0;
+            mWebView.invalidate(mTouchHighlightRegion.getBounds());
+            mPrivateHandler.postDelayed(new Runnable() {
+                @Override
+                public void run() {
+                    removeTouchHighlight();
+                }
+            }, ViewConfiguration.getPressedStateDuration());
+        }
+        if (mFocusedNode != null && mFocusedNode.mIntentUrl != null) {
+            mWebView.playSoundEffect(SoundEffectConstants.CLICK);
+            overrideLoading(mFocusedNode.mIntentUrl);
+        } else {
+            WebViewCore.TouchUpData touchUpData = new WebViewCore.TouchUpData();
+            // use "0" as generation id to inform WebKit to use the same x/y as
+            // it used when processing GET_TOUCH_HIGHLIGHT_RECTS
+            touchUpData.mMoveGeneration = 0;
+            mWebViewCore.sendMessage(EventHub.TOUCH_UP, touchUpData);
+        }
+    }
+
+    void sendPluginDrawMsg() {
+        mWebViewCore.sendMessage(EventHub.PLUGIN_SURFACE_READY);
+    }
+
+    /*
+     * Return true if the rect (e.g. plugin) is fully visible and maximized
+     * inside the WebView.
+     */
+    boolean isRectFitOnScreen(Rect rect) {
+        final int rectWidth = rect.width();
+        final int rectHeight = rect.height();
+        final int viewWidth = getViewWidth();
+        final int viewHeight = getViewHeightWithTitle();
+        float scale = Math.min((float) viewWidth / rectWidth, (float) viewHeight / rectHeight);
+        scale = mZoomManager.computeScaleWithLimits(scale);
+        return !mZoomManager.willScaleTriggerZoom(scale)
+                && contentToViewX(rect.left) >= getScrollX()
+                && contentToViewX(rect.right) <= getScrollX() + viewWidth
+                && contentToViewY(rect.top) >= getScrollY()
+                && contentToViewY(rect.bottom) <= getScrollY() + viewHeight;
+    }
+
+    /*
+     * Maximize and center the rectangle, specified in the document coordinate
+     * space, inside the WebView. If the zoom doesn't need to be changed, do an
+     * animated scroll to center it. If the zoom needs to be changed, find the
+     * zoom center and do a smooth zoom transition. The rect is in document
+     * coordinates
+     */
+    void centerFitRect(Rect rect) {
+        final int rectWidth = rect.width();
+        final int rectHeight = rect.height();
+        final int viewWidth = getViewWidth();
+        final int viewHeight = getViewHeightWithTitle();
+        float scale = Math.min((float) viewWidth / rectWidth, (float) viewHeight
+                / rectHeight);
+        scale = mZoomManager.computeScaleWithLimits(scale);
+        if (!mZoomManager.willScaleTriggerZoom(scale)) {
+            pinScrollTo(contentToViewX(rect.left + rectWidth / 2) - viewWidth / 2,
+                    contentToViewY(rect.top + rectHeight / 2) - viewHeight / 2,
+                    true, 0);
+        } else {
+            float actualScale = mZoomManager.getScale();
+            float oldScreenX = rect.left * actualScale - getScrollX();
+            float rectViewX = rect.left * scale;
+            float rectViewWidth = rectWidth * scale;
+            float newMaxWidth = mContentWidth * scale;
+            float newScreenX = (viewWidth - rectViewWidth) / 2;
+            // pin the newX to the WebView
+            if (newScreenX > rectViewX) {
+                newScreenX = rectViewX;
+            } else if (newScreenX > (newMaxWidth - rectViewX - rectViewWidth)) {
+                newScreenX = viewWidth - (newMaxWidth - rectViewX);
+            }
+            float zoomCenterX = (oldScreenX * scale - newScreenX * actualScale)
+                    / (scale - actualScale);
+            float oldScreenY = rect.top * actualScale + getTitleHeight()
+                    - getScrollY();
+            float rectViewY = rect.top * scale + getTitleHeight();
+            float rectViewHeight = rectHeight * scale;
+            float newMaxHeight = mContentHeight * scale + getTitleHeight();
+            float newScreenY = (viewHeight - rectViewHeight) / 2;
+            // pin the newY to the WebView
+            if (newScreenY > rectViewY) {
+                newScreenY = rectViewY;
+            } else if (newScreenY > (newMaxHeight - rectViewY - rectViewHeight)) {
+                newScreenY = viewHeight - (newMaxHeight - rectViewY);
+            }
+            float zoomCenterY = (oldScreenY * scale - newScreenY * actualScale)
+                    / (scale - actualScale);
+            mZoomManager.setZoomCenter(zoomCenterX, zoomCenterY);
+            mZoomManager.startZoomAnimation(scale, false);
+        }
+    }
+
+    // Called by JNI to handle a touch on a node representing an email address,
+    // address, or phone number
+    private void overrideLoading(String url) {
+        mCallbackProxy.uiOverrideUrlLoading(url);
+    }
+
+    @Override
+    public boolean requestFocus(int direction, Rect previouslyFocusedRect) {
+        // FIXME: If a subwindow is showing find, and the user touches the
+        // background window, it can steal focus.
+        if (mFindIsUp) return false;
+        boolean result = false;
+        result = mWebViewPrivate.super_requestFocus(direction, previouslyFocusedRect);
+        if (mWebViewCore.getSettings().getNeedInitialFocus() && !mWebView.isInTouchMode()) {
+            // For cases such as GMail, where we gain focus from a direction,
+            // we want to move to the first available link.
+            // FIXME: If there are no visible links, we may not want to
+            int fakeKeyDirection = 0;
+            switch(direction) {
+                case View.FOCUS_UP:
+                    fakeKeyDirection = KeyEvent.KEYCODE_DPAD_UP;
+                    break;
+                case View.FOCUS_DOWN:
+                    fakeKeyDirection = KeyEvent.KEYCODE_DPAD_DOWN;
+                    break;
+                case View.FOCUS_LEFT:
+                    fakeKeyDirection = KeyEvent.KEYCODE_DPAD_LEFT;
+                    break;
+                case View.FOCUS_RIGHT:
+                    fakeKeyDirection = KeyEvent.KEYCODE_DPAD_RIGHT;
+                    break;
+                default:
+                    return result;
+            }
+            // TODO: Send initial focus request to webkit (b/6108927)
+        }
+        return result;
+    }
+
+    @Override
+    public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+        int heightMode = MeasureSpec.getMode(heightMeasureSpec);
+        int heightSize = MeasureSpec.getSize(heightMeasureSpec);
+        int widthMode = MeasureSpec.getMode(widthMeasureSpec);
+        int widthSize = MeasureSpec.getSize(widthMeasureSpec);
+
+        int measuredHeight = heightSize;
+        int measuredWidth = widthSize;
+
+        // Grab the content size from WebViewCore.
+        int contentHeight = contentToViewDimension(mContentHeight);
+        int contentWidth = contentToViewDimension(mContentWidth);
+
+//        Log.d(LOGTAG, "------- measure " + heightMode);
+
+        if (heightMode != MeasureSpec.EXACTLY) {
+            mHeightCanMeasure = true;
+            measuredHeight = contentHeight;
+            if (heightMode == MeasureSpec.AT_MOST) {
+                // If we are larger than the AT_MOST height, then our height can
+                // no longer be measured and we should scroll internally.
+                if (measuredHeight > heightSize) {
+                    measuredHeight = heightSize;
+                    mHeightCanMeasure = false;
+                    measuredHeight |= View.MEASURED_STATE_TOO_SMALL;
+                }
+            }
+        } else {
+            mHeightCanMeasure = false;
+        }
+        if (mNativeClass != 0) {
+            nativeSetHeightCanMeasure(mHeightCanMeasure);
+        }
+        // For the width, always use the given size unless unspecified.
+        if (widthMode == MeasureSpec.UNSPECIFIED) {
+            mWidthCanMeasure = true;
+            measuredWidth = contentWidth;
+        } else {
+            if (measuredWidth < contentWidth) {
+                measuredWidth |= View.MEASURED_STATE_TOO_SMALL;
+            }
+            mWidthCanMeasure = false;
+        }
+
+        synchronized (this) {
+            mWebViewPrivate.setMeasuredDimension(measuredWidth, measuredHeight);
+        }
+    }
+
+    @Override
+    public boolean requestChildRectangleOnScreen(View child,
+                                                 Rect rect,
+                                                 boolean immediate) {
+        if (mNativeClass == 0) {
+            return false;
+        }
+        // don't scroll while in zoom animation. When it is done, we will adjust
+        // the necessary components
+        if (mZoomManager.isFixedLengthAnimationInProgress()) {
+            return false;
+        }
+
+        rect.offset(child.getLeft() - child.getScrollX(),
+                child.getTop() - child.getScrollY());
+
+        Rect content = new Rect(viewToContentX(getScrollX()),
+                viewToContentY(getScrollY()),
+                viewToContentX(getScrollX() + getWidth()
+                - mWebView.getVerticalScrollbarWidth()),
+                viewToContentY(getScrollY() + getViewHeightWithTitle()));
+        content = nativeSubtractLayers(content);
+        int screenTop = contentToViewY(content.top);
+        int screenBottom = contentToViewY(content.bottom);
+        int height = screenBottom - screenTop;
+        int scrollYDelta = 0;
+
+        if (rect.bottom > screenBottom) {
+            int oneThirdOfScreenHeight = height / 3;
+            if (rect.height() > 2 * oneThirdOfScreenHeight) {
+                // If the rectangle is too tall to fit in the bottom two thirds
+                // of the screen, place it at the top.
+                scrollYDelta = rect.top - screenTop;
+            } else {
+                // If the rectangle will still fit on screen, we want its
+                // top to be in the top third of the screen.
+                scrollYDelta = rect.top - (screenTop + oneThirdOfScreenHeight);
+            }
+        } else if (rect.top < screenTop) {
+            scrollYDelta = rect.top - screenTop;
+        }
+
+        int screenLeft = contentToViewX(content.left);
+        int screenRight = contentToViewX(content.right);
+        int width = screenRight - screenLeft;
+        int scrollXDelta = 0;
+
+        if (rect.right > screenRight && rect.left > screenLeft) {
+            if (rect.width() > width) {
+                scrollXDelta += (rect.left - screenLeft);
+            } else {
+                scrollXDelta += (rect.right - screenRight);
+            }
+        } else if (rect.left < screenLeft) {
+            scrollXDelta -= (screenLeft - rect.left);
+        }
+
+        if ((scrollYDelta | scrollXDelta) != 0) {
+            return pinScrollBy(scrollXDelta, scrollYDelta, !immediate, 0);
+        }
+
+        return false;
+    }
+
+    /* package */ void replaceTextfieldText(int oldStart, int oldEnd,
+            String replace, int newStart, int newEnd) {
+        WebViewCore.ReplaceTextData arg = new WebViewCore.ReplaceTextData();
+        arg.mReplace = replace;
+        arg.mNewStart = newStart;
+        arg.mNewEnd = newEnd;
+        mTextGeneration++;
+        arg.mTextGeneration = mTextGeneration;
+        mWebViewCore.sendMessage(EventHub.REPLACE_TEXT, oldStart, oldEnd, arg);
+    }
+
+    /* package */ void passToJavaScript(String currentText, KeyEvent event) {
+        // check if mWebViewCore has been destroyed
+        if (mWebViewCore == null) {
+            return;
+        }
+        WebViewCore.JSKeyData arg = new WebViewCore.JSKeyData();
+        arg.mEvent = event;
+        arg.mCurrentText = currentText;
+        // Increase our text generation number, and pass it to webcore thread
+        mTextGeneration++;
+        mWebViewCore.sendMessage(EventHub.PASS_TO_JS, mTextGeneration, 0, arg);
+        // WebKit's document state is not saved until about to leave the page.
+        // To make sure the host application, like Browser, has the up to date
+        // document state when it goes to background, we force to save the
+        // document state.
+        mWebViewCore.removeMessages(EventHub.SAVE_DOCUMENT_STATE);
+        mWebViewCore.sendMessageDelayed(EventHub.SAVE_DOCUMENT_STATE, null, 1000);
+    }
+
+    /**
+     * @hide
+     */
+    public synchronized WebViewCore getWebViewCore() {
+        return mWebViewCore;
+    }
+
+    /**
+     * Used only by TouchEventQueue to store pending touch events.
+     */
+    private static class QueuedTouch {
+        long mSequence;
+        MotionEvent mEvent; // Optional
+        TouchEventData mTed; // Optional
+
+        QueuedTouch mNext;
+
+        public QueuedTouch set(TouchEventData ted) {
+            mSequence = ted.mSequence;
+            mTed = ted;
+            mEvent = null;
+            mNext = null;
+            return this;
+        }
+
+        public QueuedTouch set(MotionEvent ev, long sequence) {
+            mEvent = MotionEvent.obtain(ev);
+            mSequence = sequence;
+            mTed = null;
+            mNext = null;
+            return this;
+        }
+
+        public QueuedTouch add(QueuedTouch other) {
+            if (other.mSequence < mSequence) {
+                other.mNext = this;
+                return other;
+            }
+
+            QueuedTouch insertAt = this;
+            while (insertAt.mNext != null && insertAt.mNext.mSequence < other.mSequence) {
+                insertAt = insertAt.mNext;
+            }
+            other.mNext = insertAt.mNext;
+            insertAt.mNext = other;
+            return this;
+        }
+    }
+
+    /**
+     * WebView handles touch events asynchronously since some events must be passed to WebKit
+     * for potentially slower processing. TouchEventQueue serializes touch events regardless
+     * of which path they take to ensure that no events are ever processed out of order
+     * by WebView.
+     */
+    private class TouchEventQueue {
+        private long mNextTouchSequence = Long.MIN_VALUE + 1;
+        private long mLastHandledTouchSequence = Long.MIN_VALUE;
+        private long mIgnoreUntilSequence = Long.MIN_VALUE + 1;
+
+        // Events waiting to be processed.
+        private QueuedTouch mTouchEventQueue;
+
+        // Known events that are waiting on a response before being enqueued.
+        private QueuedTouch mPreQueue;
+
+        // Pool of QueuedTouch objects saved for later use.
+        private QueuedTouch mQueuedTouchRecycleBin;
+        private int mQueuedTouchRecycleCount;
+
+        private long mLastEventTime = Long.MAX_VALUE;
+        private static final int MAX_RECYCLED_QUEUED_TOUCH = 15;
+
+        // milliseconds until we abandon hope of getting all of a previous gesture
+        private static final int QUEUED_GESTURE_TIMEOUT = 1000;
+
+        private QueuedTouch obtainQueuedTouch() {
+            if (mQueuedTouchRecycleBin != null) {
+                QueuedTouch result = mQueuedTouchRecycleBin;
+                mQueuedTouchRecycleBin = result.mNext;
+                mQueuedTouchRecycleCount--;
+                return result;
+            }
+            return new QueuedTouch();
+        }
+
+        /**
+         * Allow events with any currently missing sequence numbers to be skipped in processing.
+         */
+        public void ignoreCurrentlyMissingEvents() {
+            mIgnoreUntilSequence = mNextTouchSequence;
+
+            // Run any events we have available and complete, pre-queued or otherwise.
+            runQueuedAndPreQueuedEvents();
+        }
+
+        private void runQueuedAndPreQueuedEvents() {
+            QueuedTouch qd = mPreQueue;
+            boolean fromPreQueue = true;
+            while (qd != null && qd.mSequence == mLastHandledTouchSequence + 1) {
+                handleQueuedTouch(qd);
+                QueuedTouch recycleMe = qd;
+                if (fromPreQueue) {
+                    mPreQueue = qd.mNext;
+                } else {
+                    mTouchEventQueue = qd.mNext;
+                }
+                recycleQueuedTouch(recycleMe);
+                mLastHandledTouchSequence++;
+
+                long nextPre = mPreQueue != null ? mPreQueue.mSequence : Long.MAX_VALUE;
+                long nextQueued = mTouchEventQueue != null ?
+                        mTouchEventQueue.mSequence : Long.MAX_VALUE;
+                fromPreQueue = nextPre < nextQueued;
+                qd = fromPreQueue ? mPreQueue : mTouchEventQueue;
+            }
+        }
+
+        /**
+         * Add a TouchEventData to the pre-queue.
+         *
+         * An event in the pre-queue is an event that we know about that
+         * has been sent to webkit, but that we haven't received back and
+         * enqueued into the normal touch queue yet. If webkit ever times
+         * out and we need to ignore currently missing events, we'll run
+         * events from the pre-queue to patch the holes.
+         *
+         * @param ted TouchEventData to pre-queue
+         */
+        public void preQueueTouchEventData(TouchEventData ted) {
+            QueuedTouch newTouch = obtainQueuedTouch().set(ted);
+            if (mPreQueue == null) {
+                mPreQueue = newTouch;
+            } else {
+                QueuedTouch insertionPoint = mPreQueue;
+                while (insertionPoint.mNext != null &&
+                        insertionPoint.mNext.mSequence < newTouch.mSequence) {
+                    insertionPoint = insertionPoint.mNext;
+                }
+                newTouch.mNext = insertionPoint.mNext;
+                insertionPoint.mNext = newTouch;
+            }
+        }
+
+        private void recycleQueuedTouch(QueuedTouch qd) {
+            if (mQueuedTouchRecycleCount < MAX_RECYCLED_QUEUED_TOUCH) {
+                qd.mNext = mQueuedTouchRecycleBin;
+                mQueuedTouchRecycleBin = qd;
+                mQueuedTouchRecycleCount++;
+            }
+        }
+
+        /**
+         * Reset the touch event queue. This will dump any pending events
+         * and reset the sequence numbering.
+         */
+        public void reset() {
+            mNextTouchSequence = Long.MIN_VALUE + 1;
+            mLastHandledTouchSequence = Long.MIN_VALUE;
+            mIgnoreUntilSequence = Long.MIN_VALUE + 1;
+            while (mTouchEventQueue != null) {
+                QueuedTouch recycleMe = mTouchEventQueue;
+                mTouchEventQueue = mTouchEventQueue.mNext;
+                recycleQueuedTouch(recycleMe);
+            }
+            while (mPreQueue != null) {
+                QueuedTouch recycleMe = mPreQueue;
+                mPreQueue = mPreQueue.mNext;
+                recycleQueuedTouch(recycleMe);
+            }
+        }
+
+        /**
+         * Return the next valid sequence number for tagging incoming touch events.
+         * @return The next touch event sequence number
+         */
+        public long nextTouchSequence() {
+            return mNextTouchSequence++;
+        }
+
+        /**
+         * Enqueue a touch event in the form of TouchEventData.
+         * The sequence number will be read from the mSequence field of the argument.
+         *
+         * If the touch event's sequence number is the next in line to be processed, it will
+         * be handled before this method returns. Any subsequent events that have already
+         * been queued will also be processed in their proper order.
+         *
+         * @param ted Touch data to be processed in order.
+         * @return true if the event was processed before returning, false if it was just enqueued.
+         */
+        public boolean enqueueTouchEvent(TouchEventData ted) {
+            // Remove from the pre-queue if present
+            QueuedTouch preQueue = mPreQueue;
+            if (preQueue != null) {
+                // On exiting this block, preQueue is set to the pre-queued QueuedTouch object
+                // if it was present in the pre-queue, and removed from the pre-queue itself.
+                if (preQueue.mSequence == ted.mSequence) {
+                    mPreQueue = preQueue.mNext;
+                } else {
+                    QueuedTouch prev = preQueue;
+                    preQueue = null;
+                    while (prev.mNext != null) {
+                        if (prev.mNext.mSequence == ted.mSequence) {
+                            preQueue = prev.mNext;
+                            prev.mNext = preQueue.mNext;
+                            break;
+                        } else {
+                            prev = prev.mNext;
+                        }
+                    }
+                }
+            }
+
+            if (ted.mSequence < mLastHandledTouchSequence) {
+                // Stale event and we already moved on; drop it. (Should not be common.)
+                Log.w(LOGTAG, "Stale touch event " + MotionEvent.actionToString(ted.mAction) +
+                        " received from webcore; ignoring");
+                return false;
+            }
+
+            if (dropStaleGestures(ted.mMotionEvent, ted.mSequence)) {
+                return false;
+            }
+
+            // dropStaleGestures above might have fast-forwarded us to
+            // an event we have already.
+            runNextQueuedEvents();
+
+            if (mLastHandledTouchSequence + 1 == ted.mSequence) {
+                if (preQueue != null) {
+                    recycleQueuedTouch(preQueue);
+                    preQueue = null;
+                }
+                handleQueuedTouchEventData(ted);
+
+                mLastHandledTouchSequence++;
+
+                // Do we have any more? Run them if so.
+                runNextQueuedEvents();
+            } else {
+                // Reuse the pre-queued object if we had it.
+                QueuedTouch qd = preQueue != null ? preQueue : obtainQueuedTouch().set(ted);
+                mTouchEventQueue = mTouchEventQueue == null ? qd : mTouchEventQueue.add(qd);
+            }
+            return true;
+        }
+
+        /**
+         * Enqueue a touch event in the form of a MotionEvent from the framework.
+         *
+         * If the touch event's sequence number is the next in line to be processed, it will
+         * be handled before this method returns. Any subsequent events that have already
+         * been queued will also be processed in their proper order.
+         *
+         * @param ev MotionEvent to be processed in order
+         */
+        public void enqueueTouchEvent(MotionEvent ev) {
+            final long sequence = nextTouchSequence();
+
+            if (dropStaleGestures(ev, sequence)) {
+                return;
+            }
+
+            // dropStaleGestures above might have fast-forwarded us to
+            // an event we have already.
+            runNextQueuedEvents();
+
+            if (mLastHandledTouchSequence + 1 == sequence) {
+                handleQueuedMotionEvent(ev);
+
+                mLastHandledTouchSequence++;
+
+                // Do we have any more? Run them if so.
+                runNextQueuedEvents();
+            } else {
+                QueuedTouch qd = obtainQueuedTouch().set(ev, sequence);
+                mTouchEventQueue = mTouchEventQueue == null ? qd : mTouchEventQueue.add(qd);
+            }
+        }
+
+        private void runNextQueuedEvents() {
+            QueuedTouch qd = mTouchEventQueue;
+            while (qd != null && qd.mSequence == mLastHandledTouchSequence + 1) {
+                handleQueuedTouch(qd);
+                QueuedTouch recycleMe = qd;
+                qd = qd.mNext;
+                recycleQueuedTouch(recycleMe);
+                mLastHandledTouchSequence++;
+            }
+            mTouchEventQueue = qd;
+        }
+
+        private boolean dropStaleGestures(MotionEvent ev, long sequence) {
+            if (ev != null && ev.getAction() == MotionEvent.ACTION_MOVE && !mConfirmMove) {
+                // This is to make sure that we don't attempt to process a tap
+                // or long press when webkit takes too long to get back to us.
+                // The movement will be properly confirmed when we process the
+                // enqueued event later.
+                final int dx = Math.round(ev.getX()) - mLastTouchX;
+                final int dy = Math.round(ev.getY()) - mLastTouchY;
+                if (dx * dx + dy * dy > mTouchSlopSquare) {
+                    mPrivateHandler.removeMessages(SWITCH_TO_SHORTPRESS);
+                    mPrivateHandler.removeMessages(SWITCH_TO_LONGPRESS);
+                }
+            }
+
+            if (mTouchEventQueue == null) {
+                return sequence <= mLastHandledTouchSequence;
+            }
+
+            // If we have a new down event and it's been a while since the last event
+            // we saw, catch up as best we can and keep going.
+            if (ev != null && ev.getAction() == MotionEvent.ACTION_DOWN) {
+                long eventTime = ev.getEventTime();
+                long lastHandledEventTime = mLastEventTime;
+                if (eventTime > lastHandledEventTime + QUEUED_GESTURE_TIMEOUT) {
+                    Log.w(LOGTAG, "Got ACTION_DOWN but still waiting on stale event. " +
+                            "Catching up.");
+                    runQueuedAndPreQueuedEvents();
+
+                    // Drop leftovers that we truly don't have.
+                    QueuedTouch qd = mTouchEventQueue;
+                    while (qd != null && qd.mSequence < sequence) {
+                        QueuedTouch recycleMe = qd;
+                        qd = qd.mNext;
+                        recycleQueuedTouch(recycleMe);
+                    }
+                    mTouchEventQueue = qd;
+                    mLastHandledTouchSequence = sequence - 1;
+                }
+            }
+
+            if (mIgnoreUntilSequence - 1 > mLastHandledTouchSequence) {
+                QueuedTouch qd = mTouchEventQueue;
+                while (qd != null && qd.mSequence < mIgnoreUntilSequence) {
+                    QueuedTouch recycleMe = qd;
+                    qd = qd.mNext;
+                    recycleQueuedTouch(recycleMe);
+                }
+                mTouchEventQueue = qd;
+                mLastHandledTouchSequence = mIgnoreUntilSequence - 1;
+            }
+
+            if (mPreQueue != null) {
+                // Drop stale prequeued events
+                QueuedTouch qd = mPreQueue;
+                while (qd != null && qd.mSequence < mIgnoreUntilSequence) {
+                    QueuedTouch recycleMe = qd;
+                    qd = qd.mNext;
+                    recycleQueuedTouch(recycleMe);
+                }
+                mPreQueue = qd;
+            }
+
+            return sequence <= mLastHandledTouchSequence;
+        }
+
+        private void handleQueuedTouch(QueuedTouch qt) {
+            if (qt.mTed != null) {
+                handleQueuedTouchEventData(qt.mTed);
+            } else {
+                handleQueuedMotionEvent(qt.mEvent);
+                qt.mEvent.recycle();
+            }
+        }
+
+        private void handleQueuedMotionEvent(MotionEvent ev) {
+            mLastEventTime = ev.getEventTime();
+            int action = ev.getActionMasked();
+            if (ev.getPointerCount() > 1) {  // Multi-touch
+                handleMultiTouchInWebView(ev);
+            } else {
+                final ScaleGestureDetector detector = mZoomManager.getMultiTouchGestureDetector();
+                if (detector != null && mPreventDefault != PREVENT_DEFAULT_YES) {
+                    // ScaleGestureDetector needs a consistent event stream to operate properly.
+                    // It won't take any action with fewer than two pointers, but it needs to
+                    // update internal bookkeeping state.
+                    detector.onTouchEvent(ev);
+                }
+
+                handleTouchEventCommon(ev, action, Math.round(ev.getX()), Math.round(ev.getY()));
+            }
+        }
+
+        private void handleQueuedTouchEventData(TouchEventData ted) {
+            if (ted.mMotionEvent != null) {
+                mLastEventTime = ted.mMotionEvent.getEventTime();
+            }
+            if (!ted.mReprocess) {
+                if (ted.mAction == MotionEvent.ACTION_DOWN
+                        && mPreventDefault == PREVENT_DEFAULT_MAYBE_YES) {
+                    // if prevent default is called from WebCore, UI
+                    // will not handle the rest of the touch events any
+                    // more.
+                    mPreventDefault = ted.mNativeResult ? PREVENT_DEFAULT_YES
+                            : PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN;
+                } else if (ted.mAction == MotionEvent.ACTION_MOVE
+                        && mPreventDefault == PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN) {
+                    // the return for the first ACTION_MOVE will decide
+                    // whether UI will handle touch or not. Currently no
+                    // support for alternating prevent default
+                    mPreventDefault = ted.mNativeResult ? PREVENT_DEFAULT_YES
+                            : PREVENT_DEFAULT_NO;
+                }
+                if (mPreventDefault == PREVENT_DEFAULT_YES) {
+                    mTouchHighlightRegion.setEmpty();
+                }
+            } else {
+                if (ted.mPoints.length > 1) {  // multi-touch
+                    if (!ted.mNativeResult && mPreventDefault != PREVENT_DEFAULT_YES) {
+                        mPreventDefault = PREVENT_DEFAULT_NO;
+                        handleMultiTouchInWebView(ted.mMotionEvent);
+                    } else {
+                        mPreventDefault = PREVENT_DEFAULT_YES;
+                    }
+                    return;
+                }
+
+                // prevent default is not called in WebCore, so the
+                // message needs to be reprocessed in UI
+                if (!ted.mNativeResult) {
+                    // Following is for single touch.
+                    switch (ted.mAction) {
+                        case MotionEvent.ACTION_DOWN:
+                            mLastDeferTouchX = ted.mPointsInView[0].x;
+                            mLastDeferTouchY = ted.mPointsInView[0].y;
+                            mDeferTouchMode = TOUCH_INIT_MODE;
+                            break;
+                        case MotionEvent.ACTION_MOVE: {
+                            // no snapping in defer process
+                            int x = ted.mPointsInView[0].x;
+                            int y = ted.mPointsInView[0].y;
+
+                            if (mDeferTouchMode != TOUCH_DRAG_MODE) {
+                                mDeferTouchMode = TOUCH_DRAG_MODE;
+                                mLastDeferTouchX = x;
+                                mLastDeferTouchY = y;
+                                startScrollingLayer(x, y);
+                                startDrag();
+                            }
+                            int deltaX = pinLocX((int) (getScrollX()
+                                    + mLastDeferTouchX - x))
+                                    - getScrollX();
+                            int deltaY = pinLocY((int) (getScrollY()
+                                    + mLastDeferTouchY - y))
+                                    - getScrollY();
+                            doDrag(deltaX, deltaY);
+                            if (deltaX != 0) mLastDeferTouchX = x;
+                            if (deltaY != 0) mLastDeferTouchY = y;
+                            break;
+                        }
+                        case MotionEvent.ACTION_UP:
+                        case MotionEvent.ACTION_CANCEL:
+                            if (mDeferTouchMode == TOUCH_DRAG_MODE) {
+                                // no fling in defer process
+                                mScroller.springBack(getScrollX(), getScrollY(), 0,
+                                        computeMaxScrollX(), 0,
+                                        computeMaxScrollY());
+                                invalidate();
+                                WebViewCore.resumePriority();
+                                WebViewCore.resumeUpdatePicture(mWebViewCore);
+                            }
+                            mDeferTouchMode = TOUCH_DONE_MODE;
+                            break;
+                        case WebViewCore.ACTION_DOUBLETAP:
+                            // doDoubleTap() needs mLastTouchX/Y as anchor
+                            mLastDeferTouchX = ted.mPointsInView[0].x;
+                            mLastDeferTouchY = ted.mPointsInView[0].y;
+                            mZoomManager.handleDoubleTap(mLastTouchX, mLastTouchY);
+                            mDeferTouchMode = TOUCH_DONE_MODE;
+                            break;
+                        case WebViewCore.ACTION_LONGPRESS:
+                            HitTestResult hitTest = getHitTestResult();
+                            if (hitTest != null && hitTest.getType()
+                                    != HitTestResult.UNKNOWN_TYPE) {
+                                performLongClick();
+                            }
+                            mDeferTouchMode = TOUCH_DONE_MODE;
+                            break;
+                    }
+                }
+            }
+        }
+    }
+
+    //-------------------------------------------------------------------------
+    // Methods can be called from a separate thread, like WebViewCore
+    // If it needs to call the View system, it has to send message.
+    //-------------------------------------------------------------------------
+
+    /**
+     * General handler to receive message coming from webkit thread
+     */
+    class PrivateHandler extends Handler {
+        @Override
+        public void handleMessage(Message msg) {
+            // exclude INVAL_RECT_MSG_ID since it is frequently output
+            if (DebugFlags.WEB_VIEW && msg.what != INVAL_RECT_MSG_ID) {
+                if (msg.what >= FIRST_PRIVATE_MSG_ID
+                        && msg.what <= LAST_PRIVATE_MSG_ID) {
+                    Log.v(LOGTAG, HandlerPrivateDebugString[msg.what
+                            - FIRST_PRIVATE_MSG_ID]);
+                } else if (msg.what >= FIRST_PACKAGE_MSG_ID
+                        && msg.what <= LAST_PACKAGE_MSG_ID) {
+                    Log.v(LOGTAG, HandlerPackageDebugString[msg.what
+                            - FIRST_PACKAGE_MSG_ID]);
+                } else {
+                    Log.v(LOGTAG, Integer.toString(msg.what));
+                }
+            }
+            if (mWebViewCore == null) {
+                // after WebView's destroy() is called, skip handling messages.
+                return;
+            }
+            if (mBlockWebkitViewMessages
+                    && msg.what != WEBCORE_INITIALIZED_MSG_ID) {
+                // Blocking messages from webkit
+                return;
+            }
+            switch (msg.what) {
+                case REMEMBER_PASSWORD: {
+                    mDatabase.setUsernamePassword(
+                            msg.getData().getString("host"),
+                            msg.getData().getString("username"),
+                            msg.getData().getString("password"));
+                    ((Message) msg.obj).sendToTarget();
+                    break;
+                }
+                case NEVER_REMEMBER_PASSWORD: {
+                    mDatabase.setUsernamePassword(
+                            msg.getData().getString("host"), null, null);
+                    ((Message) msg.obj).sendToTarget();
+                    break;
+                }
+                case PREVENT_DEFAULT_TIMEOUT: {
+                    // if timeout happens, cancel it so that it won't block UI
+                    // to continue handling touch events
+                    if ((msg.arg1 == MotionEvent.ACTION_DOWN
+                            && mPreventDefault == PREVENT_DEFAULT_MAYBE_YES)
+                            || (msg.arg1 == MotionEvent.ACTION_MOVE
+                            && mPreventDefault == PREVENT_DEFAULT_NO_FROM_TOUCH_DOWN)) {
+                        cancelWebCoreTouchEvent(
+                                viewToContentX(mLastTouchX + getScrollX()),
+                                viewToContentY(mLastTouchY + getScrollY()),
+                                true);
+                    }
+                    break;
+                }
+                case SCROLL_SELECT_TEXT: {
+                    if (mAutoScrollX == 0 && mAutoScrollY == 0) {
+                        mSentAutoScrollMessage = false;
+                        break;
+                    }
+                    if (mCurrentScrollingLayerId == 0) {
+                        pinScrollBy(mAutoScrollX, mAutoScrollY, true, 0);
+                    } else {
+                        scrollLayerTo(mScrollingLayerRect.left + mAutoScrollX,
+                                mScrollingLayerRect.top + mAutoScrollY);
+                    }
+                    sendEmptyMessageDelayed(
+                            SCROLL_SELECT_TEXT, SELECT_SCROLL_INTERVAL);
+                    break;
+                }
+                case SWITCH_TO_SHORTPRESS: {
+                    if (mTouchMode == TOUCH_INIT_MODE) {
+                        mTouchMode = TOUCH_SHORTPRESS_MODE;
+                    } else if (mTouchMode == TOUCH_DOUBLE_TAP_MODE) {
+                        mTouchMode = TOUCH_DONE_MODE;
+                    }
+                    break;
+                }
+                case SWITCH_TO_LONGPRESS: {
+                    removeTouchHighlight();
+                    if (inFullScreenMode() || mDeferTouchProcess) {
+                        TouchEventData ted = new TouchEventData();
+                        ted.mAction = WebViewCore.ACTION_LONGPRESS;
+                        ted.mIds = new int[1];
+                        ted.mIds[0] = 0;
+                        ted.mPoints = new Point[1];
+                        ted.mPoints[0] = new Point(viewToContentX(mLastTouchX + getScrollX()),
+                                                   viewToContentY(mLastTouchY + getScrollY()));
+                        ted.mPointsInView = new Point[1];
+                        ted.mPointsInView[0] = new Point(mLastTouchX, mLastTouchY);
+                        // metaState for long press is tricky. Should it be the
+                        // state when the press started or when the press was
+                        // released? Or some intermediary key state? For
+                        // simplicity for now, we don't set it.
+                        ted.mMetaState = 0;
+                        ted.mReprocess = mDeferTouchProcess;
+                        ted.mNativeLayer = nativeScrollableLayer(
+                                ted.mPoints[0].x, ted.mPoints[0].y,
+                                ted.mNativeLayerRect, null);
+                        ted.mSequence = mTouchEventQueue.nextTouchSequence();
+                        mTouchEventQueue.preQueueTouchEventData(ted);
+                        mWebViewCore.sendMessage(EventHub.TOUCH_EVENT, ted);
+                    } else if (mPreventDefault != PREVENT_DEFAULT_YES) {
+                        mTouchMode = TOUCH_DONE_MODE;
+                        performLongClick();
+                    }
+                    break;
+                }
+                case RELEASE_SINGLE_TAP: {
+                    doShortPress();
+                    break;
+                }
+                case SCROLL_TO_MSG_ID: {
+                    // arg1 = animate, arg2 = onlyIfImeIsShowing
+                    // obj = Point(x, y)
+                    if (msg.arg2 == 1) {
+                        // This scroll is intended to bring the textfield into
+                        // view, but is only necessary if the IME is showing
+                        InputMethodManager imm = InputMethodManager.peekInstance();
+                        if (imm == null || !imm.isAcceptingText()
+                                || !imm.isActive(mWebView)) {
+                            break;
+                        }
+                    }
+                    final Point p = (Point) msg.obj;
+                    if (msg.arg1 == 1) {
+                        spawnContentScrollTo(p.x, p.y);
+                    } else {
+                        setContentScrollTo(p.x, p.y);
+                    }
+                    break;
+                }
+                case UPDATE_ZOOM_RANGE: {
+                    WebViewCore.ViewState viewState = (WebViewCore.ViewState) msg.obj;
+                    // mScrollX contains the new minPrefWidth
+                    mZoomManager.updateZoomRange(viewState, getViewWidth(), viewState.mScrollX);
+                    break;
+                }
+                case UPDATE_ZOOM_DENSITY: {
+                    final float density = (Float) msg.obj;
+                    mZoomManager.updateDefaultZoomDensity(density);
+                    break;
+                }
+                case REPLACE_BASE_CONTENT: {
+                    nativeReplaceBaseContent(msg.arg1);
+                    break;
+                }
+                case NEW_PICTURE_MSG_ID: {
+                    // called for new content
+                    final WebViewCore.DrawData draw = (WebViewCore.DrawData) msg.obj;
+                    setNewPicture(draw, true);
+                    break;
+                }
+                case WEBCORE_INITIALIZED_MSG_ID:
+                    // nativeCreate sets mNativeClass to a non-zero value
+                    String drawableDir = BrowserFrame.getRawResFilename(
+                            BrowserFrame.DRAWABLEDIR, mContext);
+                    WindowManager windowManager =
+                            (WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE);
+                    Display display = windowManager.getDefaultDisplay();
+                    nativeCreate(msg.arg1, drawableDir,
+                            ActivityManager.isHighEndGfx(display));
+                    if (mDelaySetPicture != null) {
+                        setNewPicture(mDelaySetPicture, true);
+                        mDelaySetPicture = null;
+                    }
+                    if (mIsPaused) {
+                        nativeSetPauseDrawing(mNativeClass, true);
+                    }
+                    break;
+                case UPDATE_TEXTFIELD_TEXT_MSG_ID:
+                    // Make sure that the textfield is currently focused
+                    // and representing the same node as the pointer.
+                    if (msg.arg2 == mTextGeneration) {
+                        String text = (String) msg.obj;
+                        if (null == text) {
+                            text = "";
+                        }
+                        if (mInputConnection != null &&
+                                mFieldPointer == msg.arg1) {
+                            mInputConnection.setTextAndKeepSelection(text);
+                        }
+                    }
+                    break;
+                case REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID:
+                    displaySoftKeyboard(true);
+                    // fall through to UPDATE_TEXT_SELECTION_MSG_ID
+                case UPDATE_TEXT_SELECTION_MSG_ID:
+                    updateTextSelectionFromMessage(msg.arg1, msg.arg2,
+                            (WebViewCore.TextSelectionData) msg.obj);
+                    break;
+                case FORM_DID_BLUR:
+                    // TODO: Figure out if this is needed for something (b/6111763)
+                    break;
+                case UNHANDLED_NAV_KEY:
+                    // TODO: Support this (b/6109044)
+                    break;
+                case CLEAR_TEXT_ENTRY:
+                    hideSoftKeyboard();
+                    break;
+                case INVAL_RECT_MSG_ID: {
+                    Rect r = (Rect)msg.obj;
+                    if (r == null) {
+                        invalidate();
+                    } else {
+                        // we need to scale r from content into view coords,
+                        // which viewInvalidate() does for us
+                        viewInvalidate(r.left, r.top, r.right, r.bottom);
+                    }
+                    break;
+                }
+
+                case LONG_PRESS_CENTER:
+                    // as this is shared by keydown and trackballdown, reset all
+                    // the states
+                    mGotCenterDown = false;
+                    mTrackballDown = false;
+                    performLongClick();
+                    break;
+
+                case WEBCORE_NEED_TOUCH_EVENTS:
+                    mForwardTouchEvents = (msg.arg1 != 0);
+                    break;
+
+                case PREVENT_TOUCH_ID:
+                    if (inFullScreenMode()) {
+                        break;
+                    }
+                    TouchEventData ted = (TouchEventData) msg.obj;
+
+                    if (mTouchEventQueue.enqueueTouchEvent(ted)) {
+                        // WebCore is responding to us; remove pending timeout.
+                        // It will be re-posted when needed.
+                        removeMessages(PREVENT_DEFAULT_TIMEOUT);
+                    }
+                    break;
+
+                case REQUEST_KEYBOARD:
+                    if (msg.arg1 == 0) {
+                        hideSoftKeyboard();
+                    } else {
+                        displaySoftKeyboard(false);
+                    }
+                    break;
+
+                case DRAG_HELD_MOTIONLESS:
+                    mHeldMotionless = MOTIONLESS_TRUE;
+                    invalidate();
+                    // fall through to keep scrollbars awake
+
+                case AWAKEN_SCROLL_BARS:
+                    if (mTouchMode == TOUCH_DRAG_MODE
+                            && mHeldMotionless == MOTIONLESS_TRUE) {
+                        mWebViewPrivate.awakenScrollBars(ViewConfiguration
+                                .getScrollDefaultDelay(), false);
+                        mPrivateHandler.sendMessageDelayed(mPrivateHandler
+                                .obtainMessage(AWAKEN_SCROLL_BARS),
+                                ViewConfiguration.getScrollDefaultDelay());
+                    }
+                    break;
+
+                case SCREEN_ON:
+                    mWebView.setKeepScreenOn(msg.arg1 == 1);
+                    break;
+
+                case ENTER_FULLSCREEN_VIDEO:
+                    int layerId = msg.arg1;
+
+                    String url = (String) msg.obj;
+                    if (mHTML5VideoViewProxy != null) {
+                        mHTML5VideoViewProxy.enterFullScreenVideo(layerId, url);
+                    }
+                    break;
+
+                case EXIT_FULLSCREEN_VIDEO:
+                    if (mHTML5VideoViewProxy != null) {
+                        mHTML5VideoViewProxy.exitFullScreenVideo();
+                    }
+                    break;
+
+                case SHOW_FULLSCREEN: {
+                    View view = (View) msg.obj;
+                    int orientation = msg.arg1;
+                    int npp = msg.arg2;
+
+                    if (inFullScreenMode()) {
+                        Log.w(LOGTAG, "Should not have another full screen.");
+                        dismissFullScreenMode();
+                    }
+                    mFullScreenHolder = new PluginFullScreenHolder(WebViewClassic.this, orientation, npp);
+                    mFullScreenHolder.setContentView(view);
+                    mFullScreenHolder.show();
+                    invalidate();
+
+                    break;
+                }
+                case HIDE_FULLSCREEN:
+                    dismissFullScreenMode();
+                    break;
+
+                case SHOW_RECT_MSG_ID: {
+                    WebViewCore.ShowRectData data = (WebViewCore.ShowRectData) msg.obj;
+                    int x = getScrollX();
+                    int left = contentToViewX(data.mLeft);
+                    int width = contentToViewDimension(data.mWidth);
+                    int maxWidth = contentToViewDimension(data.mContentWidth);
+                    int viewWidth = getViewWidth();
+                    if (width < viewWidth) {
+                        // center align
+                        x += left + width / 2 - getScrollX() - viewWidth / 2;
+                    } else {
+                        x += (int) (left + data.mXPercentInDoc * width
+                                - getScrollX() - data.mXPercentInView * viewWidth);
+                    }
+                    if (DebugFlags.WEB_VIEW) {
+                        Log.v(LOGTAG, "showRectMsg=(left=" + left + ",width=" +
+                              width + ",maxWidth=" + maxWidth +
+                              ",viewWidth=" + viewWidth + ",x="
+                              + x + ",xPercentInDoc=" + data.mXPercentInDoc +
+                              ",xPercentInView=" + data.mXPercentInView+ ")");
+                    }
+                    // use the passing content width to cap x as the current
+                    // mContentWidth may not be updated yet
+                    x = Math.max(0,
+                            (Math.min(maxWidth, x + viewWidth)) - viewWidth);
+                    int top = contentToViewY(data.mTop);
+                    int height = contentToViewDimension(data.mHeight);
+                    int maxHeight = contentToViewDimension(data.mContentHeight);
+                    int viewHeight = getViewHeight();
+                    int y = (int) (top + data.mYPercentInDoc * height -
+                                   data.mYPercentInView * viewHeight);
+                    if (DebugFlags.WEB_VIEW) {
+                        Log.v(LOGTAG, "showRectMsg=(top=" + top + ",height=" +
+                              height + ",maxHeight=" + maxHeight +
+                              ",viewHeight=" + viewHeight + ",y="
+                              + y + ",yPercentInDoc=" + data.mYPercentInDoc +
+                              ",yPercentInView=" + data.mYPercentInView+ ")");
+                    }
+                    // use the passing content height to cap y as the current
+                    // mContentHeight may not be updated yet
+                    y = Math.max(0,
+                            (Math.min(maxHeight, y + viewHeight) - viewHeight));
+                    // We need to take into account the visible title height
+                    // when scrolling since y is an absolute view position.
+                    y = Math.max(0, y - getVisibleTitleHeightImpl());
+                    mWebView.scrollTo(x, y);
+                    }
+                    break;
+
+                case CENTER_FIT_RECT:
+                    centerFitRect((Rect)msg.obj);
+                    break;
+
+                case SET_SCROLLBAR_MODES:
+                    mHorizontalScrollBarMode = msg.arg1;
+                    mVerticalScrollBarMode = msg.arg2;
+                    break;
+
+                case SELECTION_STRING_CHANGED:
+                    if (mAccessibilityInjector != null) {
+                        String selectionString = (String) msg.obj;
+                        mAccessibilityInjector.onSelectionStringChange(selectionString);
+                    }
+                    break;
+
+                case HIT_TEST_RESULT:
+                    WebKitHitTest hit = (WebKitHitTest) msg.obj;
+                    mFocusedNode = hit;
+                    setTouchHighlightRects(hit);
+                    setHitTestResult(hit);
+                    break;
+
+                case SAVE_WEBARCHIVE_FINISHED:
+                    SaveWebArchiveMessage saveMessage = (SaveWebArchiveMessage)msg.obj;
+                    if (saveMessage.mCallback != null) {
+                        saveMessage.mCallback.onReceiveValue(saveMessage.mResultFile);
+                    }
+                    break;
+
+                case SET_AUTOFILLABLE:
+                    mAutoFillData = (WebViewCore.AutoFillData) msg.obj;
+                    // TODO: Support (b/6083041)
+                    break;
+
+                case AUTOFILL_COMPLETE:
+                    // TODO: Support (b/6083041)
+                    break;
+
+                case COPY_TO_CLIPBOARD:
+                    copyToClipboard((String) msg.obj);
+                    break;
+
+                case INIT_EDIT_FIELD:
+                    if (mInputConnection != null) {
+                        TextFieldInitData initData = (TextFieldInitData) msg.obj;
+                        mTextGeneration = 0;
+                        mFieldPointer = initData.mFieldPointer;
+                        mInputConnection.initEditorInfo(initData);
+                        mInputConnection.setTextAndKeepSelection(initData.mText);
+                    }
+                    break;
+
+                case REPLACE_TEXT:{
+                    String text = (String)msg.obj;
+                    int start = msg.arg1;
+                    int end = msg.arg2;
+                    int cursorPosition = start + text.length();
+                    replaceTextfieldText(start, end, text,
+                            cursorPosition, cursorPosition);
+                    break;
+                }
+
+                case UPDATE_MATCH_COUNT: {
+                    if (mFindCallback != null) {
+                        mFindCallback.updateMatchCount(msg.arg1, msg.arg2,
+                            (String) msg.obj);
+                    }
+                    break;
+                }
+                case CLEAR_CARET_HANDLE:
+                    selectionDone();
+                    break;
+
+                case KEY_PRESS:
+                    mWebViewCore.sendMessage(EventHub.KEY_PRESS, msg.arg1);
+                    break;
+
+                default:
+                    super.handleMessage(msg);
+                    break;
+            }
+        }
+    }
+
+    private void setHitTestTypeFromUrl(String url) {
+        String substr = null;
+        if (url.startsWith(SCHEME_GEO)) {
+            mInitialHitTestResult.setType(HitTestResult.GEO_TYPE);
+            substr = url.substring(SCHEME_GEO.length());
+        } else if (url.startsWith(SCHEME_TEL)) {
+            mInitialHitTestResult.setType(HitTestResult.PHONE_TYPE);
+            substr = url.substring(SCHEME_TEL.length());
+        } else if (url.startsWith(SCHEME_MAILTO)) {
+            mInitialHitTestResult.setType(HitTestResult.EMAIL_TYPE);
+            substr = url.substring(SCHEME_MAILTO.length());
+        } else {
+            mInitialHitTestResult.setType(HitTestResult.SRC_ANCHOR_TYPE);
+            mInitialHitTestResult.setExtra(url);
+            return;
+        }
+        try {
+            mInitialHitTestResult.setExtra(URLDecoder.decode(substr, "UTF-8"));
+        } catch (Throwable e) {
+            Log.w(LOGTAG, "Failed to decode URL! " + substr, e);
+            mInitialHitTestResult.setType(HitTestResult.UNKNOWN_TYPE);
+        }
+    }
+
+    private void setHitTestResult(WebKitHitTest hit) {
+        if (hit == null) {
+            mInitialHitTestResult = null;
+            return;
+        }
+        mInitialHitTestResult = new HitTestResult();
+        if (hit.mLinkUrl != null) {
+            setHitTestTypeFromUrl(hit.mLinkUrl);
+            if (hit.mImageUrl != null
+                    && mInitialHitTestResult.getType() == HitTestResult.SRC_ANCHOR_TYPE) {
+                mInitialHitTestResult.setType(HitTestResult.SRC_IMAGE_ANCHOR_TYPE);
+                mInitialHitTestResult.setExtra(hit.mImageUrl);
+            }
+        } else if (hit.mImageUrl != null) {
+            mInitialHitTestResult.setType(HitTestResult.IMAGE_TYPE);
+            mInitialHitTestResult.setExtra(hit.mImageUrl);
+        } else if (hit.mEditable) {
+            mInitialHitTestResult.setType(HitTestResult.EDIT_TEXT_TYPE);
+        } else if (hit.mIntentUrl != null) {
+            setHitTestTypeFromUrl(hit.mIntentUrl);
+        }
+    }
+
+    private boolean shouldDrawHighlightRect() {
+        if (mFocusedNode == null || mInitialHitTestResult == null) {
+            return false;
+        }
+        if (mTouchHighlightRegion.isEmpty()) {
+            return false;
+        }
+        if (mFocusedNode.mHasFocus && !mWebView.isInTouchMode()) {
+            return !mFocusedNode.mEditable;
+        }
+        if (mInitialHitTestResult.getType() == HitTestResult.UNKNOWN_TYPE) {
+            return false;
+        }
+        long delay = System.currentTimeMillis() - mTouchHighlightRequested;
+        if (delay < ViewConfiguration.getTapTimeout()) {
+            Rect r = mTouchHighlightRegion.getBounds();
+            mWebView.postInvalidateDelayed(delay, r.left, r.top, r.right, r.bottom);
+            return false;
+        }
+        return true;
+    }
+
+
+    private FocusTransitionDrawable mFocusTransition = null;
+    static class FocusTransitionDrawable extends Drawable {
+        Region mPreviousRegion;
+        Region mNewRegion;
+        float mProgress = 0;
+        WebViewClassic mWebView;
+        Paint mPaint;
+        int mMaxAlpha;
+        Point mTranslate;
+
+        public FocusTransitionDrawable(WebViewClassic view) {
+            mWebView = view;
+            mPaint = new Paint(mWebView.mTouchHightlightPaint);
+            mMaxAlpha = mPaint.getAlpha();
+        }
+
+        @Override
+        public void setColorFilter(ColorFilter cf) {
+        }
+
+        @Override
+        public void setAlpha(int alpha) {
+        }
+
+        @Override
+        public int getOpacity() {
+            return 0;
+        }
+
+        public void setProgress(float p) {
+            mProgress = p;
+            if (mWebView.mFocusTransition == this) {
+                if (mProgress == 1f)
+                    mWebView.mFocusTransition = null;
+                mWebView.invalidate();
+            }
+        }
+
+        public float getProgress() {
+            return mProgress;
+        }
+
+        @Override
+        public void draw(Canvas canvas) {
+            if (mTranslate == null) {
+                Rect bounds = mPreviousRegion.getBounds();
+                Point from = new Point(bounds.centerX(), bounds.centerY());
+                mNewRegion.getBounds(bounds);
+                Point to = new Point(bounds.centerX(), bounds.centerY());
+                mTranslate = new Point(from.x - to.x, from.y - to.y);
+            }
+            int alpha = (int) (mProgress * mMaxAlpha);
+            RegionIterator iter = new RegionIterator(mPreviousRegion);
+            Rect r = new Rect();
+            mPaint.setAlpha(mMaxAlpha - alpha);
+            float tx = mTranslate.x * mProgress;
+            float ty = mTranslate.y * mProgress;
+            int save = canvas.save(Canvas.MATRIX_SAVE_FLAG);
+            canvas.translate(-tx, -ty);
+            while (iter.next(r)) {
+                canvas.drawRect(r, mPaint);
+            }
+            canvas.restoreToCount(save);
+            iter = new RegionIterator(mNewRegion);
+            r = new Rect();
+            mPaint.setAlpha(alpha);
+            save = canvas.save(Canvas.MATRIX_SAVE_FLAG);
+            tx = mTranslate.x - tx;
+            ty = mTranslate.y - ty;
+            canvas.translate(tx, ty);
+            while (iter.next(r)) {
+                canvas.drawRect(r, mPaint);
+            }
+            canvas.restoreToCount(save);
+        }
+    };
+
+    private boolean shouldAnimateTo(WebKitHitTest hit) {
+        // TODO: Don't be annoying or throw out the animation entirely
+        return false;
+    }
+
+    private void setTouchHighlightRects(WebKitHitTest hit) {
+        FocusTransitionDrawable transition = null;
+        if (shouldAnimateTo(hit)) {
+            transition = new FocusTransitionDrawable(this);
+        }
+        Rect[] rects = hit != null ? hit.mTouchRects : null;
+        if (!mTouchHighlightRegion.isEmpty()) {
+            mWebView.invalidate(mTouchHighlightRegion.getBounds());
+            if (transition != null) {
+                transition.mPreviousRegion = new Region(mTouchHighlightRegion);
+            }
+            mTouchHighlightRegion.setEmpty();
+        }
+        if (rects != null) {
+            mTouchHightlightPaint.setColor(hit.mTapHighlightColor);
+            for (Rect rect : rects) {
+                Rect viewRect = contentToViewRect(rect);
+                // some sites, like stories in nytimes.com, set
+                // mouse event handler in the top div. It is not
+                // user friendly to highlight the div if it covers
+                // more than half of the screen.
+                if (viewRect.width() < getWidth() >> 1
+                        || viewRect.height() < getHeight() >> 1) {
+                    mTouchHighlightRegion.union(viewRect);
+                } else {
+                    Log.w(LOGTAG, "Skip the huge selection rect:"
+                            + viewRect);
+                }
+            }
+            mWebView.invalidate(mTouchHighlightRegion.getBounds());
+            if (transition != null && transition.mPreviousRegion != null) {
+                transition.mNewRegion = new Region(mTouchHighlightRegion);
+                mFocusTransition = transition;
+                ObjectAnimator animator = ObjectAnimator.ofFloat(
+                        mFocusTransition, "progress", 1f);
+                animator.start();
+            }
+        }
+    }
+
+    // Interface to allow the profiled WebView to hook the page swap notifications.
+    public interface PageSwapDelegate {
+        void onPageSwapOccurred(boolean notifyAnimationStarted);
+    }
+
+    /** @hide Called by JNI when pages are swapped (only occurs with hardware
+     * acceleration) */
+    protected void pageSwapCallback(boolean notifyAnimationStarted) {
+        mWebViewCore.resumeWebKitDraw();
+        if (notifyAnimationStarted) {
+            mWebViewCore.sendMessage(EventHub.NOTIFY_ANIMATION_STARTED);
+        }
+        if (mWebView instanceof PageSwapDelegate) {
+            // This provides a hook for ProfiledWebView to observe the tile page swaps.
+            ((PageSwapDelegate) mWebView).onPageSwapOccurred(notifyAnimationStarted);
+        }
+    }
+
+    void setNewPicture(final WebViewCore.DrawData draw, boolean updateBaseLayer) {
+        if (mNativeClass == 0) {
+            if (mDelaySetPicture != null) {
+                throw new IllegalStateException("Tried to setNewPicture with"
+                        + " a delay picture already set! (memory leak)");
+            }
+            // Not initialized yet, delay set
+            mDelaySetPicture = draw;
+            return;
+        }
+        WebViewCore.ViewState viewState = draw.mViewState;
+        boolean isPictureAfterFirstLayout = viewState != null;
+
+        if (updateBaseLayer) {
+            setBaseLayer(draw.mBaseLayer, draw.mInvalRegion,
+                    getSettings().getShowVisualIndicator(),
+                    isPictureAfterFirstLayout);
+        }
+        final Point viewSize = draw.mViewSize;
+        // We update the layout (i.e. request a layout from the
+        // view system) if the last view size that we sent to
+        // WebCore matches the view size of the picture we just
+        // received in the fixed dimension.
+        final boolean updateLayout = viewSize.x == mLastWidthSent
+                && viewSize.y == mLastHeightSent;
+        // Don't send scroll event for picture coming from webkit,
+        // since the new picture may cause a scroll event to override
+        // the saved history scroll position.
+        mSendScrollEvent = false;
+        recordNewContentSize(draw.mContentSize.x,
+                draw.mContentSize.y, updateLayout);
+        if (isPictureAfterFirstLayout) {
+            // Reset the last sent data here since dealing with new page.
+            mLastWidthSent = 0;
+            mZoomManager.onFirstLayout(draw);
+            int scrollX = viewState.mShouldStartScrolledRight
+                    ? getContentWidth() : viewState.mScrollX;
+            int scrollY = viewState.mScrollY;
+            setContentScrollTo(scrollX, scrollY);
+            if (!mDrawHistory) {
+                // As we are on a new page, hide the keyboard
+                hideSoftKeyboard();
+            }
+        }
+        mSendScrollEvent = true;
+
+        if (DebugFlags.WEB_VIEW) {
+            Rect b = draw.mInvalRegion.getBounds();
+            Log.v(LOGTAG, "NEW_PICTURE_MSG_ID {" +
+                    b.left+","+b.top+","+b.right+","+b.bottom+"}");
+        }
+        invalidateContentRect(draw.mInvalRegion.getBounds());
+
+        if (mPictureListener != null) {
+            mPictureListener.onNewPicture(getWebView(), capturePicture());
+        }
+
+        // update the zoom information based on the new picture
+        mZoomManager.onNewPicture(draw);
+
+        if (isPictureAfterFirstLayout) {
+            mViewManager.postReadyToDrawAll();
+        }
+    }
+
+    /**
+     * Used when receiving messages for REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID
+     * and UPDATE_TEXT_SELECTION_MSG_ID.
+     */
+    private void updateTextSelectionFromMessage(int nodePointer,
+            int textGeneration, WebViewCore.TextSelectionData data) {
+        if (textGeneration == mTextGeneration) {
+            if (mInputConnection != null && mFieldPointer == nodePointer) {
+                mInputConnection.setSelection(data.mStart, data.mEnd);
+            }
+        }
+        nativeSetTextSelection(mNativeClass, data.mSelectTextPtr);
+
+        if (data.mSelectTextPtr != 0 &&
+                (data.mStart != data.mEnd ||
+                (mFieldPointer == nodePointer && mFieldPointer != 0))) {
+            mIsCaretSelection = (data.mStart == data.mEnd);
+            if (!mSelectingText) {
+                setupWebkitSelect();
+            } else if (!mSelectionStarted) {
+                syncSelectionCursors();
+            }
+            if (mIsCaretSelection) {
+                resetCaretTimer();
+            }
+        } else {
+            selectionDone();
+        }
+        invalidate();
+    }
+
+    // Class used to use a dropdown for a <select> element
+    private class InvokeListBox implements Runnable {
+        // Whether the listbox allows multiple selection.
+        private boolean     mMultiple;
+        // Passed in to a list with multiple selection to tell
+        // which items are selected.
+        private int[]       mSelectedArray;
+        // Passed in to a list with single selection to tell
+        // where the initial selection is.
+        private int         mSelection;
+
+        private Container[] mContainers;
+
+        // Need these to provide stable ids to my ArrayAdapter,
+        // which normally does not have stable ids. (Bug 1250098)
+        private class Container extends Object {
+            /**
+             * Possible values for mEnabled.  Keep in sync with OptionStatus in
+             * WebViewCore.cpp
+             */
+            final static int OPTGROUP = -1;
+            final static int OPTION_DISABLED = 0;
+            final static int OPTION_ENABLED = 1;
+
+            String  mString;
+            int     mEnabled;
+            int     mId;
+
+            @Override
+            public String toString() {
+                return mString;
+            }
+        }
+
+        /**
+         *  Subclass ArrayAdapter so we can disable OptionGroupLabels,
+         *  and allow filtering.
+         */
+        private class MyArrayListAdapter extends ArrayAdapter<Container> {
+            public MyArrayListAdapter() {
+                super(WebViewClassic.this.mContext,
+                        mMultiple ? com.android.internal.R.layout.select_dialog_multichoice :
+                        com.android.internal.R.layout.webview_select_singlechoice,
+                        mContainers);
+            }
+
+            @Override
+            public View getView(int position, View convertView,
+                    ViewGroup parent) {
+                // Always pass in null so that we will get a new CheckedTextView
+                // Otherwise, an item which was previously used as an <optgroup>
+                // element (i.e. has no check), could get used as an <option>
+                // element, which needs a checkbox/radio, but it would not have
+                // one.
+                convertView = super.getView(position, null, parent);
+                Container c = item(position);
+                if (c != null && Container.OPTION_ENABLED != c.mEnabled) {
+                    // ListView does not draw dividers between disabled and
+                    // enabled elements.  Use a LinearLayout to provide dividers
+                    LinearLayout layout = new LinearLayout(mContext);
+                    layout.setOrientation(LinearLayout.VERTICAL);
+                    if (position > 0) {
+                        View dividerTop = new View(mContext);
+                        dividerTop.setBackgroundResource(
+                                android.R.drawable.divider_horizontal_bright);
+                        layout.addView(dividerTop);
+                    }
+
+                    if (Container.OPTGROUP == c.mEnabled) {
+                        // Currently select_dialog_multichoice uses CheckedTextViews.
+                        // If that changes, the class cast will no longer be valid.
+                        if (mMultiple) {
+                            Assert.assertTrue(convertView instanceof CheckedTextView);
+                            ((CheckedTextView) convertView).setCheckMarkDrawable(null);
+                        }
+                    } else {
+                        // c.mEnabled == Container.OPTION_DISABLED
+                        // Draw the disabled element in a disabled state.
+                        convertView.setEnabled(false);
+                    }
+
+                    layout.addView(convertView);
+                    if (position < getCount() - 1) {
+                        View dividerBottom = new View(mContext);
+                        dividerBottom.setBackgroundResource(
+                                android.R.drawable.divider_horizontal_bright);
+                        layout.addView(dividerBottom);
+                    }
+                    return layout;
+                }
+                return convertView;
+            }
+
+            @Override
+            public boolean hasStableIds() {
+                // AdapterView's onChanged method uses this to determine whether
+                // to restore the old state.  Return false so that the old (out
+                // of date) state does not replace the new, valid state.
+                return false;
+            }
+
+            private Container item(int position) {
+                if (position < 0 || position >= getCount()) {
+                    return null;
+                }
+                return getItem(position);
+            }
+
+            @Override
+            public long getItemId(int position) {
+                Container item = item(position);
+                if (item == null) {
+                    return -1;
+                }
+                return item.mId;
+            }
+
+            @Override
+            public boolean areAllItemsEnabled() {
+                return false;
+            }
+
+            @Override
+            public boolean isEnabled(int position) {
+                Container item = item(position);
+                if (item == null) {
+                    return false;
+                }
+                return Container.OPTION_ENABLED == item.mEnabled;
+            }
+        }
+
+        private InvokeListBox(String[] array, int[] enabled, int[] selected) {
+            mMultiple = true;
+            mSelectedArray = selected;
+
+            int length = array.length;
+            mContainers = new Container[length];
+            for (int i = 0; i < length; i++) {
+                mContainers[i] = new Container();
+                mContainers[i].mString = array[i];
+                mContainers[i].mEnabled = enabled[i];
+                mContainers[i].mId = i;
+            }
+        }
+
+        private InvokeListBox(String[] array, int[] enabled, int selection) {
+            mSelection = selection;
+            mMultiple = false;
+
+            int length = array.length;
+            mContainers = new Container[length];
+            for (int i = 0; i < length; i++) {
+                mContainers[i] = new Container();
+                mContainers[i].mString = array[i];
+                mContainers[i].mEnabled = enabled[i];
+                mContainers[i].mId = i;
+            }
+        }
+
+        /*
+         * Whenever the data set changes due to filtering, this class ensures
+         * that the checked item remains checked.
+         */
+        private class SingleDataSetObserver extends DataSetObserver {
+            private long        mCheckedId;
+            private ListView    mListView;
+            private Adapter     mAdapter;
+
+            /*
+             * Create a new observer.
+             * @param id The ID of the item to keep checked.
+             * @param l ListView for getting and clearing the checked states
+             * @param a Adapter for getting the IDs
+             */
+            public SingleDataSetObserver(long id, ListView l, Adapter a) {
+                mCheckedId = id;
+                mListView = l;
+                mAdapter = a;
+            }
+
+            @Override
+            public void onChanged() {
+                // The filter may have changed which item is checked.  Find the
+                // item that the ListView thinks is checked.
+                int position = mListView.getCheckedItemPosition();
+                long id = mAdapter.getItemId(position);
+                if (mCheckedId != id) {
+                    // Clear the ListView's idea of the checked item, since
+                    // it is incorrect
+                    mListView.clearChoices();
+                    // Search for mCheckedId.  If it is in the filtered list,
+                    // mark it as checked
+                    int count = mAdapter.getCount();
+                    for (int i = 0; i < count; i++) {
+                        if (mAdapter.getItemId(i) == mCheckedId) {
+                            mListView.setItemChecked(i, true);
+                            break;
+                        }
+                    }
+                }
+            }
+        }
+
+        @Override
+        public void run() {
+            final ListView listView = (ListView) LayoutInflater.from(mContext)
+                    .inflate(com.android.internal.R.layout.select_dialog, null);
+            final MyArrayListAdapter adapter = new MyArrayListAdapter();
+            AlertDialog.Builder b = new AlertDialog.Builder(mContext)
+                    .setView(listView).setCancelable(true)
+                    .setInverseBackgroundForced(true);
+
+            if (mMultiple) {
+                b.setPositiveButton(android.R.string.ok, new DialogInterface.OnClickListener() {
+                    @Override
+                    public void onClick(DialogInterface dialog, int which) {
+                        mWebViewCore.sendMessage(
+                                EventHub.LISTBOX_CHOICES,
+                                adapter.getCount(), 0,
+                                listView.getCheckedItemPositions());
+                    }});
+                b.setNegativeButton(android.R.string.cancel,
+                        new DialogInterface.OnClickListener() {
+                    @Override
+                    public void onClick(DialogInterface dialog, int which) {
+                        mWebViewCore.sendMessage(
+                                EventHub.SINGLE_LISTBOX_CHOICE, -2, 0);
+                }});
+            }
+            mListBoxDialog = b.create();
+            listView.setAdapter(adapter);
+            listView.setFocusableInTouchMode(true);
+            // There is a bug (1250103) where the checks in a ListView with
+            // multiple items selected are associated with the positions, not
+            // the ids, so the items do not properly retain their checks when
+            // filtered.  Do not allow filtering on multiple lists until
+            // that bug is fixed.
+
+            listView.setTextFilterEnabled(!mMultiple);
+            if (mMultiple) {
+                listView.setChoiceMode(ListView.CHOICE_MODE_MULTIPLE);
+                int length = mSelectedArray.length;
+                for (int i = 0; i < length; i++) {
+                    listView.setItemChecked(mSelectedArray[i], true);
+                }
+            } else {
+                listView.setOnItemClickListener(new OnItemClickListener() {
+                    @Override
+                    public void onItemClick(AdapterView<?> parent, View v,
+                            int position, long id) {
+                        // Rather than sending the message right away, send it
+                        // after the page regains focus.
+                        mListBoxMessage = Message.obtain(null,
+                                EventHub.SINGLE_LISTBOX_CHOICE, (int) id, 0);
+                        mListBoxDialog.dismiss();
+                        mListBoxDialog = null;
+                    }
+                });
+                if (mSelection != -1) {
+                    listView.setSelection(mSelection);
+                    listView.setChoiceMode(ListView.CHOICE_MODE_SINGLE);
+                    listView.setItemChecked(mSelection, true);
+                    DataSetObserver observer = new SingleDataSetObserver(
+                            adapter.getItemId(mSelection), listView, adapter);
+                    adapter.registerDataSetObserver(observer);
+                }
+            }
+            mListBoxDialog.setOnCancelListener(new DialogInterface.OnCancelListener() {
+                @Override
+                public void onCancel(DialogInterface dialog) {
+                    mWebViewCore.sendMessage(
+                                EventHub.SINGLE_LISTBOX_CHOICE, -2, 0);
+                    mListBoxDialog = null;
+                }
+            });
+            mListBoxDialog.show();
+        }
+    }
+
+    private Message mListBoxMessage;
+
+    /*
+     * Request a dropdown menu for a listbox with multiple selection.
+     *
+     * @param array Labels for the listbox.
+     * @param enabledArray  State for each element in the list.  See static
+     *      integers in Container class.
+     * @param selectedArray Which positions are initally selected.
+     */
+    void requestListBox(String[] array, int[] enabledArray, int[]
+            selectedArray) {
+        mPrivateHandler.post(
+                new InvokeListBox(array, enabledArray, selectedArray));
+    }
+
+    /*
+     * Request a dropdown menu for a listbox with single selection or a single
+     * <select> element.
+     *
+     * @param array Labels for the listbox.
+     * @param enabledArray  State for each element in the list.  See static
+     *      integers in Container class.
+     * @param selection Which position is initally selected.
+     */
+    void requestListBox(String[] array, int[] enabledArray, int selection) {
+        mPrivateHandler.post(
+                new InvokeListBox(array, enabledArray, selection));
+    }
+
+    private int getScaledMaxXScroll() {
+        int width;
+        if (mHeightCanMeasure == false) {
+            width = getViewWidth() / 4;
+        } else {
+            Rect visRect = new Rect();
+            calcOurVisibleRect(visRect);
+            width = visRect.width() / 2;
+        }
+        // FIXME the divisor should be retrieved from somewhere
+        return viewToContentX(width);
+    }
+
+    private int getScaledMaxYScroll() {
+        int height;
+        if (mHeightCanMeasure == false) {
+            height = getViewHeight() / 4;
+        } else {
+            Rect visRect = new Rect();
+            calcOurVisibleRect(visRect);
+            height = visRect.height() / 2;
+        }
+        // FIXME the divisor should be retrieved from somewhere
+        // the closest thing today is hard-coded into ScrollView.java
+        // (from ScrollView.java, line 363)   int maxJump = height/2;
+        return Math.round(height * mZoomManager.getInvScale());
+    }
+
+    /**
+     * Called by JNI to invalidate view
+     */
+    private void viewInvalidate() {
+        invalidate();
+    }
+
+    /**
+     * Pass the key directly to the page.  This assumes that
+     * nativePageShouldHandleShiftAndArrows() returned true.
+     */
+    private void letPageHandleNavKey(int keyCode, long time, boolean down, int metaState) {
+        int keyEventAction;
+        int eventHubAction;
+        if (down) {
+            keyEventAction = KeyEvent.ACTION_DOWN;
+            eventHubAction = EventHub.KEY_DOWN;
+            mWebView.playSoundEffect(keyCodeToSoundsEffect(keyCode));
+        } else {
+            keyEventAction = KeyEvent.ACTION_UP;
+            eventHubAction = EventHub.KEY_UP;
+        }
+
+        KeyEvent event = new KeyEvent(time, time, keyEventAction, keyCode,
+                1, (metaState & KeyEvent.META_SHIFT_ON)
+                | (metaState & KeyEvent.META_ALT_ON)
+                | (metaState & KeyEvent.META_SYM_ON)
+                , KeyCharacterMap.VIRTUAL_KEYBOARD, 0, 0);
+        mWebViewCore.sendMessage(eventHubAction, event);
+    }
+
+    /**
+     * @return Whether accessibility script has been injected.
+     */
+    private boolean accessibilityScriptInjected() {
+        // TODO: Maybe the injected script should announce its presence in
+        // the page meta-tag so the nativePageShouldHandleShiftAndArrows
+        // will check that as one of the conditions it looks for
+        return mAccessibilityScriptInjected;
+    }
+
+    /**
+     * Set the background color. It's white by default. Pass
+     * zero to make the view transparent.
+     * @param color   the ARGB color described by Color.java
+     */
+    @Override
+    public void setBackgroundColor(int color) {
+        mBackgroundColor = color;
+        mWebViewCore.sendMessage(EventHub.SET_BACKGROUND_COLOR, color);
+    }
+
+    /**
+     * @deprecated This method is now obsolete.
+     */
+    @Deprecated
+    public void debugDump() {
+    }
+
+    /**
+     * Draw the HTML page into the specified canvas. This call ignores any
+     * view-specific zoom, scroll offset, or other changes. It does not draw
+     * any view-specific chrome, such as progress or URL bars.
+     *
+     * @hide only needs to be accessible to Browser and testing
+     */
+    public void drawPage(Canvas canvas) {
+        calcOurContentVisibleRectF(mVisibleContentRect);
+        nativeDraw(canvas, mVisibleContentRect, 0, 0, false);
+    }
+
+    /**
+     * Enable the communication b/t the webView and VideoViewProxy
+     *
+     * @hide only used by the Browser
+     */
+    public void setHTML5VideoViewProxy(HTML5VideoViewProxy proxy) {
+        mHTML5VideoViewProxy = proxy;
+    }
+
+    /**
+     * Set the time to wait between passing touches to WebCore. See also the
+     * TOUCH_SENT_INTERVAL member for further discussion.
+     *
+     * @hide This is only used by the DRT test application.
+     */
+    public void setTouchInterval(int interval) {
+        mCurrentTouchInterval = interval;
+    }
+
+    /**
+     * Copy text into the clipboard. This is called indirectly from
+     * WebViewCore.
+     * @param text The text to put into the clipboard.
+     */
+    private void copyToClipboard(String text) {
+        ClipboardManager cm = (ClipboardManager)mContext
+                .getSystemService(Context.CLIPBOARD_SERVICE);
+        ClipData clip = ClipData.newPlainText(getTitle(), text);
+        cm.setPrimaryClip(clip);
+    }
+
+    /*package*/ void autoFillForm(int autoFillQueryId) {
+        mWebViewCore.sendMessage(EventHub.AUTOFILL_FORM, autoFillQueryId, /* unused */0);
+    }
+
+    /* package */ ViewManager getViewManager() {
+        return mViewManager;
+    }
+
+    private static void checkThread() {
+        if (Looper.myLooper() != Looper.getMainLooper()) {
+            Throwable throwable = new Throwable(
+                    "Warning: A WebView method was called on thread '" +
+                    Thread.currentThread().getName() + "'. " +
+                    "All WebView methods must be called on the UI thread. " +
+                    "Future versions of WebView may not support use on other threads.");
+            Log.w(LOGTAG, Log.getStackTraceString(throwable));
+            StrictMode.onWebViewMethodCalledOnWrongThread(throwable);
+        }
+    }
+
+    /** @hide send content invalidate */
+    protected void contentInvalidateAll() {
+        if (mWebViewCore != null && !mBlockWebkitViewMessages) {
+            mWebViewCore.sendMessage(EventHub.CONTENT_INVALIDATE_ALL);
+        }
+    }
+
+    /** @hide discard all textures from tiles. Used in Profiled WebView */
+    public void discardAllTextures() {
+        nativeDiscardAllTextures();
+    }
+
+    /**
+     * Begin collecting per-tile profiling data
+     *
+     * @hide only used by profiling tests
+     */
+    public void tileProfilingStart() {
+        nativeTileProfilingStart();
+    }
+    /**
+     * Return per-tile profiling data
+     *
+     * @hide only used by profiling tests
+     */
+    public float tileProfilingStop() {
+        return nativeTileProfilingStop();
+    }
+
+    /** @hide only used by profiling tests */
+    public void tileProfilingClear() {
+        nativeTileProfilingClear();
+    }
+    /** @hide only used by profiling tests */
+    public int tileProfilingNumFrames() {
+        return nativeTileProfilingNumFrames();
+    }
+    /** @hide only used by profiling tests */
+    public int tileProfilingNumTilesInFrame(int frame) {
+        return nativeTileProfilingNumTilesInFrame(frame);
+    }
+    /** @hide only used by profiling tests */
+    public int tileProfilingGetInt(int frame, int tile, String key) {
+        return nativeTileProfilingGetInt(frame, tile, key);
+    }
+    /** @hide only used by profiling tests */
+    public float tileProfilingGetFloat(int frame, int tile, String key) {
+        return nativeTileProfilingGetFloat(frame, tile, key);
+    }
+
+    /**
+     * Checks the focused content for an editable text field. This can be
+     * text input or ContentEditable.
+     * @return true if the focused item is an editable text field.
+     */
+    boolean focusCandidateIsEditableText() {
+        if (mFocusedNode != null) {
+            return mFocusedNode.mEditable;
+        }
+        return false;
+    }
+
+    // Called via JNI
+    private void postInvalidate() {
+        mWebView.postInvalidate();
+    }
+
+    private native void     nativeCreate(int ptr, String drawableDir, boolean isHighEndGfx);
+    private native void     nativeDebugDump();
+    private native void     nativeDestroy();
+
+    /**
+     * Draw the picture set with a background color and extra. If
+     * "splitIfNeeded" is true and the return value is not 0, the return value
+     * MUST be passed to WebViewCore with SPLIT_PICTURE_SET message so that the
+     * native allocation can be freed.
+     */
+    private native int nativeDraw(Canvas canvas, RectF visibleRect,
+            int color, int extra, boolean splitIfNeeded);
+    private native void     nativeDumpDisplayTree(String urlOrNull);
+    private native boolean  nativeEvaluateLayersAnimations(int nativeInstance);
+    private native int      nativeGetDrawGLFunction(int nativeInstance, Rect rect,
+            Rect viewRect, RectF visibleRect, float scale, int extras);
+    private native void     nativeUpdateDrawGLFunction(Rect rect, Rect viewRect,
+            RectF visibleRect, float scale);
+    private native String   nativeGetSelection();
+    private native Rect     nativeLayerBounds(int layer);
+    private native void     nativeSetHeightCanMeasure(boolean measure);
+    private native boolean  nativeSetBaseLayer(int nativeInstance,
+            int layer, Region invalRegion,
+            boolean showVisualIndicator, boolean isPictureAfterFirstLayout);
+    private native int      nativeGetBaseLayer();
+    private native void     nativeReplaceBaseContent(int content);
+    private native void     nativeCopyBaseContentToPicture(Picture pict);
+    private native boolean  nativeHasContent();
+    private native void     nativeStopGL();
+    private native Rect     nativeSubtractLayers(Rect content);
+    private native void     nativeDiscardAllTextures();
+    private native void     nativeTileProfilingStart();
+    private native float    nativeTileProfilingStop();
+    private native void     nativeTileProfilingClear();
+    private native int      nativeTileProfilingNumFrames();
+    private native int      nativeTileProfilingNumTilesInFrame(int frame);
+    private native int      nativeTileProfilingGetInt(int frame, int tile, String key);
+    private native float    nativeTileProfilingGetFloat(int frame, int tile, String key);
+
+    private native void     nativeUseHardwareAccelSkia(boolean enabled);
+
+    // Returns a pointer to the scrollable LayerAndroid at the given point.
+    private native int      nativeScrollableLayer(int x, int y, Rect scrollRect,
+            Rect scrollBounds);
+    /**
+     * Scroll the specified layer.
+     * @param layer Id of the layer to scroll, as determined by nativeScrollableLayer.
+     * @param newX Destination x position to which to scroll.
+     * @param newY Destination y position to which to scroll.
+     * @return True if the layer is successfully scrolled.
+     */
+    private native boolean  nativeScrollLayer(int layer, int newX, int newY);
+    private native void     nativeSetIsScrolling(boolean isScrolling);
+    private native int      nativeGetBackgroundColor();
+    native boolean  nativeSetProperty(String key, String value);
+    native String   nativeGetProperty(String key);
+    /**
+     * See {@link ComponentCallbacks2} for the trim levels and descriptions
+     */
+    private static native void     nativeOnTrimMemory(int level);
+    private static native void nativeSetPauseDrawing(int instance, boolean pause);
+    private static native void nativeSetTextSelection(int instance, int selection);
+    private static native int nativeGetHandleLayerId(int instance, int handle,
+            Rect cursorLocation);
+    private static native boolean nativeIsBaseFirst(int instance);
+}
diff --git a/core/java/android/webkit/WebViewCore.java b/core/java/android/webkit/WebViewCore.java
index 93fd92b..65356f5 100644
--- a/core/java/android/webkit/WebViewCore.java
+++ b/core/java/android/webkit/WebViewCore.java
@@ -39,7 +39,7 @@
 import android.view.MotionEvent;
 import android.view.SurfaceView;
 import android.view.View;
-import android.webkit.WebView.FocusNodeHref;
+import android.webkit.WebViewClassic.FocusNodeHref;
 
 import junit.framework.Assert;
 
@@ -72,11 +72,12 @@
      */
 
     // The WebView that corresponds to this WebViewCore.
-    private WebView mWebView;
+    // TODO: rename this field (and its getter) to mWebViewClassic or  mWebViewImpl.
+    private WebViewClassic mWebView;
     // Proxy for handling callbacks from native code
     private final CallbackProxy mCallbackProxy;
     // Settings object for maintaining all settings
-    private final WebSettings mSettings;
+    private final WebSettingsClassic mSettings;
     // Context for initializing the BrowserFrame with the proper assets.
     private final Context mContext;
     // The pointer to a native view object.
@@ -142,7 +143,7 @@
     // debugging other classes that require operation within the WebCore thread.
     /* package */ static final String THREAD_NAME = "WebViewCoreThread";
 
-    public WebViewCore(Context context, WebView w, CallbackProxy proxy,
+    public WebViewCore(Context context, WebViewClassic w, CallbackProxy proxy,
             Map<String, Object> javascriptInterfaces) {
         // No need to assign this in the WebCore thread.
         mCallbackProxy = proxy;
@@ -179,7 +180,7 @@
         // ready.
         mEventHub = new EventHub();
         // Create a WebSettings object for maintaining all settings
-        mSettings = new WebSettings(mContext, mWebView);
+        mSettings = new WebSettingsClassic(mContext, mWebView);
         // The WebIconDatabase needs to be initialized within the UI thread so
         // just request the instance here.
         WebIconDatabase.getInstance();
@@ -234,7 +235,7 @@
         // WebCore thread.
         if (mWebView != null) {
             Message.obtain(mWebView.mPrivateHandler,
-                    WebView.WEBCORE_INITIALIZED_MSG_ID,
+                    WebViewClassic.WEBCORE_INITIALIZED_MSG_ID,
                     mNativeClass, 0).sendToTarget();
         }
 
@@ -284,7 +285,7 @@
         BrowserFrame.sJavaBridge.resume();
     }
 
-    public WebSettings getSettings() {
+    public WebSettingsClassic getSettings() {
         return mSettings;
     }
 
@@ -329,7 +330,7 @@
      */
     private void formDidBlur(int nodePointer) {
         if (mWebView == null) return;
-        Message.obtain(mWebView.mPrivateHandler, WebView.FORM_DID_BLUR,
+        Message.obtain(mWebView.mPrivateHandler, WebViewClassic.FORM_DID_BLUR,
                 nodePointer, 0).sendToTarget();
     }
 
@@ -338,7 +339,7 @@
      */
     private void focusNodeChanged(WebKitHitTest hitTest) {
         if (mWebView == null) return;
-        mWebView.mPrivateHandler.obtainMessage(WebView.HIT_TEST_RESULT, hitTest)
+        mWebView.mPrivateHandler.obtainMessage(WebViewClassic.HIT_TEST_RESULT, hitTest)
                 .sendToTarget();
     }
 
@@ -508,7 +509,7 @@
     protected void enterFullscreenForVideoLayer(int layerId, String url) {
         if (mWebView == null) return;
         Message message = Message.obtain(mWebView.mPrivateHandler,
-                       WebView.ENTER_FULLSCREEN_VIDEO, layerId, 0);
+                       WebViewClassic.ENTER_FULLSCREEN_VIDEO, layerId, 0);
         message.obj = url;
         message.sendToTarget();
     }
@@ -520,7 +521,7 @@
     protected void exitFullscreenVideo() {
         if (mWebView == null) return;
         Message message = Message.obtain(mWebView.mPrivateHandler,
-                       WebView.EXIT_FULLSCREEN_VIDEO);
+                       WebViewClassic.EXIT_FULLSCREEN_VIDEO);
         message.sendToTarget();
     }
 
@@ -609,15 +610,9 @@
     private native void nativeSetFocusControllerActive(int nativeClass,
             boolean active);
 
-    private native void nativeSaveDocumentState(int nativeClass, int frame);
+    private native void nativeSaveDocumentState(int nativeClass);
 
-    private native void nativeMoveFocus(int nativeClass, int framePtr,
-            int nodePointer);
-    private native void nativeMoveMouse(int nativeClass, int framePtr, int x,
-            int y);
-
-    private native void nativeMoveMouseIfLatest(int nativeClass,
-            int moveGeneration, int framePtr, int x, int y);
+    private native void nativeMoveMouse(int nativeClass, int x, int y);
 
     private native String nativeRetrieveHref(int nativeClass, int x, int y);
     private native String nativeRetrieveAnchorText(int nativeClass,
@@ -631,16 +626,12 @@
             int[] idArray, int[] xArray, int[] yArray, int count,
             int actionIndex, int metaState);
 
-    private native void nativeUpdateFrameCache(int nativeClass);
-
     private native void nativeSetBackgroundColor(int nativeClass, int color);
 
     private native void nativeDumpDomTree(int nativeClass, boolean useFile);
 
     private native void nativeDumpRenderTree(int nativeClass, boolean useFile);
 
-    private native void nativeDumpNavTree(int nativeClass);
-
     private native void nativeSetJsFlags(int nativeClass, String flags);
 
     /**
@@ -798,21 +789,6 @@
         String mHistoryUrl;
     }
 
-    static class CursorData {
-        CursorData() {}
-        CursorData(int frame, int node, int x, int y) {
-            mFrame = frame;
-            mNode = node;
-            mX = x;
-            mY = y;
-        }
-        int mMoveGeneration;
-        int mFrame;
-        int mNode;
-        int mX;
-        int mY;
-    }
-
     static class JSInterfaceData {
         Object mObject;
         String mInterfaceName;
@@ -886,7 +862,7 @@
         String mTitle;
         Rect[] mTouchRects;
         boolean mEditable;
-        int mTapHighlightColor = WebView.HIGHLIGHT_COLOR;
+        int mTapHighlightColor = WebViewClassic.HIGHLIGHT_COLOR;
         Rect[] mEnclosingParentRects;
         boolean mHasFocus;
 
@@ -969,8 +945,8 @@
 
         static final String[] HandlerDebugString = {
             "REVEAL_SELECTION", // 96
-            "REQUEST_LABEL", // 97
-            "UPDATE_FRAME_CACHE_IF_LOADING", // = 98
+            "", // 97
+            "", // = 98
             "SCROLL_TEXT_INPUT", // = 99
             "LOAD_URL", // = 100;
             "STOP_LOADING", // = 101;
@@ -989,7 +965,7 @@
             "REPLACE_TEXT", // = 114;
             "PASS_TO_JS", // = 115;
             "SET_GLOBAL_BOUNDS", // = 116;
-            "UPDATE_CACHE_AND_TEXT_ENTRY", // = 117;
+            "", // = 117;
             "CLICK", // = 118;
             "SET_NETWORK_STATE", // = 119;
             "DOC_HAS_IMAGES", // = 120;
@@ -1007,8 +983,8 @@
             "POST_URL", // = 132;
             "SPLIT_PICTURE_SET", // = 133;
             "CLEAR_CONTENT", // = 134;
-            "SET_MOVE_MOUSE", // = 135;
-            "SET_MOVE_MOUSE_IF_LATEST", // = 136;
+            "", // = 135;
+            "", // = 136;
             "REQUEST_CURSOR_HREF", // = 137;
             "ADD_JS_INTERFACE", // = 138;
             "LOAD_DATA", // = 139;
@@ -1039,8 +1015,6 @@
     public class EventHub {
         // Message Ids
         static final int REVEAL_SELECTION = 96;
-        static final int REQUEST_LABEL = 97;
-        static final int UPDATE_FRAME_CACHE_IF_LOADING = 98;
         static final int SCROLL_TEXT_INPUT = 99;
         static final int LOAD_URL = 100;
         static final int STOP_LOADING = 101;
@@ -1059,7 +1033,6 @@
         static final int REPLACE_TEXT = 114;
         static final int PASS_TO_JS = 115;
         static final int SET_GLOBAL_BOUNDS = 116;
-        static final int UPDATE_CACHE_AND_TEXT_ENTRY = 117;
         static final int CLICK = 118;
         static final int SET_NETWORK_STATE = 119;
         static final int DOC_HAS_IMAGES = 120;
@@ -1069,7 +1042,6 @@
         static final int SINGLE_LISTBOX_CHOICE = 124;
         public static final int MESSAGE_RELAY = 125;
         static final int SET_BACKGROUND_COLOR = 126;
-        static final int SET_MOVE_FOCUS = 127;
         static final int SAVE_DOCUMENT_STATE = 128;
         static final int DELETE_SURROUNDING_TEXT = 129;
 
@@ -1081,7 +1053,6 @@
 
         // UI nav messages
         static final int SET_MOVE_MOUSE = 135;
-        static final int SET_MOVE_MOUSE_IF_LATEST = 136;
         static final int REQUEST_CURSOR_HREF = 137;
         static final int ADD_JS_INTERFACE = 138;
         static final int LOAD_DATA = 139;
@@ -1101,7 +1072,6 @@
         static final int ON_PAUSE = 143;
         static final int ON_RESUME = 144;
         static final int FREE_MEMORY = 145;
-        static final int VALID_NODE_BOUNDS = 146;
 
         // Load and save web archives
         static final int SAVE_WEBARCHIVE = 147;
@@ -1121,7 +1091,6 @@
         // debugging
         static final int DUMP_DOMTREE = 170;
         static final int DUMP_RENDERTREE = 171;
-        static final int DUMP_NAVTREE = 172;
 
         static final int SET_JS_FLAGS = 174;
         static final int CONTENT_INVALIDATE_ALL = 175;
@@ -1200,7 +1169,7 @@
         private EventHub() {}
 
         private static final int FIRST_PACKAGE_MSG_ID = REVEAL_SELECTION;
-        private static final int LAST_PACKAGE_MSG_ID = VALID_NODE_BOUNDS;
+        private static final int LAST_PACKAGE_MSG_ID = REMOVE_JS_INTERFACE;
 
         /**
          * Transfer all messages to the newly created webcore thread handler.
@@ -1251,6 +1220,12 @@
                             // Time to take down the world. Cancel all pending
                             // loads and destroy the native view and frame.
                             synchronized (WebViewCore.this) {
+                                mCallbackProxy.shutdown();
+                                // Wake up the WebCore thread just in case it is waiting for a
+                                // JavaScript dialog.
+                                synchronized (mCallbackProxy) {
+                                    mCallbackProxy.notify();
+                                }
                                 mBrowserFrame.destroy();
                                 mBrowserFrame = null;
                                 mSettings.onDestroyed();
@@ -1263,23 +1238,6 @@
                             nativeRevealSelection(mNativeClass);
                             break;
 
-                        case REQUEST_LABEL:
-                            if (mWebView != null) {
-                                int nodePointer = msg.arg2;
-                                String label = nativeRequestLabel(mNativeClass,
-                                        msg.arg1, nodePointer);
-                                if (label != null && label.length() > 0) {
-                                    Message.obtain(mWebView.mPrivateHandler,
-                                            WebView.RETURN_LABEL, nodePointer,
-                                            0, label).sendToTarget();
-                                }
-                            }
-                            break;
-
-                        case UPDATE_FRAME_CACHE_IF_LOADING:
-                            nativeUpdateFrameCacheIfLoading(mNativeClass);
-                            break;
-
                         case SCROLL_TEXT_INPUT:
                             float xPercent;
                             if (msg.obj == null) {
@@ -1373,15 +1331,15 @@
                             break;
 
                         case VIEW_SIZE_CHANGED: {
-                            viewSizeChanged((WebView.ViewSizeData) msg.obj);
+                            viewSizeChanged((WebViewClassic.ViewSizeData) msg.obj);
                             break;
                         }
                         case SET_SCROLL_OFFSET:
                             // note: these are in document coordinates
                             // (inv-zoom)
                             Point pt = (Point) msg.obj;
-                            nativeSetScrollOffset(mNativeClass, msg.arg1,
-                                    msg.arg2 == 1, pt.x, pt.y);
+                            nativeSetScrollOffset(mNativeClass,
+                                    msg.arg1 == 1, pt.x, pt.y);
                             break;
 
                         case SET_GLOBAL_BOUNDS:
@@ -1485,8 +1443,7 @@
                         }
 
                         case SAVE_DOCUMENT_STATE: {
-                            CursorData cDat = (CursorData) msg.obj;
-                            nativeSaveDocumentState(mNativeClass, cDat.mFrame);
+                            nativeSaveDocumentState(mNativeClass);
                             break;
                         }
 
@@ -1529,7 +1486,7 @@
                                     ted.mMetaState);
                             Message.obtain(
                                     mWebView.mPrivateHandler,
-                                    WebView.PREVENT_TOUCH_ID,
+                                    WebViewClassic.PREVENT_TOUCH_ID,
                                     ted.mAction,
                                     ted.mNativeResult ? 1 : 0,
                                     ted).sendToTarget();
@@ -1561,22 +1518,8 @@
                             mBrowserFrame.documentAsText((Message) msg.obj);
                             break;
 
-                        case SET_MOVE_FOCUS:
-                            CursorData focusData = (CursorData) msg.obj;
-                            nativeMoveFocus(mNativeClass, focusData.mFrame, focusData.mNode);
-                            break;
-
                         case SET_MOVE_MOUSE:
-                            CursorData cursorData = (CursorData) msg.obj;
-                            nativeMoveMouse(mNativeClass,
-                                     cursorData.mFrame, cursorData.mX, cursorData.mY);
-                            break;
-
-                        case SET_MOVE_MOUSE_IF_LATEST:
-                            CursorData cData = (CursorData) msg.obj;
-                            nativeMoveMouseIfLatest(mNativeClass,
-                                    cData.mMoveGeneration,
-                                    cData.mFrame, cData.mX, cData.mY);
+                            nativeMoveMouse(mNativeClass, msg.arg1, msg.arg2);
                             break;
 
                         case REQUEST_CURSOR_HREF: {
@@ -1590,15 +1533,6 @@
                             break;
                         }
 
-                        case UPDATE_CACHE_AND_TEXT_ENTRY:
-                            nativeUpdateFrameCache(mNativeClass);
-                            // FIXME: this should provide a minimal rectangle
-                            if (mWebView != null) {
-                                mWebView.postInvalidate();
-                            }
-                            sendUpdateTextEntry();
-                            break;
-
                         case DOC_HAS_IMAGES:
                             Message imageResult = (Message) msg.obj;
                             imageResult.arg1 =
@@ -1621,7 +1555,8 @@
                             String modifiedSelectionString =
                                 nativeModifySelection(mNativeClass, msg.arg1,
                                         msg.arg2);
-                            mWebView.mPrivateHandler.obtainMessage(WebView.SELECTION_STRING_CHANGED,
+                            mWebView.mPrivateHandler.obtainMessage(
+                                    WebViewClassic.SELECTION_STRING_CHANGED,
                                     modifiedSelectionString).sendToTarget();
                             break;
 
@@ -1653,10 +1588,6 @@
                             nativeDumpRenderTree(mNativeClass, msg.arg1 == 1);
                             break;
 
-                        case DUMP_NAVTREE:
-                            nativeDumpNavTree(mNativeClass);
-                            break;
-
                         case SET_JS_FLAGS:
                             nativeSetJsFlags(mNativeClass, (String)msg.obj);
                             break;
@@ -1666,12 +1597,12 @@
                             break;
 
                         case SAVE_WEBARCHIVE:
-                            WebView.SaveWebArchiveMessage saveMessage =
-                                (WebView.SaveWebArchiveMessage)msg.obj;
+                            WebViewClassic.SaveWebArchiveMessage saveMessage =
+                                (WebViewClassic.SaveWebArchiveMessage)msg.obj;
                             saveMessage.mResultFile =
                                 saveWebArchive(saveMessage.mBasename, saveMessage.mAutoname);
                             mWebView.mPrivateHandler.obtainMessage(
-                                WebView.SAVE_WEBARCHIVE_FINISHED, saveMessage).sendToTarget();
+                                WebViewClassic.SAVE_WEBARCHIVE_FINISHED, saveMessage).sendToTarget();
                             break;
 
                         case GEOLOCATION_PERMISSIONS_PROVIDE:
@@ -1684,7 +1615,7 @@
                         case SPLIT_PICTURE_SET:
                             nativeSplitContent(mNativeClass, msg.arg1);
                             mWebView.mPrivateHandler.obtainMessage(
-                                    WebView.REPLACE_BASE_CONTENT, msg.arg1, 0);
+                                    WebViewClassic.REPLACE_BASE_CONTENT, msg.arg1, 0);
                             mSplitPictureIsScheduled = false;
                             break;
 
@@ -1703,21 +1634,6 @@
                             nativeProvideVisitedHistory(mNativeClass, (String[])msg.obj);
                             break;
 
-                        case VALID_NODE_BOUNDS: {
-                            MotionUpData motionUpData = (MotionUpData) msg.obj;
-                            if (!nativeValidNodeAndBounds(
-                                    mNativeClass, motionUpData.mFrame,
-                                    motionUpData.mNode, motionUpData.mBounds)) {
-                                nativeUpdateFrameCache(mNativeClass);
-                            }
-                            Message message = mWebView.mPrivateHandler
-                                    .obtainMessage(WebView.DO_MOTION_UP,
-                                    motionUpData.mX, motionUpData.mY);
-                            mWebView.mPrivateHandler.sendMessageAtFrontOfQueue(
-                                    message);
-                            break;
-                        }
-
                         case HIDE_FULLSCREEN:
                             nativeFullScreenPluginHidden(mNativeClass, msg.arg1);
                             break;
@@ -1747,7 +1663,7 @@
                             }
                             WebKitHitTest hit = performHitTest(d.mX, d.mY, d.mSlop, true);
                             mWebView.mPrivateHandler.obtainMessage(
-                                    WebView.HIT_TEST_RESULT, hit)
+                                    WebViewClassic.HIT_TEST_RESULT, hit)
                                     .sendToTarget();
                             break;
 
@@ -1757,7 +1673,7 @@
 
                         case AUTOFILL_FORM:
                             nativeAutoFillForm(mNativeClass, msg.arg1);
-                            mWebView.mPrivateHandler.obtainMessage(WebView.AUTOFILL_COMPLETE, null)
+                            mWebView.mPrivateHandler.obtainMessage(WebViewClassic.AUTOFILL_COMPLETE, null)
                                     .sendToTarget();
                             break;
 
@@ -1788,7 +1704,7 @@
                                     handles[0], handles[1], handles[2],
                                     handles[3]);
                             if (copiedText != null) {
-                                mWebView.mPrivateHandler.obtainMessage(WebView.COPY_TO_CLIPBOARD, copiedText)
+                                mWebView.mPrivateHandler.obtainMessage(WebViewClassic.COPY_TO_CLIPBOARD, copiedText)
                                         .sendToTarget();
                             }
                             break;
@@ -2058,7 +1974,7 @@
                 }
                 if (mWebView != null && evt.isDown()) {
                     Message.obtain(mWebView.mPrivateHandler,
-                            WebView.UNHANDLED_NAV_KEY, keyCode,
+                            WebViewClassic.UNHANDLED_NAV_KEY, keyCode,
                             0).sendToTarget();
                 }
                 return;
@@ -2081,7 +1997,7 @@
     private float mCurrentViewScale = 1.0f;
 
     // notify webkit that our virtual view size changed size (after inv-zoom)
-    private void viewSizeChanged(WebView.ViewSizeData data) {
+    private void viewSizeChanged(WebViewClassic.ViewSizeData data) {
         int w = data.mWidth;
         int h = data.mHeight;
         int textwrapWidth = data.mTextWrapWidth;
@@ -2115,8 +2031,6 @@
             if (DebugFlags.WEB_VIEW_CORE) Log.v(LOGTAG, "viewSizeChanged");
             contentDraw();
         }
-        mEventHub.sendMessage(Message.obtain(null,
-                EventHub.UPDATE_CACHE_AND_TEXT_ENTRY));
     }
 
     // Calculate width to be used in webkit window.
@@ -2125,7 +2039,7 @@
         if (mSettings.getUseWideViewPort()) {
             if (mViewportWidth == -1) {
                 // Fixed viewport width.
-                width = WebView.DEFAULT_VIEWPORT_WIDTH;
+                width = WebViewClassic.DEFAULT_VIEWPORT_WIDTH;
             } else if (mViewportWidth > 0) {
                 // Use website specified or desired fixed viewport width.
                 width = mViewportWidth;
@@ -2137,13 +2051,6 @@
         return width;
     }
 
-    private void sendUpdateTextEntry() {
-        if (mWebView != null) {
-            Message.obtain(mWebView.mPrivateHandler,
-                    WebView.UPDATE_TEXT_ENTRY_MSG_ID).sendToTarget();
-        }
-    }
-
     // Utility method for exceededDatabaseQuota and reachedMaxAppCacheSize
     // callbacks. Computes the sum of database quota for all origins.
     private long getUsedQuota() {
@@ -2230,9 +2137,9 @@
             // If anything more complex than position has been touched, let's do a full draw
             webkitDraw();
         }
-        mWebView.mPrivateHandler.removeMessages(WebView.INVAL_RECT_MSG_ID);
+        mWebView.mPrivateHandler.removeMessages(WebViewClassic.INVAL_RECT_MSG_ID);
         mWebView.mPrivateHandler.sendMessageAtFrontOfQueue(mWebView.mPrivateHandler
-                .obtainMessage(WebView.INVAL_RECT_MSG_ID));
+                .obtainMessage(WebViewClassic.INVAL_RECT_MSG_ID));
     }
 
     private Boolean m_skipDrawFlag = false;
@@ -2289,7 +2196,7 @@
             draw.mViewSize = new Point(mCurrentViewWidth, mCurrentViewHeight);
             if (mSettings.getUseWideViewPort()) {
                 draw.mMinPrefWidth = Math.max(
-                        mViewportWidth == -1 ? WebView.DEFAULT_VIEWPORT_WIDTH
+                        mViewportWidth == -1 ? WebViewClassic.DEFAULT_VIEWPORT_WIDTH
                                 : (mViewportWidth == 0 ? mCurrentViewWidth
                                         : mViewportWidth),
                         nativeGetContentMinPrefWidth(mNativeClass));
@@ -2304,7 +2211,7 @@
             }
             if (DebugFlags.WEB_VIEW_CORE) Log.v(LOGTAG, "webkitDraw NEW_PICTURE_MSG_ID");
             Message.obtain(mWebView.mPrivateHandler,
-                    WebView.NEW_PICTURE_MSG_ID, draw).sendToTarget();
+                    WebViewClassic.NEW_PICTURE_MSG_ID, draw).sendToTarget();
         }
     }
 
@@ -2433,7 +2340,7 @@
         }
         if (mWebView != null) {
             Message msg = Message.obtain(mWebView.mPrivateHandler,
-                    WebView.SCROLL_TO_MSG_ID, animate ? 1 : 0,
+                    WebViewClassic.SCROLL_TO_MSG_ID, animate ? 1 : 0,
                     onlyIfImeIsShowing ? 1 : 0, new Point(x, y));
             if (mDrawIsScheduled) {
                 mEventHub.sendMessage(Message.obtain(null,
@@ -2446,7 +2353,6 @@
 
     // called by JNI
     private void sendNotifyProgressFinished() {
-        sendUpdateTextEntry();
         contentDraw();
     }
 
@@ -2457,7 +2363,7 @@
     private void sendViewInvalidate(int left, int top, int right, int bottom) {
         if (mWebView != null) {
             Message.obtain(mWebView.mPrivateHandler,
-                           WebView.INVAL_RECT_MSG_ID,
+                           WebViewClassic.INVAL_RECT_MSG_ID,
                            new Rect(left, top, right, bottom)).sendToTarget();
         }
     }
@@ -2473,7 +2379,7 @@
 
     // Gets the WebView corresponding to this WebViewCore. Note that the
     // WebView object must only be used on the UI thread.
-    /* package */ WebView getWebView() {
+    /* package */ WebViewClassic getWebView() {
         return mWebView;
     }
 
@@ -2499,10 +2405,8 @@
         }
 
         // remove the touch highlight when moving to a new page
-        if (WebView.sDisableNavcache) {
-            mWebView.mPrivateHandler.sendEmptyMessage(
-                    WebView.HIT_TEST_RESULT);
-        }
+        mWebView.mPrivateHandler.sendEmptyMessage(
+                WebViewClassic.HIT_TEST_RESULT);
 
         // reset the scroll position, the restored offset and scales
         mRestoredX = mRestoredY = 0;
@@ -2567,7 +2471,7 @@
         }
         if (adjust != mWebView.getDefaultZoomScale()) {
             Message.obtain(mWebView.mPrivateHandler,
-                    WebView.UPDATE_ZOOM_DENSITY, adjust).sendToTarget();
+                    WebViewClassic.UPDATE_ZOOM_DENSITY, adjust).sendToTarget();
         }
         int defaultScale = (int) (adjust * 100);
 
@@ -2618,7 +2522,7 @@
             viewState.mScrollX = 0;
             viewState.mShouldStartScrolledRight = false;
             Message.obtain(mWebView.mPrivateHandler,
-                    WebView.UPDATE_ZOOM_RANGE, viewState).sendToTarget();
+                    WebViewClassic.UPDATE_ZOOM_RANGE, viewState).sendToTarget();
             return;
         }
 
@@ -2689,7 +2593,7 @@
             mWebView.mLastHeightSent = 0;
             // Send a negative scale to indicate that WebCore should reuse
             // the current scale
-            WebView.ViewSizeData data = new WebView.ViewSizeData();
+            WebViewClassic.ViewSizeData data = new WebViewClassic.ViewSizeData();
             data.mWidth = mWebView.mLastWidthSent;
             data.mHeight = 0;
             // if mHeightCanMeasure is true, getUseWideViewPort() can't be
@@ -2713,7 +2617,7 @@
                 // to WebViewCore
                 mWebView.mLastWidthSent = 0;
             } else {
-                WebView.ViewSizeData data = new WebView.ViewSizeData();
+                WebViewClassic.ViewSizeData data = new WebViewClassic.ViewSizeData();
                 // mViewScale as 0 means it is in zoom overview mode. So we don't
                 // know the exact scale. If mRestoredScale is non-zero, use it;
                 // otherwise just use mTextWrapScale as the initial scale.
@@ -2791,7 +2695,7 @@
     private void needTouchEvents(boolean need) {
         if (mWebView != null) {
             Message.obtain(mWebView.mPrivateHandler,
-                    WebView.WEBCORE_NEED_TOUCH_EVENTS, need ? 1 : 0, 0)
+                    WebViewClassic.WEBCORE_NEED_TOUCH_EVENTS, need ? 1 : 0, 0)
                     .sendToTarget();
         }
     }
@@ -2801,7 +2705,7 @@
             String text, int textGeneration) {
         if (mWebView != null) {
             Message msg = Message.obtain(mWebView.mPrivateHandler,
-                    WebView.UPDATE_TEXTFIELD_TEXT_MSG_ID, ptr,
+                    WebViewClassic.UPDATE_TEXTFIELD_TEXT_MSG_ID, ptr,
                     textGeneration, text);
             msg.getData().putBoolean("password", changeToPassword);
             msg.sendToTarget();
@@ -2813,7 +2717,7 @@
             int textGeneration, int selectionPtr) {
         if (mWebView != null) {
             Message.obtain(mWebView.mPrivateHandler,
-                WebView.UPDATE_TEXT_SELECTION_MSG_ID, pointer, textGeneration,
+                WebViewClassic.UPDATE_TEXT_SELECTION_MSG_ID, pointer, textGeneration,
                 new TextSelectionData(start, end, selectionPtr)).sendToTarget();
         }
     }
@@ -2822,7 +2726,7 @@
     private void clearTextEntry() {
         if (mWebView == null) return;
         Message.obtain(mWebView.mPrivateHandler,
-                WebView.CLEAR_TEXT_ENTRY).sendToTarget();
+                WebViewClassic.CLEAR_TEXT_ENTRY).sendToTarget();
     }
 
     // called by JNI
@@ -2836,9 +2740,9 @@
                 text, inputType, isSpellCheckEnabled, nextFieldIsText, label,
                 maxLength);
         Message.obtain(mWebView.mPrivateHandler,
-                WebView.INIT_EDIT_FIELD, initData).sendToTarget();
+                WebViewClassic.INIT_EDIT_FIELD, initData).sendToTarget();
         Message.obtain(mWebView.mPrivateHandler,
-                WebView.REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID, pointer,
+                WebViewClassic.REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID, pointer,
                 0, new TextSelectionData(start, end, selectionPtr))
                 .sendToTarget();
     }
@@ -2850,11 +2754,10 @@
             return;
         }
         Message.obtain(mWebView.mPrivateHandler,
-                WebView.UPDATE_MATCH_COUNT, matchIndex, matchCount,
+                WebViewClassic.UPDATE_MATCH_COUNT, matchIndex, matchCount,
                 findText).sendToTarget();
     }
 
-    private native void nativeUpdateFrameCacheIfLoading(int nativeClass);
     private native void nativeRevealSelection(int nativeClass);
     private native String nativeRequestLabel(int nativeClass, int framePtr,
             int nodePtr);
@@ -2865,7 +2768,7 @@
             float xPercent, int y);
 
     // these must be in document space (i.e. not scaled/zoomed).
-    private native void nativeSetScrollOffset(int nativeClass, int gen,
+    private native void nativeSetScrollOffset(int nativeClass,
             boolean sendScrollEvent, int dx, int dy);
 
     private native void nativeSetGlobalBounds(int nativeClass, int x, int y,
@@ -2892,14 +2795,14 @@
     private void requestKeyboard(boolean showKeyboard) {
         if (mWebView != null) {
             Message.obtain(mWebView.mPrivateHandler,
-                    WebView.REQUEST_KEYBOARD, showKeyboard ? 1 : 0, 0)
+                    WebViewClassic.REQUEST_KEYBOARD, showKeyboard ? 1 : 0, 0)
                     .sendToTarget();
         }
     }
 
     private void setWebTextViewAutoFillable(int queryId, String preview) {
         if (mWebView != null) {
-            Message.obtain(mWebView.mPrivateHandler, WebView.SET_AUTOFILLABLE,
+            Message.obtain(mWebView.mPrivateHandler, WebViewClassic.SET_AUTOFILLABLE,
                     new AutoFillData(queryId, preview))
                     .sendToTarget();
         }
@@ -2912,7 +2815,7 @@
     // called by JNI
     private void keepScreenOn(boolean screenOn) {
         if (mWebView != null) {
-            Message message = mWebView.mPrivateHandler.obtainMessage(WebView.SCREEN_ON);
+            Message message = mWebView.mPrivateHandler.obtainMessage(WebViewClassic.SCREEN_ON);
             message.arg1 = screenOn ? 1 : 0;
             message.sendToTarget();
         }
@@ -2952,7 +2855,7 @@
             return;
         }
 
-        Message message = mWebView.mPrivateHandler.obtainMessage(WebView.SHOW_FULLSCREEN);
+        Message message = mWebView.mPrivateHandler.obtainMessage(WebViewClassic.SHOW_FULLSCREEN);
         message.obj = childView.mView;
         message.arg1 = orientation;
         message.arg2 = npp;
@@ -2964,7 +2867,7 @@
         if (mWebView == null) {
             return;
         }
-        mWebView.mPrivateHandler.obtainMessage(WebView.HIDE_FULLSCREEN)
+        mWebView.mPrivateHandler.obtainMessage(WebViewClassic.HIDE_FULLSCREEN)
                 .sendToTarget();
     }
 
@@ -3036,7 +2939,7 @@
             data.mXPercentInView = xPercentInView;
             data.mYPercentInDoc = yPercentInDoc;
             data.mYPercentInView = yPercentInView;
-            Message.obtain(mWebView.mPrivateHandler, WebView.SHOW_RECT_MSG_ID,
+            Message.obtain(mWebView.mPrivateHandler, WebViewClassic.SHOW_RECT_MSG_ID,
                     data).sendToTarget();
         }
     }
@@ -3046,7 +2949,7 @@
         if (mWebView == null) {
             return;
         }
-        mWebView.mPrivateHandler.obtainMessage(WebView.CENTER_FIT_RECT,
+        mWebView.mPrivateHandler.obtainMessage(WebViewClassic.CENTER_FIT_RECT,
                 new Rect(x, y, x + width, y + height)).sendToTarget();
     }
 
@@ -3055,16 +2958,13 @@
         if (mWebView == null) {
             return;
         }
-        mWebView.mPrivateHandler.obtainMessage(WebView.SET_SCROLLBAR_MODES,
+        mWebView.mPrivateHandler.obtainMessage(WebViewClassic.SET_SCROLLBAR_MODES,
                 hMode, vMode).sendToTarget();
     }
 
     // called by JNI
-    @SuppressWarnings("unused")
     private void selectAt(int x, int y) {
-        if (mWebView != null) {
-            mWebView.mPrivateHandler.obtainMessage(WebView.SELECT_AT, x, y).sendToTarget();
-        }
+        // TODO: Figure out what to do with this (b/6111818)
     }
 
     private void useMockDeviceOrientation() {
@@ -3099,8 +2999,6 @@
     private native void nativeFreeMemory(int nativeClass);
     private native void nativeFullScreenPluginHidden(int nativeClass, int npp);
     private native void nativePluginSurfaceReady(int nativeClass);
-    private native boolean nativeValidNodeAndBounds(int nativeClass, int frame,
-            int node, Rect bounds);
 
     private native WebKitHitTest nativeHitTest(int nativeClass, int x, int y,
             int slop, boolean moveMouse);
diff --git a/core/java/android/webkit/WebViewFactoryProvider.java b/core/java/android/webkit/WebViewFactoryProvider.java
new file mode 100644
index 0000000..22bf0bf
--- /dev/null
+++ b/core/java/android/webkit/WebViewFactoryProvider.java
@@ -0,0 +1,56 @@
+/*
+ * Copyright (C) 2012 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 android.webkit;
+
+/**
+ * This is the main entry-point into the WebView back end implementations, which the WebView
+ * proxy class uses to instantiate all the other objects as needed. The backend must provide an
+ * implementation of this interface, and make it available to the WebView via mechanism TBD.
+ * @hide
+ */
+public interface WebViewFactoryProvider {
+
+    /**
+     * Construct a new WebView provider.
+     * @param webView the WebView instance bound to this implementation instance. Note it will not
+     * necessarily be fully constructed at the point of this call: defer real initialization to
+     * WebViewProvider.init().
+     * @param privateAccess provides access into WebView internal methods.
+     */
+    WebViewProvider createWebView(WebView webView, WebView.PrivateAccess privateAccess);
+
+    Statics getStatics();
+
+    /**
+     * This Interface provides glue for implementing the backend of WebView static methods which
+     * cannot be implemented in-situ in the proxy class.
+     */
+    interface Statics {
+        /**
+         * Implements the API method:
+         * {@link android.webkit.WebView#findAddress(String)}
+         */
+        String findAddress(String addr);
+
+        /**
+         * Implements the API methods:
+         * {@link android.webkit.WebView#enablePlatformNotifications()}
+         * {@link android.webkit.WebView#disablePlatformNotifications()}
+         */
+        void setPlatformNotificationsEnabled(boolean enable);
+    }
+}
diff --git a/core/java/android/webkit/WebViewProvider.java b/core/java/android/webkit/WebViewProvider.java
new file mode 100644
index 0000000..2e8ad6d
--- /dev/null
+++ b/core/java/android/webkit/WebViewProvider.java
@@ -0,0 +1,372 @@
+/*
+ * Copyright (C) 2012 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 android.webkit;
+
+import android.content.res.Configuration;
+import android.graphics.Bitmap;
+import android.graphics.Canvas;
+import android.graphics.Picture;
+import android.graphics.Rect;
+import android.graphics.drawable.Drawable;
+import android.net.http.SslCertificate;
+import android.os.Bundle;
+import android.os.Message;
+import android.view.KeyEvent;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.ViewGroup.LayoutParams;
+import android.view.accessibility.AccessibilityEvent;
+import android.view.accessibility.AccessibilityNodeInfo;
+import android.view.inputmethod.EditorInfo;
+import android.view.inputmethod.InputConnection;
+import android.webkit.WebView.HitTestResult;
+import android.webkit.WebView.PictureListener;
+
+import java.io.File;
+import java.util.Map;
+
+/**
+ * WebView backend provider interface: this interface is the abstract backend to a WebView
+ * instance; each WebView object is bound to exactly one WebViewProvider object which implements
+ * the runtime behavior of that WebView.
+ *
+ * All methods must behave as per their namesake in {@link WebView}, unless otherwise noted.
+ *
+ * @hide Not part of the public API; only required by system implementors.
+ */
+public interface WebViewProvider {
+    //-------------------------------------------------------------------------
+    // Main interface for backend provider of the WebView class.
+    //-------------------------------------------------------------------------
+    /**
+     * Initialize this WebViewProvider instance. Called after the WebView has fully constructed.
+     * @param javaScriptInterfaces is a Map of interface names, as keys, and
+     * object implementing those interfaces, as values.
+     * @param privateBrowsing If true the web view will be initialized in private / incognito mode.
+     */
+    public void init(Map<String, Object> javaScriptInterfaces,
+            boolean privateBrowsing);
+
+    public void setHorizontalScrollbarOverlay(boolean overlay);
+
+    public void setVerticalScrollbarOverlay(boolean overlay);
+
+    public boolean overlayHorizontalScrollbar();
+
+    public boolean overlayVerticalScrollbar();
+
+    public int getVisibleTitleHeight();
+
+    public SslCertificate getCertificate();
+
+    public void setCertificate(SslCertificate certificate);
+
+    public void savePassword(String host, String username, String password);
+
+    public void setHttpAuthUsernamePassword(String host, String realm,
+            String username, String password);
+
+    public String[] getHttpAuthUsernamePassword(String host, String realm);
+
+    /**
+     * See {@link WebView#destroy()}.
+     * As well as releasing the internal state and resources held by the implementation,
+     * the provider should null all references it holds on the WebView proxy class, and ensure
+     * no further method calls are made to it.
+     */
+    public void destroy();
+
+    public void setNetworkAvailable(boolean networkUp);
+
+    public WebBackForwardList saveState(Bundle outState);
+
+    public boolean savePicture(Bundle b, final File dest);
+
+    public boolean restorePicture(Bundle b, File src);
+
+    public WebBackForwardList restoreState(Bundle inState);
+
+    public void loadUrl(String url, Map<String, String> additionalHttpHeaders);
+
+    public void loadUrl(String url);
+
+    public void postUrl(String url, byte[] postData);
+
+    public void loadData(String data, String mimeType, String encoding);
+
+    public void loadDataWithBaseURL(String baseUrl, String data,
+            String mimeType, String encoding, String historyUrl);
+
+    public void saveWebArchive(String filename);
+
+    public void saveWebArchive(String basename, boolean autoname, ValueCallback<String> callback);
+
+    public void stopLoading();
+
+    public void reload();
+
+    public boolean canGoBack();
+
+    public void goBack();
+
+    public boolean canGoForward();
+
+    public void goForward();
+
+    public boolean canGoBackOrForward(int steps);
+
+    public void goBackOrForward(int steps);
+
+    public boolean isPrivateBrowsingEnabled();
+
+    public boolean pageUp(boolean top);
+
+    public boolean pageDown(boolean bottom);
+
+    public void clearView();
+
+    public Picture capturePicture();
+
+    public float getScale();
+
+    public void setInitialScale(int scaleInPercent);
+
+    public void invokeZoomPicker();
+
+    public HitTestResult getHitTestResult();
+
+    public void requestFocusNodeHref(Message hrefMsg);
+
+    public void requestImageRef(Message msg);
+
+    public String getUrl();
+
+    public String getOriginalUrl();
+
+    public String getTitle();
+
+    public Bitmap getFavicon();
+
+    public String getTouchIconUrl();
+
+    public int getProgress();
+
+    public int getContentHeight();
+
+    public int getContentWidth();
+
+    public void pauseTimers();
+
+    public void resumeTimers();
+
+    public void onPause();
+
+    public void onResume();
+
+    public boolean isPaused();
+
+    public void freeMemory();
+
+    public void clearCache(boolean includeDiskFiles);
+
+    public void clearFormData();
+
+    public void clearHistory();
+
+    public void clearSslPreferences();
+
+    public WebBackForwardList copyBackForwardList();
+
+    public void findNext(boolean forward);
+
+    public int findAll(String find);
+
+    public boolean showFindDialog(String text, boolean showIme);
+
+    public void clearMatches();
+
+    public void documentHasImages(Message response);
+
+    public void setWebViewClient(WebViewClient client);
+
+    public void setDownloadListener(DownloadListener listener);
+
+    public void setWebChromeClient(WebChromeClient client);
+
+    public void setPictureListener(PictureListener listener);
+
+    public void addJavascriptInterface(Object obj, String interfaceName);
+
+    public void removeJavascriptInterface(String interfaceName);
+
+    public WebSettings getSettings();
+
+    public void emulateShiftHeld();
+
+    public void setMapTrackballToArrowKeys(boolean setMap);
+
+    public void flingScroll(int vx, int vy);
+
+    public View getZoomControls();
+
+    public boolean canZoomIn();
+
+    public boolean canZoomOut();
+
+    public boolean zoomIn();
+
+    public boolean zoomOut();
+
+    public void debugDump();
+
+    //-------------------------------------------------------------------------
+    // Provider glue methods
+    //-------------------------------------------------------------------------
+
+    /**
+     * @return the ViewDelegate implementation. This provides the functionality to back all of
+     * the name-sake functions from the View and ViewGroup base classes of WebView.
+     */
+    /* package */ ViewDelegate getViewDelegate();
+
+    /**
+     * @return a ScrollDelegate implementation. Normally this would be same object as is
+     * returned by getViewDelegate().
+     */
+    /* package */ ScrollDelegate getScrollDelegate();
+
+    //-------------------------------------------------------------------------
+    // View / ViewGroup delegation methods
+    //-------------------------------------------------------------------------
+
+    /**
+     * Provides mechanism for the name-sake methods declared in View and ViewGroup to be delegated
+     * into the WebViewProvider instance.
+     * NOTE For many of these methods, the WebView will provide a super.Foo() call before or after
+     * making the call into the provider instance. This is done for convenience in the common case
+     * of maintaining backward compatibility. For remaining super class calls (e.g. where the
+     * provider may need to only conditionally make the call based on some internal state) see the
+     * {@link WebView.PrivateAccess} callback class.
+     */
+    // TODO: See if the pattern of the super-class calls can be rationalized at all, and document
+    // the remainder on the methods below.
+    interface ViewDelegate {
+        public boolean shouldDelayChildPressedState();
+
+        public void onInitializeAccessibilityNodeInfo(AccessibilityNodeInfo info);
+
+        public void onInitializeAccessibilityEvent(AccessibilityEvent event);
+
+        public void setOverScrollMode(int mode);
+
+        public void setScrollBarStyle(int style);
+
+        public void onDrawVerticalScrollBar(Canvas canvas, Drawable scrollBar, int l, int t,
+                int r, int b);
+
+        public void onOverScrolled(int scrollX, int scrollY, boolean clampedX, boolean clampedY);
+
+        public void onWindowVisibilityChanged(int visibility);
+
+        public boolean drawChild(Canvas canvas, View child, long drawingTime);
+
+        public void onDraw(Canvas canvas);
+
+        public void setLayoutParams(LayoutParams layoutParams);
+
+        public boolean performLongClick();
+
+        public void onConfigurationChanged(Configuration newConfig);
+
+        public InputConnection onCreateInputConnection(EditorInfo outAttrs);
+
+        public boolean onKeyMultiple(int keyCode, int repeatCount, KeyEvent event);
+
+        public boolean onKeyDown(int keyCode, KeyEvent event);
+
+        public boolean onKeyUp(int keyCode, KeyEvent event);
+
+        public void onAttachedToWindow();
+
+        public void onDetachedFromWindow();
+
+        public void onVisibilityChanged(View changedView, int visibility);
+
+        public void onWindowFocusChanged(boolean hasWindowFocus);
+
+        public void onFocusChanged(boolean focused, int direction, Rect previouslyFocusedRect);
+
+        public boolean setFrame(int left, int top, int right, int bottom);
+
+        public void onSizeChanged(int w, int h, int ow, int oh);
+
+        public void onScrollChanged(int l, int t, int oldl, int oldt);
+
+        public boolean dispatchKeyEvent(KeyEvent event);
+
+        public boolean onTouchEvent(MotionEvent ev);
+
+        public boolean onHoverEvent(MotionEvent event);
+
+        public boolean onGenericMotionEvent(MotionEvent event);
+
+        public boolean onTrackballEvent(MotionEvent ev);
+
+        public boolean requestFocus(int direction, Rect previouslyFocusedRect);
+
+        public void onMeasure(int widthMeasureSpec, int heightMeasureSpec);
+
+        public boolean requestChildRectangleOnScreen(View child, Rect rect, boolean immediate);
+
+        public void setBackgroundColor(int color);
+    }
+
+    interface ScrollDelegate {
+        // These methods are declared protected in the ViewGroup base class. This interface
+        // exists to promote them to public so they may be called by the WebView proxy class.
+        // TODO: Combine into ViewDelegate?
+        /**
+         * See {@link android.webkit.WebView#computeHorizontalScrollRange}
+         */
+        public int computeHorizontalScrollRange();
+
+        /**
+         * See {@link android.webkit.WebView#computeHorizontalScrollOffset}
+         */
+        public int computeHorizontalScrollOffset();
+
+        /**
+         * See {@link android.webkit.WebView#computeVerticalScrollRange}
+         */
+        public int computeVerticalScrollRange();
+
+        /**
+         * See {@link android.webkit.WebView#computeVerticalScrollOffset}
+         */
+        public int computeVerticalScrollOffset();
+
+        /**
+         * See {@link android.webkit.WebView#computeVerticalScrollExtent}
+         */
+        public int computeVerticalScrollExtent();
+
+        /**
+         * See {@link android.webkit.WebView#computeScroll}
+         */
+        public void computeScroll();
+    }
+}
diff --git a/core/java/android/webkit/ZoomControlEmbedded.java b/core/java/android/webkit/ZoomControlEmbedded.java
index e505614..d2a0561 100644
--- a/core/java/android/webkit/ZoomControlEmbedded.java
+++ b/core/java/android/webkit/ZoomControlEmbedded.java
@@ -25,12 +25,12 @@
 class ZoomControlEmbedded implements ZoomControlBase {
 
     private final ZoomManager mZoomManager;
-    private final WebView mWebView;
+    private final WebViewClassic mWebView;
 
     // The controller is lazily initialized in getControls() for performance.
     private ZoomButtonsController mZoomButtonsController;
 
-    public ZoomControlEmbedded(ZoomManager zoomManager, WebView webView) {
+    public ZoomControlEmbedded(ZoomManager zoomManager, WebViewClassic webView) {
         mZoomManager = zoomManager;
         mWebView = webView;
     }
@@ -41,7 +41,7 @@
             mZoomButtonsController.setVisible(true);
 
             if (mZoomManager.isDoubleTapEnabled()) {
-                WebSettings settings = mWebView.getSettings();
+                WebSettingsClassic settings = mWebView.getSettings();
                 int count = settings.getDoubleTapToastCount();
                 if (mZoomManager.isInZoomOverview() && count > 0) {
                     settings.setDoubleTapToastCount(--count);
@@ -82,7 +82,7 @@
 
     private ZoomButtonsController getControls() {
         if (mZoomButtonsController == null) {
-            mZoomButtonsController = new ZoomButtonsController(mWebView);
+            mZoomButtonsController = new ZoomButtonsController(mWebView.getWebView());
             mZoomButtonsController.setOnZoomListener(new ZoomListener());
             // ZoomButtonsController positions the buttons at the bottom, but in
             // the middle. Change their layout parameters so they appear on the
diff --git a/core/java/android/webkit/ZoomControlExternal.java b/core/java/android/webkit/ZoomControlExternal.java
index d75313e..f5bfc05 100644
--- a/core/java/android/webkit/ZoomControlExternal.java
+++ b/core/java/android/webkit/ZoomControlExternal.java
@@ -35,9 +35,9 @@
     private Runnable mZoomControlRunnable;
     private final Handler mPrivateHandler = new Handler();
 
-    private final WebView mWebView;
+    private final WebViewClassic mWebView;
 
-    public ZoomControlExternal(WebView webView) {
+    public ZoomControlExternal(WebViewClassic webView) {
         mWebView = webView;
     }
 
diff --git a/core/java/android/webkit/ZoomManager.java b/core/java/android/webkit/ZoomManager.java
index 369e883..2247678 100644
--- a/core/java/android/webkit/ZoomManager.java
+++ b/core/java/android/webkit/ZoomManager.java
@@ -50,7 +50,7 @@
 
     static final String LOGTAG = "webviewZoom";
 
-    private final WebView mWebView;
+    private final WebViewClassic mWebView;
     private final CallbackProxy mCallbackProxy;
 
     // Widgets responsible for the on-screen zoom functions of the WebView.
@@ -211,7 +211,7 @@
     private boolean mHardwareAccelerated = false;
     private boolean mInHWAcceleratedZoom = false;
 
-    public ZoomManager(WebView webView, CallbackProxy callbackProxy) {
+    public ZoomManager(WebViewClassic webView, CallbackProxy callbackProxy) {
         mWebView = webView;
         mCallbackProxy = callbackProxy;
 
@@ -220,7 +220,7 @@
          * ESPN and Engadget always have wider mContentWidth no matter what the
          * viewport size is.
          */
-        setZoomOverviewWidth(WebView.DEFAULT_VIEWPORT_WIDTH);
+        setZoomOverviewWidth(WebViewClassic.DEFAULT_VIEWPORT_WIDTH);
 
         mFocusMovementQueue = new FocusMovementQueue();
     }
@@ -487,13 +487,13 @@
         // zoomScale, we can't use the WebView's pinLocX/Y functions directly.
         float scale = zoomScale * mInvInitialZoomScale;
         int tx = Math.round(scale * (mInitialScrollX + mZoomCenterX) - mZoomCenterX);
-        tx = -WebView.pinLoc(tx, mWebView.getViewWidth(), Math.round(mWebView.getContentWidth()
+        tx = -WebViewClassic.pinLoc(tx, mWebView.getViewWidth(), Math.round(mWebView.getContentWidth()
                 * zoomScale)) + mWebView.getScrollX();
         int titleHeight = mWebView.getTitleHeight();
         int ty = Math.round(scale
                 * (mInitialScrollY + mZoomCenterY - titleHeight)
                 - (mZoomCenterY - titleHeight));
-        ty = -(ty <= titleHeight ? Math.max(ty, 0) : WebView.pinLoc(ty
+        ty = -(ty <= titleHeight ? Math.max(ty, 0) : WebViewClassic.pinLoc(ty
                 - titleHeight, mWebView.getViewHeight(), Math.round(mWebView.getContentHeight()
                 * zoomScale)) + titleHeight) + mWebView.getScrollY();
 
@@ -630,7 +630,7 @@
     public void handleDoubleTap(float lastTouchX, float lastTouchY) {
         // User takes action, set initial zoom overview to false.
         mInitialZoomOverview = false;
-        WebSettings settings = mWebView.getSettings();
+        WebSettingsClassic settings = mWebView.getSettings();
         if (!isDoubleTapEnabled()) {
             return;
         }
@@ -643,20 +643,6 @@
         // remove the zoom control after double tap
         dismissZoomPicker();
 
-        /*
-         * If the double tap was on a plugin then either zoom to maximize the
-         * plugin on the screen or scale to overview mode.
-         */
-        Rect pluginBounds = mWebView.getPluginBounds(mAnchorX, mAnchorY);
-        if (pluginBounds != null) {
-            if (mWebView.isRectFitOnScreen(pluginBounds)) {
-                zoomToOverview();
-            } else {
-                mWebView.centerFitRect(pluginBounds);
-            }
-            return;
-        }
-
         final float newTextWrapScale;
         if (settings.getUseFixedViewport()) {
             newTextWrapScale = Math.max(mActualScale, getReadingLevelScale());
@@ -690,7 +676,7 @@
 
     private void setZoomOverviewWidth(int width) {
         if (width == 0) {
-            mZoomOverviewWidth = WebView.DEFAULT_VIEWPORT_WIDTH;
+            mZoomOverviewWidth = WebViewClassic.DEFAULT_VIEWPORT_WIDTH;
         } else {
             mZoomOverviewWidth = width;
         }
@@ -719,7 +705,7 @@
         final float readingScale = getReadingLevelScale();
 
         int left = mWebView.getBlockLeftEdge(mAnchorX, mAnchorY, readingScale);
-        if (left != WebView.NO_LEFTEDGE) {
+        if (left != WebViewClassic.NO_LEFTEDGE) {
             // add a 5pt padding to the left edge.
             int viewLeft = mWebView.contentToViewX(left < 5 ? 0 : (left - 5))
                     - mWebView.getScrollX();
@@ -728,7 +714,7 @@
             if (viewLeft > 0) {
                 mZoomCenterX = viewLeft * readingScale / (readingScale - mActualScale);
             } else {
-                mWebView.scrollBy(viewLeft, 0);
+                mWebView.getWebView().scrollBy(viewLeft, 0);
                 mZoomCenterX = 0;
             }
         }
@@ -955,7 +941,7 @@
         // cause its child View to reposition itself through ViewManager's
         // scaleAll(), we need to post a Runnable to ensure requestLayout().
         // Additionally, only update the text wrap scale if the width changed.
-        mWebView.post(new PostScale(w != ow &&
+        mWebView.getWebView().post(new PostScale(w != ow &&
             !mWebView.getSettings().getUseFixedViewport(), mInZoomOverview, w < ow));
     }
 
@@ -1027,7 +1013,7 @@
         final int viewWidth = mWebView.getViewWidth();
         final boolean zoomOverviewWidthChanged = setupZoomOverviewWidth(drawData, viewWidth);
         final float newZoomOverviewScale = getZoomOverviewScale();
-        WebSettings settings = mWebView.getSettings();
+        WebSettingsClassic settings = mWebView.getSettings();
         if (zoomOverviewWidthChanged && settings.isNarrowColumnLayout() &&
             settings.getUseFixedViewport() &&
             (mInitialZoomOverview || mInZoomOverview)) {
@@ -1085,7 +1071,7 @@
             if (drawData.mContentSize.x > 0) {
                 // The webkitDraw for layers will not populate contentSize, and it'll be
                 // ignored for zoom overview width update.
-                newZoomOverviewWidth = Math.min(WebView.sMaxViewportWidth,
+                newZoomOverviewWidth = Math.min(WebViewClassic.sMaxViewportWidth,
                     drawData.mContentSize.x);
             }
         } else {
@@ -1117,7 +1103,7 @@
         updateZoomRange(viewState, viewSize.x, drawData.mMinPrefWidth);
         setupZoomOverviewWidth(drawData, mWebView.getViewWidth());
         final float overviewScale = getZoomOverviewScale();
-        WebSettings settings = mWebView.getSettings();
+        WebSettingsClassic settings = mWebView.getSettings();
         if (!mMinZoomScaleFixed || settings.getUseWideViewPort()) {
             mMinZoomScale = (mInitialScale > 0) ?
                     Math.min(mInitialScale, overviewScale) : overviewScale;
diff --git a/core/java/android/widget/CalendarView.java b/core/java/android/widget/CalendarView.java
index 85252af..2a74f6a 100644
--- a/core/java/android/widget/CalendarView.java
+++ b/core/java/android/widget/CalendarView.java
@@ -154,21 +154,25 @@
 
     private final int mWeekSeperatorLineWidth;
 
-    private final int mDateTextSize;
+    private int mDateTextSize;
 
-    private final Drawable mSelectedDateVerticalBar;
+    private Drawable mSelectedDateVerticalBar;
 
     private final int mSelectedDateVerticalBarWidth;
 
-    private final int mSelectedWeekBackgroundColor;
+    private int mSelectedWeekBackgroundColor;
 
-    private final int mFocusedMonthDateColor;
+    private int mFocusedMonthDateColor;
 
-    private final int mUnfocusedMonthDateColor;
+    private int mUnfocusedMonthDateColor;
 
-    private final int mWeekSeparatorLineColor;
+    private int mWeekSeparatorLineColor;
 
-    private final int mWeekNumberColor;
+    private int mWeekNumberColor;
+
+    private int mWeekDayTextAppearanceResId;
+
+    private int mDateTextAppearanceResId;
 
     /**
      * The top offset of the weeks list.
@@ -366,15 +370,11 @@
         mSelectedDateVerticalBar = attributesArray.getDrawable(
                 R.styleable.CalendarView_selectedDateVerticalBar);
 
-        int dateTextAppearanceResId= attributesArray.getResourceId(
+        mDateTextAppearanceResId = attributesArray.getResourceId(
                 R.styleable.CalendarView_dateTextAppearance, R.style.TextAppearance_Small);
-        TypedArray dateTextAppearance = context.obtainStyledAttributes(dateTextAppearanceResId,
-                com.android.internal.R.styleable.TextAppearance);
-        mDateTextSize = dateTextAppearance.getDimensionPixelSize(
-                R.styleable.TextAppearance_textSize, DEFAULT_DATE_TEXT_SIZE);
-        dateTextAppearance.recycle();
+        updateDateTextSize();
 
-        int weekDayTextAppearanceResId = attributesArray.getResourceId(
+        mWeekDayTextAppearanceResId = attributesArray.getResourceId(
                 R.styleable.CalendarView_weekDayTextAppearance,
                 DEFAULT_WEEK_DAY_TEXT_APPEARANCE_RES_ID);
         attributesArray.recycle();
@@ -400,7 +400,7 @@
         mDayNamesHeader = (ViewGroup) content.findViewById(com.android.internal.R.id.day_names);
         mMonthName = (TextView) content.findViewById(com.android.internal.R.id.month_name);
 
-        setUpHeader(weekDayTextAppearanceResId);
+        setUpHeader();
         setUpListView();
         setUpAdapter();
 
@@ -417,6 +417,235 @@
         invalidate();
     }
 
+    /**
+     * Sets the number of weeks to be shown.
+     *
+     * @param count The shown week count.
+     */
+    public void setShownWeekCount(int count) {
+        if (mShownWeekCount != count) {
+            mShownWeekCount = count;
+            invalidate();
+        }
+    }
+
+    /**
+     * Gets the number of weeks to be shown.
+     *
+     * @return The shown week count.
+     */
+    public int getShownWeekCount() {
+        return mShownWeekCount;
+    }
+
+    /**
+     * Sets the background color for the selected week.
+     *
+     * @param color The week background color.
+     */
+    public void setSelectedWeekBackgroundColor(int color) {
+        if (mSelectedWeekBackgroundColor != color) {
+            mSelectedWeekBackgroundColor = color;
+            final int childCount = mListView.getChildCount();
+            for (int i = 0; i < childCount; i++) {
+                WeekView weekView = (WeekView) mListView.getChildAt(i);
+                if (weekView.mHasSelectedDay) {
+                    weekView.invalidate();
+                }
+            }
+        }
+    }
+
+    /**
+     * Gets the background color for the selected week.
+     *
+     * @return The week background color.
+     */
+    public int getSelectedWeekBackgroundColor() {
+        return mSelectedWeekBackgroundColor;
+    }
+
+    /**
+     * Sets the color for the dates of the focused month.
+     *
+     * @param color The focused month date color.
+     */
+    public void setFocusedMonthDateColor(int color) {
+        if (mFocusedMonthDateColor != color) {
+            mFocusedMonthDateColor = color;
+            final int childCount = mListView.getChildCount();
+            for (int i = 0; i < childCount; i++) {
+                WeekView weekView = (WeekView) mListView.getChildAt(i);
+                if (weekView.mHasFocusedDay) {
+                    weekView.invalidate();
+                }
+            }
+        }
+    }
+
+    /**
+     * Gets the color for the dates in the focused month.
+     *
+     * @return The focused month date color.
+     */
+    public int getFocusedMonthDateColor() {
+        return mFocusedMonthDateColor;
+    }
+
+    /**
+     * Sets the color for the dates of a not focused month.
+     *
+     * @param color A not focused month date color.
+     */
+    public void setUnfocusedMonthDateColor(int color) {
+        if (mUnfocusedMonthDateColor != color) {
+            mUnfocusedMonthDateColor = color;
+            final int childCount = mListView.getChildCount();
+            for (int i = 0; i < childCount; i++) {
+                WeekView weekView = (WeekView) mListView.getChildAt(i);
+                if (weekView.mHasUnfocusedDay) {
+                    weekView.invalidate();
+                }
+            }
+        }
+    }
+
+    /**
+     * Gets the color for the dates in a not focused month.
+     *
+     * @return A not focused month date color.
+     */
+    public int getUnfocusedMonthDateColor() {
+        return mFocusedMonthDateColor;
+    }
+
+    /**
+     * Sets the color for the week numbers.
+     *
+     * @param color The week number color.
+     */
+    public void setWeekNumberColor(int color) {
+        if (mWeekNumberColor != color) {
+            mWeekNumberColor = color;
+            if (mShowWeekNumber) {
+                invalidateAllWeekViews();
+            }
+        }
+    }
+
+    /**
+     * Gets the color for the week numbers.
+     *
+     * @return The week number color.
+     */
+    public int getWeekNumberColor() {
+        return mWeekNumberColor;
+    }
+
+    /**
+     * Sets the color for the separator line between weeks.
+     *
+     * @param color The week separator color.
+     */
+    public void setWeekSeparatorLineColor(int color) {
+        if (mWeekSeparatorLineColor != color) {
+            mWeekSeparatorLineColor = color;
+            invalidateAllWeekViews();
+        }
+    }
+
+    /**
+     * Gets the color for the separator line between weeks.
+     *
+     * @return The week separator color.
+     */
+    public int getWeekSeparatorLineColor() {
+        return mWeekSeparatorLineColor;
+    }
+
+    /**
+     * Sets the drawable for the vertical bar shown at the beginning and at
+     * the end of the selected date.
+     *
+     * @param resourceId The vertical bar drawable resource id.
+     */
+    public void setSelectedDateVerticalBar(int resourceId) {
+        Drawable drawable = getResources().getDrawable(resourceId);
+        setSelectedDateVerticalBar(drawable);
+    }
+
+    /**
+     * Sets the drawable for the vertical bar shown at the beginning and at
+     * the end of the selected date.
+     *
+     * @param drawable The vertical bar drawable.
+     */
+    public void setSelectedDateVerticalBar(Drawable drawable) {
+        if (mSelectedDateVerticalBar != drawable) {
+            mSelectedDateVerticalBar = drawable;
+            final int childCount = mListView.getChildCount();
+            for (int i = 0; i < childCount; i++) {
+                WeekView weekView = (WeekView) mListView.getChildAt(i);
+                if (weekView.mHasSelectedDay) {
+                    weekView.invalidate();
+                }
+            }
+        }
+    }
+
+    /**
+     * Gets the drawable for the vertical bar shown at the beginning and at
+     * the end of the selected date.
+     *
+     * @return The vertical bar drawable.
+     */
+    public Drawable getSelectedDateVerticalBar() {
+        return mSelectedDateVerticalBar;
+    }
+
+    /**
+     * Sets the text appearance for the week day abbreviation of the calendar header.
+     *
+     * @param resourceId The text appearance resource id.
+     */
+    public void setWeekDayTextAppearance(int resourceId) {
+        if (mWeekDayTextAppearanceResId != resourceId) {
+            mWeekDayTextAppearanceResId = resourceId;
+            setUpHeader();
+        }
+    }
+
+    /**
+     * Gets the text appearance for the week day abbreviation of the calendar header.
+     *
+     * @return The text appearance resource id.
+     */
+    public int getWeekDayTextAppearance() {
+        return mWeekDayTextAppearanceResId;
+    }
+
+    /**
+     * Sets the text appearance for the calendar dates.
+     *
+     * @param resourceId The text appearance resource id.
+     */
+    public void setDateTextAppearance(int resourceId) {
+        if (mDateTextAppearanceResId != resourceId) {
+            mDateTextAppearanceResId = resourceId;
+            updateDateTextSize();
+            invalidateAllWeekViews();
+        }
+    }
+
+    /**
+     * Gets the text appearance for the calendar dates.
+     *
+     * @return The text appearance resource id.
+     */
+    public int getDateTextAppearance() {
+        return mDateTextAppearanceResId;
+    }
+
     @Override
     public void setEnabled(boolean enabled) {
         mListView.setEnabled(enabled);
@@ -545,7 +774,7 @@
         }
         mShowWeekNumber = showWeekNumber;
         mAdapter.notifyDataSetChanged();
-        setUpHeader(DEFAULT_WEEK_DAY_TEXT_APPEARANCE_RES_ID);
+        setUpHeader();
     }
 
     /**
@@ -594,7 +823,7 @@
         mFirstDayOfWeek = firstDayOfWeek;
         mAdapter.init();
         mAdapter.notifyDataSetChanged();
-        setUpHeader(DEFAULT_WEEK_DAY_TEXT_APPEARANCE_RES_ID);
+        setUpHeader();
     }
 
     /**
@@ -655,6 +884,25 @@
         goTo(mTempDate, animate, true, center);
     }
 
+    private void updateDateTextSize() {
+        TypedArray dateTextAppearance = getContext().obtainStyledAttributes(
+                mDateTextAppearanceResId, R.styleable.TextAppearance);
+        mDateTextSize = dateTextAppearance.getDimensionPixelSize(
+                R.styleable.TextAppearance_textSize, DEFAULT_DATE_TEXT_SIZE);
+        dateTextAppearance.recycle();
+    }
+
+    /**
+     * Invalidates all week views.
+     */
+    private void invalidateAllWeekViews() {
+        final int childCount = mListView.getChildCount();
+        for (int i = 0; i < childCount; i++) {
+            View view = mListView.getChildAt(i);
+            view.invalidate();
+        }
+    }
+
     /**
      * Sets the current locale.
      *
@@ -727,7 +975,7 @@
     /**
      * Sets up the strings to be used by the header.
      */
-    private void setUpHeader(int weekDayTextAppearanceResId) {
+    private void setUpHeader() {
         mDayLabels = new String[mDaysPerWeek];
         for (int i = mFirstDayOfWeek, count = mFirstDayOfWeek + mDaysPerWeek; i < count; i++) {
             int calendarDay = (i > Calendar.SATURDAY) ? i - Calendar.SATURDAY : i;
@@ -743,8 +991,8 @@
         }
         for (int i = 1, count = mDayNamesHeader.getChildCount(); i < count; i++) {
             label = (TextView) mDayNamesHeader.getChildAt(i);
-            if (weekDayTextAppearanceResId > -1) {
-                label.setTextAppearance(mContext, weekDayTextAppearanceResId);
+            if (mWeekDayTextAppearanceResId > -1) {
+                label.setTextAppearance(mContext, mWeekDayTextAppearanceResId);
             }
             if (i < mDaysPerWeek + 1) {
                 label.setText(mDayLabels[i - 1]);
@@ -1198,6 +1446,12 @@
         // Quick lookup for checking which days are in the focus month
         private boolean[] mFocusDay;
 
+        // Whether this view has a focused day.
+        private boolean mHasFocusedDay;
+
+        // Whether this view has only focused days.
+        private boolean mHasUnfocusedDay;
+
         // The first day displayed by this item
         private Calendar mFirstDay;
 
@@ -1235,11 +1489,8 @@
         public WeekView(Context context) {
             super(context);
 
-            mHeight = (mListView.getHeight() - mListView.getPaddingTop() - mListView
-                    .getPaddingBottom()) / mShownWeekCount;
-
             // Sets up any standard paints that will be used
-            setPaintProperties();
+            initilaizePaints();
         }
 
         /**
@@ -1281,8 +1532,12 @@
             mFirstDay = (Calendar) mTempDate.clone();
             mMonthOfFirstWeekDay = mTempDate.get(Calendar.MONTH);
 
+            mHasUnfocusedDay = true;
             for (; i < mNumCells; i++) {
-                mFocusDay[i] = (mTempDate.get(Calendar.MONTH) == focusedMonth);
+                final boolean isFocusedDay = (mTempDate.get(Calendar.MONTH) == focusedMonth);
+                mFocusDay[i] = isFocusedDay;
+                mHasFocusedDay |= isFocusedDay;
+                mHasUnfocusedDay &= !isFocusedDay;
                 // do not draw dates outside the valid range to avoid user confusion
                 if (mTempDate.before(mMinDate) || mTempDate.after(mMaxDate)) {
                     mDayNumbers[i] = "";
@@ -1302,18 +1557,15 @@
         }
 
         /**
-         * Sets up the text and style properties for painting.
+         * Initialize the paint isntances.
          */
-        private void setPaintProperties() {
+        private void initilaizePaints() {
             mDrawPaint.setFakeBoldText(false);
             mDrawPaint.setAntiAlias(true);
-            mDrawPaint.setTextSize(mDateTextSize);
             mDrawPaint.setStyle(Style.FILL);
 
             mMonthNumDrawPaint.setFakeBoldText(true);
             mMonthNumDrawPaint.setAntiAlias(true);
-            mMonthNumDrawPaint.setTextSize(mDateTextSize);
-            mMonthNumDrawPaint.setColor(mFocusedMonthDateColor);
             mMonthNumDrawPaint.setStyle(Style.FILL);
             mMonthNumDrawPaint.setTextAlign(Align.CENTER);
         }
@@ -1369,7 +1621,7 @@
         @Override
         protected void onDraw(Canvas canvas) {
             drawBackground(canvas);
-            drawWeekNumbers(canvas);
+            drawWeekNumbersAndDates(canvas);
             drawWeekSeparators(canvas);
             drawSelectedDateVerticalBars(canvas);
         }
@@ -1401,12 +1653,13 @@
          *
          * @param canvas The canvas to draw on
          */
-        private void drawWeekNumbers(Canvas canvas) {
+        private void drawWeekNumbersAndDates(Canvas canvas) {
             float textHeight = mDrawPaint.getTextSize();
             int y = (int) ((mHeight + textHeight) / 2) - mWeekSeperatorLineWidth;
             int nDays = mNumCells;
 
             mDrawPaint.setTextAlign(Align.CENTER);
+            mDrawPaint.setTextSize(mDateTextSize);
             int i = 0;
             int divisor = 2 * nDays;
             if (mShowWeekNumber) {
@@ -1487,6 +1740,8 @@
 
         @Override
         protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+            mHeight = (mListView.getHeight() - mListView.getPaddingTop() - mListView
+                    .getPaddingBottom()) / mShownWeekCount;
             setMeasuredDimension(MeasureSpec.getSize(widthMeasureSpec), mHeight);
         }
     }
diff --git a/core/java/android/widget/CheckedTextView.java b/core/java/android/widget/CheckedTextView.java
index dd53325..603cea1 100644
--- a/core/java/android/widget/CheckedTextView.java
+++ b/core/java/android/widget/CheckedTextView.java
@@ -143,7 +143,7 @@
     }
 
     @Override
-    public void onResolvePadding(int layoutDirection) {
+    public void onPaddingChanged(int layoutDirection) {
         int newPadding = (mCheckMarkDrawable != null) ?
                 mCheckMarkWidth + mBasePadding : mBasePadding;
         mNeedRequestlayout |= (mPaddingRight != newPadding);
diff --git a/core/java/android/widget/DatePicker.java b/core/java/android/widget/DatePicker.java
index 110c8f3..fd93980 100644
--- a/core/java/android/widget/DatePicker.java
+++ b/core/java/android/widget/DatePicker.java
@@ -162,7 +162,7 @@
         int endYear = attributesArray.getInt(R.styleable.DatePicker_endYear, DEFAULT_END_YEAR);
         String minDate = attributesArray.getString(R.styleable.DatePicker_minDate);
         String maxDate = attributesArray.getString(R.styleable.DatePicker_maxDate);
-        int layoutResourceId = attributesArray.getResourceId(R.styleable.DatePicker_layout,
+        int layoutResourceId = attributesArray.getResourceId(R.styleable.DatePicker_internalLayout,
                 R.layout.date_picker);
         attributesArray.recycle();
 
diff --git a/core/java/android/widget/LinearLayout.java b/core/java/android/widget/LinearLayout.java
index b5deec7..a1bea43 100644
--- a/core/java/android/widget/LinearLayout.java
+++ b/core/java/android/widget/LinearLayout.java
@@ -309,7 +309,7 @@
             if (child != null && child.getVisibility() != GONE) {
                 if (hasDividerBeforeChildAt(i)) {
                     final LayoutParams lp = (LayoutParams) child.getLayoutParams();
-                    final int top = child.getTop() - lp.topMargin;
+                    final int top = child.getTop() - lp.topMargin - mDividerHeight;
                     drawHorizontalDivider(canvas, top);
                 }
             }
@@ -336,7 +336,7 @@
             if (child != null && child.getVisibility() != GONE) {
                 if (hasDividerBeforeChildAt(i)) {
                     final LayoutParams lp = (LayoutParams) child.getLayoutParams();
-                    final int left = child.getLeft() - lp.leftMargin;
+                    final int left = child.getLeft() - lp.leftMargin - mDividerWidth;
                     drawVerticalDivider(canvas, left);
                 }
             }
diff --git a/core/java/android/widget/NumberPicker.java b/core/java/android/widget/NumberPicker.java
index 6405ee9..3335da0 100644
--- a/core/java/android/widget/NumberPicker.java
+++ b/core/java/android/widget/NumberPicker.java
@@ -559,17 +559,17 @@
                 getResources().getDisplayMetrics());
         mSelectionDividerHeight = attributesArray.getDimensionPixelSize(
                 R.styleable.NumberPicker_selectionDividerHeight, defSelectionDividerHeight);
-        mMinHeight = attributesArray.getDimensionPixelSize(R.styleable.NumberPicker_minHeight,
-                SIZE_UNSPECIFIED);
-        mMaxHeight = attributesArray.getDimensionPixelSize(R.styleable.NumberPicker_maxHeight,
-                SIZE_UNSPECIFIED);
+        mMinHeight = attributesArray.getDimensionPixelSize(
+                R.styleable.NumberPicker_internalMinHeight, SIZE_UNSPECIFIED);
+        mMaxHeight = attributesArray.getDimensionPixelSize(
+                R.styleable.NumberPicker_internalMaxHeight, SIZE_UNSPECIFIED);
         if (mMinHeight != SIZE_UNSPECIFIED && mMaxHeight != SIZE_UNSPECIFIED
                 && mMinHeight > mMaxHeight) {
             throw new IllegalArgumentException("minHeight > maxHeight");
         }
-        mMinWidth = attributesArray.getDimensionPixelSize(R.styleable.NumberPicker_minWidth,
+        mMinWidth = attributesArray.getDimensionPixelSize(R.styleable.NumberPicker_internalMinWidth,
                 SIZE_UNSPECIFIED);
-        mMaxWidth = attributesArray.getDimensionPixelSize(R.styleable.NumberPicker_maxWidth,
+        mMaxWidth = attributesArray.getDimensionPixelSize(R.styleable.NumberPicker_internalMaxWidth,
                 SIZE_UNSPECIFIED);
         if (mMinWidth != SIZE_UNSPECIFIED && mMaxWidth != SIZE_UNSPECIFIED
                 && mMinWidth > mMaxWidth) {
diff --git a/core/java/android/widget/RemoteViews.java b/core/java/android/widget/RemoteViews.java
index 62afd61..55acb74 100644
--- a/core/java/android/widget/RemoteViews.java
+++ b/core/java/android/widget/RemoteViews.java
@@ -1217,7 +1217,7 @@
     /**
      * Equivalent to calling ImageView.setImageBitmap
      * 
-     * @param viewId The id of the view whose drawable should change
+     * @param viewId The id of the view whose bitmap should change
      * @param bitmap The new Bitmap for the drawable
      */
     public void setImageViewBitmap(int viewId, Bitmap bitmap) {
@@ -1240,7 +1240,7 @@
      * and {@link Chronometer#start Chronometer.start()} or
      * {@link Chronometer#stop Chronometer.stop()}.
      * 
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the {@link Chronometer} to change
      * @param base The time at which the timer would have read 0:00.  This
      *             time should be based off of
      *             {@link android.os.SystemClock#elapsedRealtime SystemClock.elapsedRealtime()}.
@@ -1261,7 +1261,7 @@
      *
      * If indeterminate is true, then the values for max and progress are ignored.
      * 
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the {@link ProgressBar} to change
      * @param max The 100% value for the progress bar
      * @param progress The current value of the progress bar.
      * @param indeterminate True if the progress bar is indeterminate, 
@@ -1367,7 +1367,7 @@
     /**
      * Equivalent to calling {@link android.widget.TextView#setTextColor(int)}.
      * 
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view whose text color should change
      * @param color Sets the text color for all the states (normal, selected,
      *            focused) to be this color.
      */
@@ -1380,7 +1380,7 @@
      *
      * @param appWidgetId The id of the app widget which contains the specified view. (This
      *      parameter is ignored in this deprecated method)
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the {@link AbsListView}
      * @param intent The intent of the service which will be
      *            providing data to the RemoteViewsAdapter
      * @deprecated This method has been deprecated. See
@@ -1395,7 +1395,7 @@
      * Equivalent to calling {@link android.widget.AbsListView#setRemoteViewsAdapter(Intent)}.
      * Can only be used for App Widgets.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the {@link AbsListView}
      * @param intent The intent of the service which will be
      *            providing data to the RemoteViewsAdapter
      */
@@ -1406,7 +1406,7 @@
     /**
      * Equivalent to calling {@link android.widget.AbsListView#smoothScrollToPosition(int, int)}.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view to change
      * @param position Scroll to this adapter position
      */
     public void setScrollPosition(int viewId, int position) {
@@ -1416,7 +1416,7 @@
     /**
      * Equivalent to calling {@link android.widget.AbsListView#smoothScrollToPosition(int, int)}.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view to change
      * @param offset Scroll by this adapter position offset
      */
     public void setRelativeScrollPosition(int viewId, int offset) {
@@ -1426,7 +1426,7 @@
     /**
      * Call a method taking one boolean on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1437,7 +1437,7 @@
     /**
      * Call a method taking one byte on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1448,7 +1448,7 @@
     /**
      * Call a method taking one short on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1459,7 +1459,7 @@
     /**
      * Call a method taking one int on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1470,7 +1470,7 @@
     /**
      * Call a method taking one long on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1481,7 +1481,7 @@
     /**
      * Call a method taking one float on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1492,7 +1492,7 @@
     /**
      * Call a method taking one double on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1503,7 +1503,7 @@
     /**
      * Call a method taking one char on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1514,7 +1514,7 @@
     /**
      * Call a method taking one String on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1525,7 +1525,7 @@
     /**
      * Call a method taking one CharSequence on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1536,7 +1536,7 @@
     /**
      * Call a method taking one Uri on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1550,7 +1550,7 @@
      * <p class="note">The bitmap will be flattened into the parcel if this object is
      * sent across processes, so it may end up using a lot of memory, and may be fairly slow.</p>
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1561,7 +1561,7 @@
     /**
      * Call a method taking one Bundle on a view in the layout for this RemoteViews.
      *
-     * @param viewId The id of the view whose text should change
+     * @param viewId The id of the view on which to call the method.
      * @param methodName The name of the method to call.
      * @param value The value to pass to the method.
      */
@@ -1570,10 +1570,11 @@
     }
 
     /**
+     * Call a method taking one Intent on a view in the layout for this RemoteViews.
      *
-     * @param viewId
-     * @param methodName
-     * @param value
+     * @param viewId The id of the view on which to call the method.
+     * @param methodName The name of the method to call.
+     * @param value The {@link android.content.Intent} to pass the method.
      */
     public void setIntent(int viewId, String methodName, Intent value) {
         addAction(new ReflectionAction(viewId, methodName, ReflectionAction.INTENT, value));
diff --git a/core/java/android/widget/Spinner.java b/core/java/android/widget/Spinner.java
index 2cacbdc..89c506f 100644
--- a/core/java/android/widget/Spinner.java
+++ b/core/java/android/widget/Spinner.java
@@ -26,6 +26,7 @@
 import android.graphics.Rect;
 import android.graphics.drawable.Drawable;
 import android.util.AttributeSet;
+import android.util.DisplayMetrics;
 import android.view.Gravity;
 import android.view.View;
 import android.view.ViewGroup;
@@ -40,13 +41,13 @@
  *
  * <p>See the <a href="{@docRoot}resources/tutorials/views/hello-spinner.html">Spinner
  * tutorial</a>.</p>
- * 
+ *
  * @attr ref android.R.styleable#Spinner_prompt
  */
 @Widget
 public class Spinner extends AbsSpinner implements OnClickListener {
     private static final String TAG = "Spinner";
-    
+
     // Only measure this many items to get a decent max width.
     private static final int MAX_ITEMS_MEASURED = 15;
 
@@ -54,7 +55,7 @@
      * Use a dialog window for selecting spinner options.
      */
     public static final int MODE_DIALOG = 0;
-    
+
     /**
      * Use a dropdown anchored to the Spinner for selecting spinner options.
      */
@@ -759,13 +760,30 @@
 
         @Override
         public void show() {
+            final Drawable background = getBackground();
+            int bgOffset = 0;
+            if (background != null) {
+                background.getPadding(mTempRect);
+                bgOffset = -mTempRect.left;
+            } else {
+                mTempRect.left = mTempRect.right = 0;
+            }
+
             final int spinnerPaddingLeft = Spinner.this.getPaddingLeft();
             if (mDropDownWidth == WRAP_CONTENT) {
                 final int spinnerWidth = Spinner.this.getWidth();
                 final int spinnerPaddingRight = Spinner.this.getPaddingRight();
+
+                int contentWidth =  measureContentWidth(
+                        (SpinnerAdapter) mAdapter, getBackground());
+                final int contentWidthLimit = mContext.getResources()
+                        .getDisplayMetrics().widthPixels - mTempRect.left - mTempRect.right;
+                if (contentWidth > contentWidthLimit) {
+                    contentWidth = contentWidthLimit;
+                }
+
                 setContentWidth(Math.max(
-                        measureContentWidth((SpinnerAdapter) mAdapter, getBackground()),
-                        spinnerWidth - spinnerPaddingLeft - spinnerPaddingRight));
+                       contentWidth, spinnerWidth - spinnerPaddingLeft - spinnerPaddingRight));
             } else if (mDropDownWidth == MATCH_PARENT) {
                 final int spinnerWidth = Spinner.this.getWidth();
                 final int spinnerPaddingRight = Spinner.this.getPaddingRight();
@@ -773,12 +791,6 @@
             } else {
                 setContentWidth(mDropDownWidth);
             }
-            final Drawable background = getBackground();
-            int bgOffset = 0;
-            if (background != null) {
-                background.getPadding(mTempRect);
-                bgOffset = -mTempRect.left;
-            }
             setHorizontalOffset(bgOffset + spinnerPaddingLeft);
             setInputMethodMode(ListPopupWindow.INPUT_METHOD_NOT_NEEDED);
             super.show();
diff --git a/core/java/android/widget/TextView.java b/core/java/android/widget/TextView.java
index 385c7c7..56a0d1e 100644
--- a/core/java/android/widget/TextView.java
+++ b/core/java/android/widget/TextView.java
@@ -8715,7 +8715,7 @@
     }
 
     @Override
-    public void onResolveTextDirection() {
+    public void onResolvedTextDirectionChanged() {
         if (hasPasswordTransformationMethod()) {
             // TODO: take care of the content direction to show the password text and dots justified
             // to the left or to the right
diff --git a/core/java/android/widget/TimePicker.java b/core/java/android/widget/TimePicker.java
index ef1d7d0..7eff1aa 100644
--- a/core/java/android/widget/TimePicker.java
+++ b/core/java/android/widget/TimePicker.java
@@ -136,7 +136,7 @@
         TypedArray attributesArray = context.obtainStyledAttributes(
                 attrs, R.styleable.TimePicker, defStyle, 0);
         int layoutResourceId = attributesArray.getResourceId(
-                R.styleable.TimePicker_layout, R.layout.time_picker);
+                R.styleable.TimePicker_internalLayout, R.layout.time_picker);
         attributesArray.recycle();
 
         LayoutInflater inflater = (LayoutInflater) context.getSystemService(
diff --git a/core/java/com/android/internal/app/ResolverActivity.java b/core/java/com/android/internal/app/ResolverActivity.java
index 3fba1be..0563846 100644
--- a/core/java/com/android/internal/app/ResolverActivity.java
+++ b/core/java/com/android/internal/app/ResolverActivity.java
@@ -17,6 +17,8 @@
 package com.android.internal.app;
 
 import com.android.internal.R;
+import com.android.internal.content.PackageMonitor;
+
 import android.content.ComponentName;
 import android.content.Context;
 import android.content.DialogInterface;
@@ -58,6 +60,12 @@
     private TextView mClearDefaultHint;
     private PackageManager mPm;
 
+    private final PackageMonitor mPackageMonitor = new PackageMonitor() {
+        @Override public void onSomePackagesChanged() {
+            mAdapter.handlePackagesChanged();
+        }
+    };
+
     private Intent makeMyIntent() {
         Intent intent = new Intent(getIntent());
         // The resolver activity is set to be hidden from recent tasks.
@@ -88,6 +96,8 @@
         ap.mTitle = title;
         ap.mOnClickListener = this;
 
+        mPackageMonitor.register(this, false);
+
         if (alwaysUseOption) {
             LayoutInflater inflater = (LayoutInflater) getSystemService(
                     Context.LAYOUT_INFLATER_SERVICE);
@@ -114,6 +124,19 @@
         setupAlert();
     }
 
+    @Override
+    protected void onRestart() {
+        super.onRestart();
+        mPackageMonitor.register(this, false);
+        mAdapter.handlePackagesChanged();
+    }
+
+    @Override
+    protected void onStop() {
+        super.onStop();
+        mPackageMonitor.unregister();
+    }
+
     public void onClick(DialogInterface dialog, int which) {
         ResolveInfo ri = mAdapter.resolveInfoForPosition(which);
         Intent intent = mAdapter.intentForPosition(which);
@@ -225,29 +248,48 @@
     }
 
     private final class ResolveListAdapter extends BaseAdapter {
+        private final Intent[] mInitialIntents;
+        private final List<ResolveInfo> mBaseResolveList;
         private final Intent mIntent;
         private final LayoutInflater mInflater;
 
+        private List<ResolveInfo> mCurrentResolveList;
         private List<DisplayResolveInfo> mList;
 
         public ResolveListAdapter(Context context, Intent intent,
                 Intent[] initialIntents, List<ResolveInfo> rList) {
             mIntent = new Intent(intent);
             mIntent.setComponent(null);
+            mInitialIntents = initialIntents;
+            mBaseResolveList = rList;
             mInflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
+            rebuildList();
+        }
 
-            if (rList == null) {
-                rList = mPm.queryIntentActivities(
-                        intent, PackageManager.MATCH_DEFAULT_ONLY
+        public void handlePackagesChanged() {
+            rebuildList();
+            notifyDataSetChanged();
+            if (mList.size() <= 0) {
+                // We no longer have any items...  just finish the activity.
+                finish();
+            }
+        }
+
+        private void rebuildList() {
+            if (mBaseResolveList != null) {
+                mCurrentResolveList = mBaseResolveList;
+            } else {
+                mCurrentResolveList = mPm.queryIntentActivities(
+                        mIntent, PackageManager.MATCH_DEFAULT_ONLY
                         | (mAlwaysCheck != null ? PackageManager.GET_RESOLVED_FILTER : 0));
             }
             int N;
-            if ((rList != null) && ((N = rList.size()) > 0)) {
+            if ((mCurrentResolveList != null) && ((N = mCurrentResolveList.size()) > 0)) {
                 // Only display the first matches that are either of equal
                 // priority or have asked to be default options.
-                ResolveInfo r0 = rList.get(0);
+                ResolveInfo r0 = mCurrentResolveList.get(0);
                 for (int i=1; i<N; i++) {
-                    ResolveInfo ri = rList.get(i);
+                    ResolveInfo ri = mCurrentResolveList.get(i);
                     if (false) Log.v(
                         "ResolveListActivity",
                         r0.activityInfo.name + "=" +
@@ -257,7 +299,7 @@
                    if (r0.priority != ri.priority ||
                         r0.isDefault != ri.isDefault) {
                         while (i < N) {
-                            rList.remove(i);
+                            mCurrentResolveList.remove(i);
                             N--;
                         }
                     }
@@ -265,15 +307,15 @@
                 if (N > 1) {
                     ResolveInfo.DisplayNameComparator rComparator =
                             new ResolveInfo.DisplayNameComparator(mPm);
-                    Collections.sort(rList, rComparator);
+                    Collections.sort(mCurrentResolveList, rComparator);
                 }
                 
                 mList = new ArrayList<DisplayResolveInfo>();
                 
                 // First put the initial items at the top.
-                if (initialIntents != null) {
-                    for (int i=0; i<initialIntents.length; i++) {
-                        Intent ii = initialIntents[i];
+                if (mInitialIntents != null) {
+                    for (int i=0; i<mInitialIntents.length; i++) {
+                        Intent ii = mInitialIntents[i];
                         if (ii == null) {
                             continue;
                         }
@@ -300,14 +342,14 @@
                 
                 // Check for applications with same name and use application name or
                 // package name if necessary
-                r0 = rList.get(0);
+                r0 = mCurrentResolveList.get(0);
                 int start = 0;
                 CharSequence r0Label =  r0.loadLabel(mPm);
                 for (int i = 1; i < N; i++) {
                     if (r0Label == null) {
                         r0Label = r0.activityInfo.packageName;
                     }
-                    ResolveInfo ri = rList.get(i);
+                    ResolveInfo ri = mCurrentResolveList.get(i);
                     CharSequence riLabel = ri.loadLabel(mPm);
                     if (riLabel == null) {
                         riLabel = ri.activityInfo.packageName;
@@ -315,13 +357,13 @@
                     if (riLabel.equals(r0Label)) {
                         continue;
                     }
-                    processGroup(rList, start, (i-1), r0, r0Label);
+                    processGroup(mCurrentResolveList, start, (i-1), r0, r0Label);
                     r0 = ri;
                     r0Label = riLabel;
                     start = i;
                 }
                 // Process last group
-                processGroup(rList, start, (N-1), r0, r0Label);
+                processGroup(mCurrentResolveList, start, (N-1), r0, r0Label);
             }
         }
 
diff --git a/core/java/com/android/internal/util/Protocol.java b/core/java/com/android/internal/util/Protocol.java
index 0cadb16..d462d7f 100644
--- a/core/java/com/android/internal/util/Protocol.java
+++ b/core/java/com/android/internal/util/Protocol.java
@@ -44,6 +44,7 @@
     public static final int BASE_WIFI_P2P_MANAGER                                   = 0x00022000;
     public static final int BASE_WIFI_P2P_SERVICE                                   = 0x00023000;
     public static final int BASE_WIFI_MONITOR                                       = 0x00024000;
+    public static final int BASE_WIFI_MANAGER                                       = 0x00025000;
     public static final int BASE_DHCP                                               = 0x00030000;
     public static final int BASE_DATA_CONNECTION                                    = 0x00040000;
     public static final int BASE_DATA_CONNECTION_AC                                 = 0x00041000;
diff --git a/core/res/res/anim/screen_rotate_0_frame.xml b/core/res/res/anim/screen_rotate_0_frame.xml
new file mode 100644
index 0000000..5ea9bf8
--- /dev/null
+++ b/core/res/res/anim/screen_rotate_0_frame.xml
@@ -0,0 +1,25 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+** Copyright 2012, 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:shareInterpolator="false">
+    <alpha android:fromAlpha="1.0" android:toAlpha="1.0"
+            android:interpolator="@interpolator/decelerate_quint"
+            android:duration="@android:integer/config_shortAnimTime" />
+</set>
diff --git a/core/res/res/anim/screen_rotate_180_enter.xml b/core/res/res/anim/screen_rotate_180_enter.xml
index 470416b..688a8d5 100644
--- a/core/res/res/anim/screen_rotate_180_enter.xml
+++ b/core/res/res/anim/screen_rotate_180_enter.xml
@@ -25,4 +25,4 @@
             android:fillEnabled="true"
             android:fillBefore="true" android:fillAfter="true"
             android:duration="@android:integer/config_mediumAnimTime" />
-</set>
\ No newline at end of file
+</set>
diff --git a/core/res/res/anim/screen_rotate_180_frame.xml b/core/res/res/anim/screen_rotate_180_frame.xml
new file mode 100644
index 0000000..19dade1
--- /dev/null
+++ b/core/res/res/anim/screen_rotate_180_frame.xml
@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+** Copyright 2012, 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:shareInterpolator="false">
+    <rotate android:fromDegrees="180" android:toDegrees="0"
+            android:pivotX="50%" android:pivotY="50%"
+            android:interpolator="@interpolator/decelerate_quint"
+            android:fillEnabled="true"
+            android:fillBefore="true" android:fillAfter="true"
+            android:duration="@android:integer/config_mediumAnimTime" />
+</set>
diff --git a/core/res/res/anim/screen_rotate_finish_enter.xml b/core/res/res/anim/screen_rotate_finish_enter.xml
index 849aa66..9d731e6 100644
--- a/core/res/res/anim/screen_rotate_finish_enter.xml
+++ b/core/res/res/anim/screen_rotate_finish_enter.xml
@@ -19,13 +19,14 @@
 
 <set xmlns:android="http://schemas.android.com/apk/res/android"
         android:shareInterpolator="false">
-    <scale android:fromXScale="1.0" android:toXScale="1.25"
-            android:fromYScale="1.0" android:toYScale="1.25"
+    <scale android:fromXScale="1.0" android:toXScale="1.1111111111111"
+            android:fromYScale="1.0" android:toYScale="1.1111111111111"
             android:pivotX="50%" android:pivotY="50%"
-            android:interpolator="@interpolator/decelerate_quint"
+            android:interpolator="@interpolator/accelerate_decelerate"
             android:fillEnabled="true"
             android:fillBefore="true" android:fillAfter="true"
-            android:duration="@android:integer/config_mediumAnimTime"/>
+            android:duration="@android:integer/config_shortAnimTime"/>
+    <!--
     <scale android:fromXScale="100%p" android:toXScale="100%"
             android:fromYScale="100%p" android:toYScale="100%"
             android:pivotX="50%" android:pivotY="50%"
@@ -33,4 +34,5 @@
             android:fillEnabled="true"
             android:fillBefore="true" android:fillAfter="true"
             android:duration="@android:integer/config_mediumAnimTime" />
+    -->
 </set>
diff --git a/core/res/res/anim/screen_rotate_finish_exit.xml b/core/res/res/anim/screen_rotate_finish_exit.xml
index 7f70dbc..60daa18 100644
--- a/core/res/res/anim/screen_rotate_finish_exit.xml
+++ b/core/res/res/anim/screen_rotate_finish_exit.xml
@@ -19,23 +19,21 @@
 
 <set xmlns:android="http://schemas.android.com/apk/res/android"
         android:shareInterpolator="false">
-    <scale android:fromXScale="1.0" android:toXScale="1.25"
-            android:fromYScale="1.0" android:toYScale="1.25"
+    <scale android:fromXScale="1.0" android:toXScale="1.0"
+            android:fromYScale="1.0" android:toYScale="1.0"
             android:pivotX="50%" android:pivotY="50%"
-            android:interpolator="@interpolator/decelerate_quint"
+            android:interpolator="@interpolator/accelerate_decelerate"
             android:fillEnabled="true"
             android:fillBefore="false" android:fillAfter="true"
-            android:duration="@android:integer/config_mediumAnimTime"/>
-    <!--
+            android:duration="@android:integer/config_shortAnimTime"/>
     <scale android:fromXScale="100%" android:toXScale="100%p"
             android:fromYScale="100%" android:toYScale="100%p"
             android:pivotX="50%" android:pivotY="50%"
-            android:interpolator="@interpolator/decelerate_quint"
+            android:interpolator="@interpolator/accelerate_decelerate"
             android:duration="@android:integer/config_mediumAnimTime" />
-    -->
     <alpha android:fromAlpha="1.0" android:toAlpha="0"
-            android:interpolator="@interpolator/decelerate_quint"
+            android:interpolator="@interpolator/accelerate_decelerate"
             android:fillEnabled="true"
             android:fillBefore="true" android:fillAfter="true"
-            android:duration="@android:integer/config_mediumAnimTime" />
+            android:duration="@android:integer/config_shortAnimTime" />
 </set>
diff --git a/core/res/res/anim/screen_rotate_finish_frame.xml b/core/res/res/anim/screen_rotate_finish_frame.xml
new file mode 100644
index 0000000..06dfc5e
--- /dev/null
+++ b/core/res/res/anim/screen_rotate_finish_frame.xml
@@ -0,0 +1,36 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+** Copyright 2012, 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:shareInterpolator="false">
+    <scale android:fromXScale="1.0" android:toXScale="1.1111111111111"
+            android:fromYScale="1.0" android:toYScale="1.1111111111111"
+            android:pivotX="50%" android:pivotY="50%"
+            android:interpolator="@interpolator/accelerate_decelerate"
+            android:fillEnabled="true"
+            android:fillBefore="true" android:fillAfter="true"
+            android:duration="@android:integer/config_shortAnimTime"/>
+    <scale android:fromXScale="100%" android:toXScale="100%p"
+            android:fromYScale="100%" android:toYScale="100%p"
+            android:pivotX="50%" android:pivotY="50%"
+            android:fillEnabled="true"
+            android:fillBefore="true" android:fillAfter="true"
+            android:interpolator="@interpolator/accelerate_decelerate"
+            android:duration="@android:integer/config_shortAnimTime" />
+</set>
diff --git a/core/res/res/anim/screen_rotate_minus_90_frame.xml b/core/res/res/anim/screen_rotate_minus_90_frame.xml
new file mode 100644
index 0000000..874f2e9
--- /dev/null
+++ b/core/res/res/anim/screen_rotate_minus_90_frame.xml
@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+** Copyright 2012, 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:shareInterpolator="false">
+    <rotate android:fromDegrees="0" android:toDegrees="90"
+            android:pivotX="50%" android:pivotY="50%"
+            android:interpolator="@interpolator/decelerate_quint"
+            android:fillEnabled="true"
+            android:fillBefore="true" android:fillAfter="true"
+            android:duration="@android:integer/config_mediumAnimTime" />
+</set>
diff --git a/core/res/res/anim/screen_rotate_plus_90_frame.xml b/core/res/res/anim/screen_rotate_plus_90_frame.xml
new file mode 100644
index 0000000..03c6aa6
--- /dev/null
+++ b/core/res/res/anim/screen_rotate_plus_90_frame.xml
@@ -0,0 +1,28 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+** Copyright 2012, 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:shareInterpolator="false">
+    <rotate android:fromDegrees="0" android:toDegrees="-90"
+            android:pivotX="50%" android:pivotY="50%"
+            android:interpolator="@interpolator/decelerate_quint"
+            android:fillEnabled="true"
+            android:fillBefore="true" android:fillAfter="true"
+            android:duration="@android:integer/config_mediumAnimTime" />
+</set>
diff --git a/core/res/res/anim/screen_rotate_start_enter.xml b/core/res/res/anim/screen_rotate_start_enter.xml
index e3f48e4..162ae8c 100644
--- a/core/res/res/anim/screen_rotate_start_enter.xml
+++ b/core/res/res/anim/screen_rotate_start_enter.xml
@@ -19,8 +19,8 @@
 
 <set xmlns:android="http://schemas.android.com/apk/res/android"
         android:shareInterpolator="false">
-    <scale android:fromXScale="1.0" android:toXScale="0.8"
-            android:fromYScale="1.0" android:toYScale="0.8"
+    <scale android:fromXScale="1.0" android:toXScale="0.9"
+            android:fromYScale="1.0" android:toYScale="0.9"
             android:pivotX="50%" android:pivotY="50%"
             android:interpolator="@interpolator/decelerate_quint"
             android:fillEnabled="true"
diff --git a/core/res/res/anim/screen_rotate_start_exit.xml b/core/res/res/anim/screen_rotate_start_exit.xml
index e3f48e4..162ae8c 100644
--- a/core/res/res/anim/screen_rotate_start_exit.xml
+++ b/core/res/res/anim/screen_rotate_start_exit.xml
@@ -19,8 +19,8 @@
 
 <set xmlns:android="http://schemas.android.com/apk/res/android"
         android:shareInterpolator="false">
-    <scale android:fromXScale="1.0" android:toXScale="0.8"
-            android:fromYScale="1.0" android:toYScale="0.8"
+    <scale android:fromXScale="1.0" android:toXScale="0.9"
+            android:fromYScale="1.0" android:toYScale="0.9"
             android:pivotX="50%" android:pivotY="50%"
             android:interpolator="@interpolator/decelerate_quint"
             android:fillEnabled="true"
diff --git a/core/res/res/anim/screen_rotate_start_frame.xml b/core/res/res/anim/screen_rotate_start_frame.xml
new file mode 100644
index 0000000..162ae8c
--- /dev/null
+++ b/core/res/res/anim/screen_rotate_start_frame.xml
@@ -0,0 +1,29 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+** Copyright 2012, 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:shareInterpolator="false">
+    <scale android:fromXScale="1.0" android:toXScale="0.9"
+            android:fromYScale="1.0" android:toYScale="0.9"
+            android:pivotX="50%" android:pivotY="50%"
+            android:interpolator="@interpolator/decelerate_quint"
+            android:fillEnabled="true"
+            android:fillBefore="true" android:fillAfter="true"
+            android:duration="@android:integer/config_mediumAnimTime"/>
+</set>
diff --git a/core/res/res/values/attrs.xml b/core/res/res/values/attrs.xml
index 9375730..f31deef 100755
--- a/core/res/res/values/attrs.xml
+++ b/core/res/res/values/attrs.xml
@@ -3376,9 +3376,13 @@
     </declare-styleable>
 
     <declare-styleable name="DatePicker">
-        <!-- The first year (inclusive), for example "1940". -->
+        <!-- The first year (inclusive), for example "1940".
+             {@deprecated Use minDate instead.}
+         -->
         <attr name="startYear" format="integer" />
-        <!-- The last year (inclusive), for example "2010". -->
+        <!-- The last year (inclusive), for example "2010".
+             {@deprecated Use maxDate instead.}
+         -->
         <attr name="endYear" format="integer" />
         <!-- Whether the spinners are shown. -->
         <attr name="spinnersShown" format="boolean" />
@@ -3388,8 +3392,8 @@
         <attr name="minDate" format="string" />
         <!-- The minimal date shown by this calendar view in mm/dd/yyyy format. -->
         <attr name="maxDate" format="string" />
-        <!-- @hide The layout of the time picker. -->
-        <attr name="layout" />
+        <!-- @hide The layout of the date picker. -->
+        <attr name="internalLayout" format="reference"  />
     </declare-styleable>
 
     <declare-styleable name="TwoLineListItem">
@@ -3593,15 +3597,15 @@
         <attr name="shownWeekCount" format="integer"/>
         <!-- The background color for the selected week. -->
         <attr name="selectedWeekBackgroundColor" format="color|reference" />
-        <!-- The color for the dates of the selected month. -->
+        <!-- The color for the dates of the focused month. -->
         <attr name="focusedMonthDateColor" format="color|reference" />
         <!-- The color for the dates of an unfocused month. -->
         <attr name="unfocusedMonthDateColor" format="color|reference" />
         <!-- The color for the week numbers. -->
         <attr name="weekNumberColor" format="color|reference" />
-        <!-- The color for the sepatator line between weeks. -->
+        <!-- The color for the separator line between weeks. -->
         <attr name="weekSeparatorLineColor" format="color|reference" />
-        <!-- Drawable for the vertical bar shown at the beggining and at the end of a selected date. -->
+        <!-- Drawable for the vertical bar shown at the beginning and at the end of the selected date. -->
         <attr name="selectedDateVerticalBar" format="reference" />
         <!-- The text appearance for the week day abbreviation of the calendar header. -->
         <attr name="weekDayTextAppearance" format="reference" />
@@ -3619,20 +3623,18 @@
         <!-- @hide The height of the selection divider. -->
         <attr name="selectionDividerHeight" format="dimension" />
         <!-- @hide The min height of the NumberPicker. -->
-        <attr name="minHeight" />
+        <attr name="internalMinHeight" format="dimension" />
         <!-- @hide The max height of the NumberPicker. -->
-        <attr name="maxHeight" />
+        <attr name="internalMaxHeight" format="dimension" />
         <!-- @hide The min width of the NumberPicker. -->
-        <attr name="minWidth" />
+        <attr name="internalMinWidth" format="dimension" />
         <!-- @hide The max width of the NumberPicker. -->
-        <attr name="maxWidth" />
-        <!-- @hide The max width of the NumberPicker. -->
-        <attr name="maxWidth" />
+        <attr name="internalMaxWidth" format="dimension" />
     </declare-styleable>
 
     <declare-styleable name="TimePicker">
         <!-- @hide The layout of the time picker. -->
-        <attr name="layout" />
+        <attr name="internalLayout" />
     </declare-styleable>
 
     <!-- ========================= -->
diff --git a/core/res/res/values/config.xml b/core/res/res/values/config.xml
index 8e5b509..eaf9c8c 100755
--- a/core/res/res/values/config.xml
+++ b/core/res/res/values/config.xml
@@ -654,20 +654,37 @@
          PERSIST may improve performance by reducing how often journal blocks are
          reallocated (compared to truncation) resulting in better data block locality
          and less churn of the storage media. -->
-    <string name="db_default_journal_mode">TRUNCATE</string>
+    <string name="db_default_journal_mode">PERSIST</string>
 
     <!-- Maximum size of the persistent journal file in bytes.
          If the journal file grows to be larger than this amount then SQLite will
          truncate it after committing the transaction. -->
     <integer name="db_journal_size_limit">524288</integer>
 
-    <!-- The database synchronization mode.
+    <!-- The database synchronization mode when using the default journal mode.
+         FULL is safest and preserves durability at the cost of extra fsyncs.
+         NORMAL also preserves durability in non-WAL modes and uses checksums to ensure
+         integrity although there is a small chance that an error might go unnoticed.
          Choices are: FULL, NORMAL, OFF. -->
-    <string name="db_sync_mode">FULL</string>
+    <string name="db_default_sync_mode">FULL</string>
 
-    <!-- The Write-Ahead Log auto-checkpoint interval in database pages.
-         The log is checkpointed automatically whenever it exceeds this many pages. -->
-    <integer name="db_wal_autocheckpoint">1</integer>
+    <!-- The database synchronization mode when using Write-Ahead Logging.
+         FULL is safest and preserves durability at the cost of extra fsyncs.
+         NORMAL sacrifices durability in WAL mode because syncs are only performed before
+         and after checkpoint operations.  If checkpoints are infrequent and power loss
+         occurs, then committed transactions could be lost and applications might break.
+         Choices are: FULL, NORMAL, OFF. -->
+    <string name="db_wal_sync_mode">FULL</string>
+
+    <!-- The Write-Ahead Log auto-checkpoint interval in database pages (typically 1 to 4KB).
+         The log is checkpointed automatically whenever it exceeds this many pages.
+         When a database is reopened, its journal mode is set back to the default
+         journal mode, which may cause a checkpoint operation to occur.  Checkpoints
+         can also happen at other times when transactions are committed.
+         The bigger the WAL file, the longer a checkpoint operation takes, so we try
+         to keep the WAL file relatively small to avoid long delays.
+         The size of the WAL file is also constrained by 'db_journal_size_limit'. -->
+    <integer name="db_wal_autocheckpoint">100</integer>
 
     <!-- Max space (in MB) allocated to DownloadManager to store the downloaded
          files if they are to be stored in DownloadManager's data dir,
diff --git a/core/res/res/values/public.xml b/core/res/res/values/public.xml
index 15499fe..2d8a394 100644
--- a/core/res/res/values/public.xml
+++ b/core/res/res/values/public.xml
@@ -441,7 +441,8 @@
   <java-symbol type="string" name="day_of_week_shortest_tuesday" />
   <java-symbol type="string" name="day_of_week_shortest_wednesday" />
   <java-symbol type="string" name="db_default_journal_mode" />
-  <java-symbol type="string" name="db_sync_mode" />
+  <java-symbol type="string" name="db_default_sync_mode" />
+  <java-symbol type="string" name="db_wal_sync_mode" />
   <java-symbol type="string" name="decline" />
   <java-symbol type="string" name="default_permission_group" />
   <java-symbol type="string" name="default_text_encoding" />
@@ -1281,16 +1282,22 @@
   <!-- From services -->
   <java-symbol type="anim" name="screen_rotate_0_enter" />
   <java-symbol type="anim" name="screen_rotate_0_exit" />
+  <java-symbol type="anim" name="screen_rotate_0_frame" />
   <java-symbol type="anim" name="screen_rotate_180_enter" />
   <java-symbol type="anim" name="screen_rotate_180_exit" />
+  <java-symbol type="anim" name="screen_rotate_180_frame" />
   <java-symbol type="anim" name="screen_rotate_finish_enter" />
   <java-symbol type="anim" name="screen_rotate_finish_exit" />
+  <java-symbol type="anim" name="screen_rotate_finish_frame" />
   <java-symbol type="anim" name="screen_rotate_minus_90_enter" />
   <java-symbol type="anim" name="screen_rotate_minus_90_exit" />
+  <java-symbol type="anim" name="screen_rotate_minus_90_frame" />
   <java-symbol type="anim" name="screen_rotate_plus_90_enter" />
   <java-symbol type="anim" name="screen_rotate_plus_90_exit" />
+  <java-symbol type="anim" name="screen_rotate_plus_90_frame" />
   <java-symbol type="anim" name="screen_rotate_start_enter" />
   <java-symbol type="anim" name="screen_rotate_start_exit" />
+  <java-symbol type="anim" name="screen_rotate_start_frame" />
   <java-symbol type="anim" name="window_move_from_decor" />
   <java-symbol type="array" name="config_autoBrightnessButtonBacklightValues" />
   <java-symbol type="array" name="config_autoBrightnessKeyboardBacklightValues" />
@@ -1954,7 +1961,9 @@
   <public type="attr" name="flipInterval" id="0x01010179" />
   <public type="attr" name="fillViewport" id="0x0101017a" />
   <public type="attr" name="prompt" id="0x0101017b" />
+  <!-- {@deprecated Use minDate instead.} -->
   <public type="attr" name="startYear" id="0x0101017c" />
+  <!-- {@deprecated Use maxDate instead.} -->
   <public type="attr" name="endYear" id="0x0101017d" />
   <public type="attr" name="mode" id="0x0101017e" />
   <public type="attr" name="layout_x" id="0x0101017f" />
@@ -3525,6 +3534,8 @@
 
   <public type="attr" name="textDirection"/>
 
+  <public type="attr" name="layoutDirection" />
+
   <public type="attr" name="paddingStart"/>
   <public type="attr" name="paddingEnd"/>
 
diff --git a/core/res/res/values/styles.xml b/core/res/res/values/styles.xml
index 610bad8..569be90 100644
--- a/core/res/res/values/styles.xml
+++ b/core/res/res/values/styles.xml
@@ -528,11 +528,11 @@
     </style>
 
     <style name="Widget.TimePicker">
-        <item name="android:layout">@android:layout/time_picker</item>
+        <item name="android:internalLayout">@android:layout/time_picker</item>
     </style>
 
     <style name="Widget.DatePicker">
-        <item name="android:layout">@android:layout/date_picker</item>
+        <item name="android:internalLayout">@android:layout/date_picker</item>
         <item name="android:calendarViewShown">false</item>
     </style>
 
@@ -1656,16 +1656,16 @@
         <item name="android:flingable">true</item>
         <item name="android:selectionDivider">@android:drawable/numberpicker_selection_divider</item>
         <item name="android:selectionDividerHeight">2dip</item>
-        <item name="android:minWidth">48dip</item>
-        <item name="android:maxHeight">200dip</item>
+        <item name="android:internalMinWidth">48dip</item>
+        <item name="android:internalMaxHeight">200dip</item>
     </style>
 
     <style name="Widget.Holo.TimePicker" parent="Widget.TimePicker">
-        <item name="android:layout">@android:layout/time_picker_holo</item>
+        <item name="android:internalLayout">@android:layout/time_picker_holo</item>
     </style>
 
     <style name="Widget.Holo.DatePicker" parent="Widget.DatePicker">
-        <item name="android:layout">@android:layout/date_picker_holo</item>
+        <item name="android:internalLayout">@android:layout/date_picker_holo</item>
         <item name="android:calendarViewShown">true</item>
     </style>
 
diff --git a/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/ConnectivityManagerTestActivity.java b/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/ConnectivityManagerTestActivity.java
index d375d4c..259f15f 100644
--- a/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/ConnectivityManagerTestActivity.java
+++ b/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/ConnectivityManagerTestActivity.java
@@ -94,6 +94,7 @@
      * Control Wifi States
      */
     public WifiManager mWifiManager;
+    public WifiManager.Channel mChannel;
 
     /*
      * Verify connectivity state
@@ -240,7 +241,7 @@
         mCM = (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE);
         // Get an instance of WifiManager
         mWifiManager =(WifiManager)getSystemService(Context.WIFI_SERVICE);
-        mWifiManager.asyncConnect(this, new WifiServiceHandler());
+        mChannel = mWifiManager.initialize(mContext, mContext.getMainLooper(), null);
 
         initializeNetworkStates();
 
@@ -594,7 +595,14 @@
                         log("found " + ssid + " in the scan result list");
                         log("retry: " + retry);
                         foundApInScanResults = true;
-                        mWifiManager.connectNetwork(config);
+                        mWifiManager.connect(mChannel, config,
+                                new WifiManager.ActionListener() {
+                                    public void onSuccess() {
+                                    }
+                                    public void onFailure(int reason) {
+                                        log("connect failure " + reason);
+                                    }
+                                });
                         break;
                    }
                 }
@@ -641,7 +649,13 @@
         for (WifiConfiguration wifiConfig: wifiConfigList) {
             log("remove wifi configuration: " + wifiConfig.networkId);
             int netId = wifiConfig.networkId;
-            mWifiManager.forgetNetwork(netId);
+            mWifiManager.forget(mChannel, netId, new WifiManager.ActionListener() {
+                    public void onSuccess() {
+                    }
+                    public void onFailure(int reason) {
+                        log("Failed to forget " + reason);
+                    }
+                });
         }
         return true;
     }
diff --git a/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/functional/WifiConnectionTest.java b/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/functional/WifiConnectionTest.java
index d33a445..8d73bc0 100644
--- a/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/functional/WifiConnectionTest.java
+++ b/core/tests/ConnectivityManagerTest/src/com/android/connectivitymanagertest/functional/WifiConnectionTest.java
@@ -63,6 +63,7 @@
     private ConnectivityManagerTestActivity mAct;
     private ConnectivityManagerTestRunner mRunner;
     private WifiManager mWifiManager = null;
+    private WifiManager.Channel mChannel;
     private Set<WifiConfiguration> enabledNetworks = null;
 
     public WifiConnectionTest() {
@@ -76,7 +77,8 @@
         mWifiManager = (WifiManager) mRunner.getContext().getSystemService(Context.WIFI_SERVICE);
 
         mAct = getActivity();
-        mWifiManager.asyncConnect(mAct, new WifiServiceHandler());
+        mChannel = mWifiManager.initialize(mAct, mAct.getMainLooper(), null);
+
         networks = mAct.loadNetworkConfigurations();
         if (DEBUG) {
             printNetworkConfigurations();
diff --git a/core/tests/bandwidthtests/src/com/android/bandwidthtest/util/ConnectionUtil.java b/core/tests/bandwidthtests/src/com/android/bandwidthtest/util/ConnectionUtil.java
index 8d778c4..c3cc7c5 100644
--- a/core/tests/bandwidthtests/src/com/android/bandwidthtest/util/ConnectionUtil.java
+++ b/core/tests/bandwidthtests/src/com/android/bandwidthtest/util/ConnectionUtil.java
@@ -59,7 +59,7 @@
     private static final int WAIT_FOR_SCAN_RESULT = 10 * 1000; // 10 seconds
     private static final int WIFI_SCAN_TIMEOUT = 50 * 1000;
     public static final int SHORT_TIMEOUT = 5 * 1000;
-    public static final int LONG_TIMEOUT = 120 * 1000; // 2 minutes
+    public static final int LONG_TIMEOUT = 5 * 60 * 1000; // 5 minutes
     private ConnectivityReceiver mConnectivityReceiver = null;
     private WifiReceiver mWifiReceiver = null;
     private DownloadReceiver mDownloadReceiver = null;
@@ -74,6 +74,7 @@
     private int mWifiState;
     private NetworkInfo mWifiNetworkInfo;
     private WifiManager mWifiManager;
+    private WifiManager.Channel mChannel;
     private Context mContext;
     // Verify connectivity state
     private static final int NUM_NETWORK_TYPES = ConnectivityManager.MAX_NETWORK_TYPE + 1;
@@ -114,7 +115,7 @@
 
         // Get an instance of WifiManager
         mWifiManager =(WifiManager)mContext.getSystemService(Context.WIFI_SERVICE);
-        mWifiManager.asyncConnect(mContext, new WifiServiceHandler());
+        mChannel = mWifiManager.initialize(mContext, mContext.getMainLooper(), null);
 
         mDownloadManager = (DownloadManager)mContext.getSystemService(Context.DOWNLOAD_SERVICE);
 
@@ -458,7 +459,13 @@
                 if (mNetworkInfo == null) {
                     Log.v(LOG_TAG, "Do not have networkInfo! Force fetch of network info.");
                     mNetworkInfo = mCM.getActiveNetworkInfo();
-                    Assert.assertNotNull(mNetworkInfo);
+                }
+                // Still null after force fetch? Maybe the network did not have time to be brought
+                // up yet.
+                if (mNetworkInfo == null) {
+                    Log.v(LOG_TAG, "Failed to force fetch networkInfo. " +
+                            "The network is still not ready. Wait for the next broadcast");
+                    continue;
                 }
                 if ((mNetworkInfo.getType() != networkType) ||
                         (mNetworkInfo.getState() != expectedState)) {
@@ -567,7 +574,14 @@
                         Log.v(LOG_TAG, "Found " + ssid + " in the scan result list.");
                         Log.v(LOG_TAG, "Retry: " + retry);
                         foundApInScanResults = true;
-                        mWifiManager.connectNetwork(config);
+                        mWifiManager.connect(mChannel, config, new WifiManager.ActionListener() {
+                                public void onSuccess() {
+                                }
+                                public void onFailure(int reason) {
+                                    Log.e(LOG_TAG, "connect failed " + reason);
+                                }
+                            });
+
                         break;
                     }
                 }
@@ -614,7 +628,13 @@
         for (WifiConfiguration wifiConfig: wifiConfigList) {
             Log.v(LOG_TAG, "Remove wifi configuration: " + wifiConfig.networkId);
             int netId = wifiConfig.networkId;
-            mWifiManager.forgetNetwork(netId);
+            mWifiManager.forget(mChannel, netId, new WifiManager.ActionListener() {
+                    public void onSuccess() {
+                    }
+                    public void onFailure(int reason) {
+                        Log.e(LOG_TAG, "forget failed " + reason);
+                    }
+                });
         }
         return true;
     }
@@ -723,4 +743,4 @@
         }
         return false;
     }
-}
\ No newline at end of file
+}
diff --git a/core/tests/coretests/src/android/webkit/ZoomManagerTest.java b/core/tests/coretests/src/android/webkit/ZoomManagerTest.java
index 1c9defe..7e0e0b2 100644
--- a/core/tests/coretests/src/android/webkit/ZoomManagerTest.java
+++ b/core/tests/coretests/src/android/webkit/ZoomManagerTest.java
@@ -24,8 +24,9 @@
     @Override
     public void setUp() {
         WebView webView = new WebView(this.getContext());
-        CallbackProxy callbackProxy = new CallbackProxy(this.getContext(), webView);
-        zoomManager = new ZoomManager(webView, callbackProxy);
+        WebViewClassic webViewClassic = WebViewClassic.fromWebView(webView);
+        CallbackProxy callbackProxy = new CallbackProxy(this.getContext(), webViewClassic);
+        zoomManager = new ZoomManager(webViewClassic, callbackProxy);
 
         zoomManager.init(1.00f);
     }
diff --git a/docs/html/guide/appendix/install-location.jd b/docs/html/guide/appendix/install-location.jd
index 292d3e7..e5ed226 100644
--- a/docs/html/guide/appendix/install-location.jd
+++ b/docs/html/guide/appendix/install-location.jd
@@ -174,7 +174,7 @@
   <dt>Copy Protection</dt>
     <dd>Your application cannot be installed to a device's SD card if it uses Android Market's 
       Copy Protection feature. However, if you use Android Market's 
-      <a href="{@docRoot}guide/publishing/licensing.html">Application Licensing</a> instead, your 
+      <a href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a> instead, your 
       application <em>can</em> be installed to internal or external storage, including SD cards.</dd>
 </dl>
 
diff --git a/docs/html/guide/developing/devices/emulator.jd b/docs/html/guide/developing/devices/emulator.jd
index 02dcb68..c217790 100644
--- a/docs/html/guide/developing/devices/emulator.jd
+++ b/docs/html/guide/developing/devices/emulator.jd
@@ -78,7 +78,7 @@
 applications. You can choose what version of the Android system you want to
 run in the emulator by configuring AVDs, and you can also customize the
 mobile device skin and key mappings. When launching the emulator and at runtime,
-you can use a variety of commands and options to control the its behaviors.
+you can use a variety of commands and options to control its behavior.
 </p>
 
 <p>The Android system image distributed in the SDK contains ARM machine code for
diff --git a/docs/html/guide/developing/tools/emulator.jd b/docs/html/guide/developing/tools/emulator.jd
index 5151ec1..09e41c3 100644
--- a/docs/html/guide/developing/tools/emulator.jd
+++ b/docs/html/guide/developing/tools/emulator.jd
@@ -516,7 +516,7 @@
   </tr>
   <tr>
     <td>Audio volume up button</td>
-    <td>KEYPAD_PLUS, Ctrl-5</td>
+    <td>KEYPAD_PLUS, Ctrl-F5</td>
   </tr>
 
   <tr>
diff --git a/docs/html/guide/developing/tools/proguard.jd b/docs/html/guide/developing/tools/proguard.jd
index eca262a..ea8a1ea 100644
--- a/docs/html/guide/developing/tools/proguard.jd
+++ b/docs/html/guide/developing/tools/proguard.jd
@@ -39,7 +39,7 @@
   sized <code>.apk</code> file that is more difficult to reverse engineer. Because ProGuard makes your
   application harder to reverse engineer, it is important that you use it
   when your application utilizes features that are sensitive to security like when you are
-  <a href="{@docRoot}guide/publishing/licensing.html">Licensing Your Applications</a>.</p>
+  <a href="{@docRoot}guide/market/licensing/index.html">Licensing Your Applications</a>.</p>
 
   <p>ProGuard is integrated into the Android build system, so you do not have to invoke it
   manually. ProGuard runs only when you build your application in release mode, so you do not 
diff --git a/docs/html/guide/guide_toc.cs b/docs/html/guide/guide_toc.cs
index 4a9a684..fd2ec93 100644
--- a/docs/html/guide/guide_toc.cs
+++ b/docs/html/guide/guide_toc.cs
@@ -451,8 +451,24 @@
       <li><a href="<?cs var:toroot ?>guide/publishing/publishing.html">
           <span class="en">Publishing on Android Market</span>
           </a></li>
-      <li><a href="<?cs var:toroot ?>guide/publishing/licensing.html">
+      <li class="toggle-list">
+        <div><a href="<?cs var:toroot ?>guide/market/licensing/index.html">
           <span class="en">Application Licensing</span></a>
+        </div>
+        <ul>
+          <li><a href="<?cs var:toroot?>guide/market/licensing/overview.html">
+              <span class="en">Licensing Overview</span></a>
+          </li>
+          <li><a href="<?cs var:toroot?>guide/market/licensing/setting-up.html">
+              <span class="en">Setting Up for Licensing</span></a>
+          </li>
+          <li><a href="<?cs var:toroot?>guide/market/licensing/adding-licensing.html">
+              <span class="en">Adding Licensing to Your App</span></a>
+          </li>
+          <li><a href="<?cs var:toroot?>guide/market/licensing/licensing-reference.html">
+              <span class="en">Licensing Reference</span></a>
+          </li>
+        </ul>
       </li>
       <li class="toggle-list">
         <div><a href="<?cs var:toroot?>guide/market/billing/index.html">
@@ -485,6 +501,10 @@
       <li><a href="<?cs var:toroot ?>guide/market/publishing/multiple-apks.html">
           <span class="en">Multiple APK Support</span></a>
       </li>
+      <li><a href="<?cs var:toroot ?>guide/market/expansion-files.html">
+          <span class="en">APK Expansion Files</span></a>
+          <span class="new">new!</span>
+      </li>
     </ul>
   </li>
 
diff --git a/docs/html/guide/market/expansion-files.jd b/docs/html/guide/market/expansion-files.jd
new file mode 100644
index 0000000..5aaf9f1
--- /dev/null
+++ b/docs/html/guide/market/expansion-files.jd
@@ -0,0 +1,1267 @@
+page.title=APK Expansion Files
+@jd:body
+
+
+<div id="qv-wrapper">
+<div id="qv">
+<h2>Quickview</h2>
+<ul>
+  <li>Recommended for most apps that exceed the 50MB APK limit</li>
+  <li>You can provide up to 4GB of additional data for each APK</li>
+  <li>Android Market hosts and serves the expansion files at no charge</li>
+  <li>The files can be any file type you want and are saved to the device's shared storage</li>
+</ul>
+
+<h2>In this document</h2>
+<ol>
+  <li><a href="#Overview">Overview</a>
+    <ol>
+      <li><a href="#Filename">File name format</a></li>
+      <li><a href="#StorageLocation">Storage location</a></li>
+      <li><a href="#DownloadProcess">Download process</a></li>
+      <li><a href="#Checklist">Development checklist</a></li>
+    </ol>
+  </li>
+  <li><a href="#Rules">Rules and Limitations</a></li>
+  <li><a href="#Downloading">Downloading the Expansion Files</a>
+    <ol>
+      <li><a href="#AboutLibraries">About the Downloader Library</a></li>
+      <li><a href="#Preparing">Preparing to use the Downloader Library</a></li>
+      <li><a href="#Permissions">Declaring user permissions</a></li>
+      <li><a href="#DownloaderService">Implementing the downloader service</a></li>
+      <li><a href="#AlarmReceiver">Implementing the alarm receiver</a></li>
+      <li><a href="#Download">Starting the download</a></li>
+      <li><a href="#Progress">Receiving download progress</a></li>
+    </ol>
+  </li>
+  <li><a href="#ExpansionPolicy">Using APKExpansionPolicy</a></li>
+  <li><a href="#ReadingTheFile">Reading the Expansion File</a>
+    <ol>
+      <li><a href="#GettingFilenames">Getting the file names</a></li>
+      <li><a href="#ZipLib">Using the APK Expansion Zip Library</a></li>
+    </ol>
+  </li>
+  <li><a href="#Testing">Testing Your Expansion Files</a>
+    <ol>
+      <li><a href="#TestingReading">Testing file reads</a></li>
+      <li><a href="#TestingReading">Testing file downloads</a></li>
+    </ol>
+  </li>
+  <li><a href="#Updating">Updating Your Application</a></li>
+</ol>
+
+<h2>See also</h2>
+<ol>
+  <li><a href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a></li>
+  <li><a href="{@docRoot}guide/market/publishing/multiple-apks.html">Multiple
+APK Support</a></li>
+</ol>
+</div>
+</div>
+
+
+
+<p>Android Market currently requires that your APK file be no more than 50MB. For most
+applications, this is plenty of space for all the application's code and assets.
+However, some apps need more space for high-fidelity graphics, media files, or other large assets.
+Previously, if your app exceeded 50MB, you had to host and download the additional resources
+yourself when the user opens the app. Hosting and serving the extra files can be costly, and the
+user experience is often less than ideal. To make this process easier for you and more pleasant
+for users, Android Market allows you to attach two large expansion files that supplement your
+APK.</p>
+
+<p>Android Market hosts the expansion files for your application and serves them to the device at
+no cost to you. The expansion files are saved to the device's shared storage location (the
+SD card or USB-mountable partition; also known as the "external" storage) where your app can access
+them. On most devices, Android Market downloads the expansion file(s) at the same time it
+downloads the APK, so your application has everything it needs when the user opens it for the
+first time. In some cases, however, your application must download the files from Android Market
+when your application starts.</p>
+
+
+
+<h2 id="Overview">Overview</h2>
+
+<p>Each time you upload an APK using the Android Market Developer Console, you have the option to
+add one or two expansion files to the APK. Each file can be up to 2GB and it can be any format you
+choose, but we recommend you use a compressed file to conserve bandwidth during the download.
+Conceptually, each expansion file plays a different role:</p>
+
+<ul>
+  <li>The <strong>main</strong> expansion file is the
+primary expansion file for additional resources required by your application.</li>
+  <li>The <strong>patch</strong> expansion file is optional and intended for small updates to the
+main expansion file.</li>
+</ul>
+
+<p>While you can use the two expansion files any way you wish, we recommend that the main
+expansion file deliver the primary assets and should rarely if ever updated; the patch expansion
+file should be smaller and serve as a “patch carrier,” getting updated with each major
+release or as necessary.</p>
+
+<p>However, even if your application update requires only a new patch expansion file, you still must
+upload a new APK with an updated <a
+href="{@docRoot}guide/topics/manifest/manifest-element.html#vcode">{@code
+versionCode}</a> in the manifest. (The Android Market
+Developer Console does not allow you to upload an expansion file to an existing APK.)</p>
+
+<p class="note"><strong>Note:</strong> The patch expansion file is semantically the same as the
+main expansion file&mdash;you can use each file any way you want. The system does
+not use the patch expansion file to perform patching for your app. You must perform patching
+yourself or be able to distinguish between the two files.</p>
+
+
+
+<h3 id="Filename">File name format</h3>
+
+<p>Each expansion file you upload can be any format you choose (ZIP, PDF, MP4, etc.). Regardless of
+the file type, Android Market considers them opaque binary blobs and renames the files
+using the following scheme:</p>
+
+<pre class="classic no-pretty-print">
+[main|patch].&lt;expansion-version&gt;.&lt;package-name&gt;.obb
+</pre>
+
+<p>There are three components to this scheme:</p>
+
+<dl>
+  <dt>{@code main} or {@code patch}</dt>
+    <dd>Specifies whether the file is the main or patch expansion file. There can be
+only one main file and one patch file for each APK.</dd>
+  <dt>{@code &lt;expansion-version&gt;}</dt>
+    <dd>This is an integer that matches the version code of the APK with which the expansion is
+<em>first</em> associated (it matches the application's <a
+href="{@docRoot}guide/topics/manifest/manifest-element.html#vcode">{@code android:versionCode}</a>
+value).
+    <p>"First" is emphasized because although the Android Market Developer Console allows you to
+re-use an uploaded expansion file with a new APK, the expansion file's name does not change&mdash;it
+retains the version applied to it when you first uploaded the file.</p></dd>
+  <dt>{@code &lt;package-name&gt;}</dt> 
+    <dd>Your application's Java-style package name.</dd>
+</dl>
+
+<p>For example, suppose your APK version is 314159 and your package name is com.example.app. If you
+upload a main expansion file, the file is renamed to:</p>
+<pre class="classic no-pretty-print">main.314159.com.example.app.obb</pre>
+
+
+<h3 id="StorageLocation">Storage location</h3>
+
+<p>When Android Market downloads your expansion files to a device, it saves them to the system's
+shared storage location. To ensure proper behavior, you must not delete, move, or rename the
+expansion files. In the event that your application must perform the download from Android Market
+itself, you must save the files to the exact same location.</p>
+
+<p>The specific location for your expansion files is:</p>
+
+<pre class="classic no-pretty-print">
+&lt;shared-storage&gt;/Android/obb/&lt;package-name&gt;/
+</pre>
+
+<ul>
+  <li>{@code &lt;shared-storage&gt;} is the path to the shared storage space, available from
+{@link android.os.Environment#getExternalStorageDirectory()}.</li>
+  <li>{@code &lt;package-name&gt;} is your application's Java-style package name, available
+from {@link android.content.Context#getPackageName()}.</li>
+</ul>
+
+<p>For each application, there are never more than two expansion files in this directory.
+One is the main expansion file and the other is the patch expansion file (if necessary). Previous
+versions are overwritten when you update your application with new expansion files.</p>
+
+<p>If you must unpack the contents of your expansion files, <strong>do not</strong> delete the
+{@code .obb} expansion files afterwards and <strong>do not</strong> save the unpacked data
+in the same directory. You should save your unpacked files in the directory
+specified by {@link android.content.Context#getExternalFilesDir getExternalFilesDir()}. However,
+if possible, it's best if you use an expansion file format that allows you to read directly from
+the file instead of requiring you to unpack the data. For example, we've provided a library
+project called the <a href="#ZipLib">APK Expansion Zip Library</a> that reads your data directly
+from the ZIP file.</p>
+
+<p class="note"><strong>Note:</strong> Unlike APK files, any files saved on the shared storage can
+be read by the user and other applications.</p>
+
+<p class="note"><strong>Tip:</strong> If you're packaging media files into a ZIP, you can use media
+playback calls on the files with offset and length controls (such as {@link
+android.media.MediaPlayer#setDataSource(FileDescriptor,long,long) MediaPlayer.setDataSource()} and
+{@link android.media.SoundPool#load(FileDescriptor,long,long,int) SoundPool.load()}) without the
+need to unpack your ZIP. In order for this to work, you must not perform additional compression on
+the media files when creating the ZIP packages. For example, when using the <code>zip</code> tool,
+you should use the <code>-n</code> option to specify the file suffixes that should not be
+compressed: <br/>
+<code>zip -n .mp4;.ogg main_expansion media_files</code></p>
+
+
+<h3 id="DownloadProcess">Download process</h3>
+
+<p>Most of the time, Android Market downloads and saves your expansion files at the same time it
+downloads the APK to the device. However, in some cases Android Market
+cannot download the expansion files or the user might have deleted previously downloaded expansion
+files. To handle these situations, your app must be able to download the files
+itself when the main activity starts, using a URL provided by Android Market.</p>
+
+<p>The download process from a high level looks like this:</p>
+
+<ol>
+  <li>User selects to install your app from Android Market.</li>
+  <li>If Android Market is able to download the expansion files (which is the case for most
+devices), it downloads them along with the APK.
+     <p>If Android Market is unable to download the expansion files, it downloads the
+APK only.</p>
+  </li>
+  <li>When the user launches your application, your app must check whether the expansion files are
+already saved on the device.
+    <ol>
+      <li>If yes, your app is ready to go.</li>
+      <li>If no, your app must download the expansion files over HTTP from Android Market. Your app
+must send a request to the Android Market client using the Android Market's <a
+href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a> service, which
+responds with the name, file size, and URL for each expansion file. With this information, you then
+download the files and save them to the proper <a href="#StorageLocation">storage location</a>.</li>
+    </ol>
+  </li>
+</ol>
+
+<p class="caution"><strong>Caution:</strong> It is critical that you include the necessary code to
+download the expansion files from Android Market in the event that the files are not already on the
+device when your application starts. As discussed in the following section about <a
+href="#Downloading">Downloading the Expansion Files</a>, we've made a library available to you that
+greatly simplifies this process and performs the download from a service with a minimal amount of
+code from you.</p>
+
+
+
+
+<h3 id="Checklist">Development checklist</h3>
+
+<p>Here's a summary of the tasks you should perform to use expansion files with your
+application:</p>
+
+<ol>
+  <li>First determine whether your application absolutely requires more than 50MB per installation.
+Space is precious and you should keep your total application size as small as possible. If your app
+uses more than 50MB in order to provide multiple versions of your graphic assets for multiple screen
+densities, consider instead publishing <a
+href="{@docRoot}guide/market/publishing/multiple-apks.html">multiple APKs</a> in which each APK
+contains only the assets required for the screens that it targets.</li>
+  <li>Determine which application resources to separate from your APK and package them in a
+file to use as the main expansion file.
+    <p>Normally, you should only use the second patch expansion file when performing updates to
+the main expansion file. However, if your resources exceed the 2GB limit for the main
+expansion file, you can use the patch file for the rest of your assets.</p>
+  </li>
+  <li>Develop your application such that it uses the resources from your expansion files in the
+device's <a href="#StorageLocation">shared storage location</a>.
+    <p>Remember that you must not delete, move, or rename the expansion files.</p>
+    <p>If your application doesn't demand a specific format, we suggest you create ZIP files for 
+your expansion files, then read them using the <a href="#ZipLib">APK Expansion Zip
+Library</a>.</p>
+  </li>
+  <li>Add logic to your application's main activity that checks whether the expansion files
+are on the device upon start-up. If the files are not on the device, use Android Market's <a
+href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a> service to request URLs
+for the expansion files, then download and save them.
+    <p>To greatly reduce the amount of code you must write and ensure a good user experience
+during the download, we recommend you use the <a href="AboutLibraries">Downloader
+Library</a> to implement your download behavior.</p>
+    <p>If you build your own download service instead of using the library, be aware that you
+must not change the name of the expansion files and must save them to the proper
+<a href="#StorageLocation">storage location</a>.</p></li>
+</ol>
+
+<p>Once you've finished your application development, follow the guide to <a href="#Testing">Testing
+Your Expansion Files</a>.</p>
+
+
+
+
+
+
+<h2 id="Rules">Rules and Limitations</h2>
+
+<p>Adding APK expansion files is a feature available when you upload your application using the
+Android Market Developer Console. When uploading your application for the first time or updating an
+application that uses expansion files, you must be aware of the following rules and limitations:</p>
+
+<ol type="I">
+  <li>Each expansion file can be no more than 2GB.</li>
+  <li>In order to download your expansion files from Android Market, <strong>the user must have
+acquired your application from Android Market</strong>. Android Market will not
+provide the URLs for your expansion files if the application was installed by other means.</li>
+  <li>When performing the download from within your application, the URL that Android Market
+provides for each file is unique for every download and each one expires shortly after it is given
+to your application.</li>
+  <li>If you update your application with a new APK or upload <a
+href="{@docRoot}guide/market/publishing/multiple-apks.html">multiple APKs</a> for the same
+application, you can select expansion files that you've uploaded for a previous APK. <strong>The
+expansion file's name does not change</strong>&mdash;it retains the version received by the APK to
+which the file was originally associated.</li>
+  <li>If you use expansion files in combination with <a
+href="{@docRoot}guide/market/publishing/multiple-apks.html">multiple APKs</a> in order to
+provide different expansion files for different devices, you still must upload separate APKs
+for each device in order to provide a unique  <a
+href="{@docRoot}guide/topics/manifest/manifest-element.html#vcode">{@code versionCode}</a>
+value and declare different <a href="{@docRoot}guide/appendix/market-filters.html">filters</a> for
+each APK.</li>
+  <li>You cannot issue an update to your application by changing the expansion files
+alone&mdash;<strong>you must upload a new APK</strong> to update your app. If your changes only
+concern the assets in your expansion files, you can update your APK simply by changing the <a
+href="{@docRoot}guide/topics/manifest/manifest-element.html#vcode">{@code versionCode}</a> (and
+perhaps also the <a href="{@docRoot}guide/topics/manifest/manifest-element.html#vname">{@code
+versionName}</a>).</p></li>
+  <li><strong>Do not save other data into your <code>obb/</code>
+directory</strong>. If you must unpack some data, save it into the location specified by {@link
+android.content.Context#getExternalFilesDir getExternalFilesDir()}.</li>
+  <li><strong>Do not delete or rename the {@code .obb} expansion file</strong> (unless you're
+performing an update). Doing so will cause Android Market (or your app itself) to repeatedly
+download the expansion file.</li>
+  <li>When updating an expansion file manually, you must delete the previous expansion file.</li>
+</ol>
+
+
+
+
+
+
+
+
+
+<h2 id="Downloading">Downloading the Expansion Files</h2>
+
+<p>In most cases, Android Market downloads and saves your expansion files to the device at the same
+time it installs or updates the APK. This way, the expansion files are available when your
+application launches for the first time. However, in some cases your app must download the
+expansion files itself by requesting them from a URL provided to you in a response
+from Android Market's <a
+href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a> service.</p>
+
+<p>The basic logic you need to download your expansion files is the following:</p>
+
+<ol>
+  <li>When your application starts, look for the expansion files on the <a
+href="#StorageLocation">shared storage location</a> (in the
+<code>Android/obb/&lt;package-name&gt;/</code> directory).
+    <ol type="a">
+      <li>If the expansion files are there, you're all set and your application can continue.</li>
+      <li>If the expansion files are <em>not</em> there:
+        <ol>
+          <li>Perform a request using Android Market's <a
+href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a> to get your
+app's expansion file names, sizes, and URLs.</li> 
+          <li>Use the URLs provided by Android Market to download the expansion files and save
+the expansion files. You <strong>must</strong> save the files to the <a
+href="#StorageLocation">shared storage location</a>
+(<code>Android/obb/&lt;package-name&gt;/</code>) and use the exact file name provided
+by Android Market's response.
+            <p class="note"><strong>Note:</strong> The URL that Android Market provides for your
+expansion files is unique for every download and each one expires shortly after it is given to
+your application.</p>
+          </li>
+        </ol>
+      </li>
+    </ol>
+  </li>
+</ol>
+
+
+<p>If your application is free (not a paid app), then you probably haven't used the <a
+href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a> service. It's primarily
+designed for you to enforce
+licensing policies for your application and ensure that the user has the right to
+use your app (he or she rightfully paid for it on Android Market). In order to facilitate the
+expansion file functionality, the licensing service has been enhanced to provide a response
+to your application that includes the URL of your application's expansion files that are hosted
+on Android Market. So, even if your application is free for users, you need to include the Android
+Market License Verification Library (LVL) to use APK expansion files. Of course, if your application
+is free, you don't need to enforce license verification&mdash;you simply need the
+library to perform the request that returns the URL of your expansion files.</p>
+
+<p class="note"><strong>Note:</strong> Whether your application is free or not, Android Market
+returns the expansion file URLs only if the user acquired your application from Android Market.</p>
+
+<p>In addition to the LVL, you need a set of code that downloads the expansion files
+over an HTTP connection and saves them to the proper location on the device's shared storage.
+As you build this procedure into your application, there are several issues you should take into
+consideration:</p>
+
+<ul>
+  <li>The device might not have enough space for the expansion files, so you should check
+before beginning the download and warn the user if there's not enough space.</li>
+  <li>File downloads should occur in a background service in order to avoid blocking the user
+interaction and allow the user to leave your app while the download completes.</li>
+  <li>A variety of errors might occur during the request and download that you must
+gracefully handle.</li>
+  <li>Network connectivity can change during the download, so you should handle such changes and
+if interrupted, resume the download when possible.</li>
+  <li>While the download occurs in the background, you should provide a notification that
+indicates the download progress, notifies the user when it's done, and takes the user back to
+your application when selected.</li>
+</ul>
+
+
+<p>To simplify this work for you, we've built the <a href="#AboutLibraries">Downloader Library</a>,
+which requests the expansion file URLs through the licensing service, downloads the expansion files,
+performs all of the tasks listed above, and even allows your activity to pause and resume the
+download. By adding the Downloader Library and a few code hooks to your application, almost all the
+work to download the expansion files is already coded for you. As such, in order to provide the best
+user experience with minimal effort on your behalf, we recommend you use the Downloader Library to
+download your expansion files. The information in the following sections explain how to integrate
+the library into your application.</p>
+
+<p>If you'd rather develop your own solution to download the expansion files using the Android
+Market URLs, you must follow the <a href="{@docRoot}guide/market/licensing/index.html">Application
+Licensing</a> documentation to perform a license request, then retrieve the expansion file names,
+sizes, and URLs from the response extras. You should use the <a href="#ExpansionPolicy">{@code
+APKExpansionPolicy}</a> class (included in the License Verification Library) as your licensing
+policy, which captures the expansion file names, sizes, and URLs from the licensing service..</p>
+
+
+
+<h3 id="AboutLibraries">About the Downloader Library</h3>
+
+<p>To use APK expansion files with your application and provide the best user experience with
+minimal effort on your behalf, we recommend you use the Downloader Library that's included in the
+Android Market APK Expansion Library package. This library downloads your expansion files in a
+background service, shows a user notification with the download status, handles network
+connectivity loss, resumes the download when possible, and more.</p>
+
+<p>To implement expansion file downloads using the Downloader Library, all you need to do is:</p>
+
+<ul>
+  <li>Extend a special {@link android.app.Service} subclass and {@link
+android.content.BroadcastReceiver} subclass that each require just a few
+lines of code from you.</li>
+  <li>Add some logic to your main activity that checks whether the expansion files have
+already been downloaded and, if not, invokes the download process and displays a
+progress UI.</li>
+  <li>Implement a callback interface with a few methods in your main activity that
+receives updates about the download progress.</li>
+</ul>
+
+<p>The following sections explain how to set up your app using the Downloader Library.</p>
+
+
+<h3 id="Preparing">Preparing to use the Downloader Library</h3>
+
+<p>To use the Downloader Library, you need to
+download two packages from the SDK Manager and add the appropriate libraries to your
+application.</p>
+
+<p>First, open the Android SDK Manager, expand <em>Extras</em> and download:</p>
+<ul>
+  <li><em>Google Market Licensing package</em></li>
+  <li><em>Google Market APK Expansion Library package</em></li>
+</ul>
+
+<p>If you're using Eclipse, create a project for each library and add it to your app:</p>
+<ol>
+  <li>Create a new Library Project for the License Verification Library and Downloader
+Library. For each library:
+    <ol>
+      <li>Begin a new Android project.</li>
+      <li>Select <strong>Create project from existing
+source</strong> and choose the library from the {@code &lt;sdk&gt;/extras/google/} directory
+({@code market_licensing/} for the License Verification Library or {@code
+market_apk_expansion/downloader_library/} for the Downloader Library).</li>
+      <li>Specify a <em>Project Name</em> such as "Android Market License Library" and "Market
+Downloader
+Library"</li>
+      <li>Click <strong>Finish</strong>.</li>
+    </ol>
+<p class="note"><strong>Note:</strong> The Downloader Library depends on the License
+Verification Library. Be sure to add the License
+Verification Library to the Downloader Library's project properties (same process as
+steps 2 and 3 below).</p>
+  </li>
+  <li>Right-click the Android project in which you want to use APK expansion files and
+select <strong>Properties</strong>.</li>
+  <li>In the <em>Library</em> panel, click <strong>Add</strong> to select and add each of the
+libraries to your application.</li>
+</ol>
+
+<p>Or, from a command line, update your project to include the libraries:</p>
+<ol>
+  <li>Change directories to the <code>&lt;sdk&gt;/tools/</code> directory.</li>
+  <li>Execute <code>android update project</code> with the {@code --library} option to add both the
+LVL and the Downloader Library to your project. For example:
+<pre class="no-pretty-print">
+android update project --path ~/Android/MyApp \
+--library ~/android_sdk/extras/google/market_licensing \
+--library ~/android_sdk/extras/google/market_apk_expansion/downloader_library
+</pre>
+  </li>
+</ol>
+
+<p>With both the License Verification Library and Downloader Library added to your
+application, you'll be able to quickly integrate the ability to download expansion files from
+Android Market. The format that you choose for the expansion files and how you read them
+from the shared storage is a separate implementation that you should consider based on your
+application needs.</p>
+
+<p class="note"><strong>Tip:</strong> The APK Expansion Library package includes a sample
+application
+that shows how to use the Downloader Library in an app. The sample uses a third library
+available in the APK Expansion Library package called the APK Expansion Zip Library. If
+you plan on
+using ZIP files for your expansion files, we suggest you also add the APK Expansion Zip Library to
+your application. For more information, see the section below
+about <a href="#ZipLib">Using the APK Expansion Zip Library</a>.</p>
+
+
+
+<h3 id="Permissions">Declaring user permissions</h3>
+
+<p>In order to download the expansion files, the Downloader Library
+requires several permissions that you must declare in your application's manifest file. They
+are:</p>
+
+<pre>
+&lt;manifest ...>
+    &lt;!-- Required to access Android Market Licensing -->
+    &lt;uses-permission android:name="com.android.vending.CHECK_LICENSE" />
+
+    &lt;!-- Required to download files from Android Market -->
+    &lt;uses-permission android:name="android.permission.INTERNET" />
+
+    &lt;!-- Required to keep CPU alive while downloading files (NOT to keep screen awake) -->
+    &lt;uses-permission android:name="android.permission.WAKE_LOCK" />
+
+    &lt;!-- Required to poll the state of the network connection and respond to changes -->
+    &lt;uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
+
+    &lt;!-- Required to check whether Wi-Fi is enabled -->
+    &lt;uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
+
+    &lt;!-- Required to read and write the expansion files on shared storage -->
+    &lt;uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
+    ...
+&lt;/manifest>
+</pre>
+
+<p class="note"><strong>Note:</strong> By default, the Downloader Library requires API
+level 4, but the APK Expansion Zip Library requires API level 5.</p>
+
+
+<h3 id="DownloaderService">Implementing the downloader service</h3>
+
+<p>In order to perform downloads in the background, the Downloader Library provides its
+own {@link android.app.Service} subclass called {@code DownloaderService} that you should extend. In
+addition to downloading the expansion files for you, the {@code DownloaderService} also:</p>
+
+<ul>
+  <li>Registers a {@link android.content.BroadcastReceiver} that listens for changes to the
+device's network connectivity (the {@link android.net.ConnectivityManager#CONNECTIVITY_ACTION}
+broadcast) in order to pause the download when necessary (such as due to connectivity loss) and
+resume the download when possible (connectivity is acquired).</li>
+  <li>Schedules an {@link android.app.AlarmManager#RTC_WAKEUP} alarm to retry the download for
+cases in which the service gets killed.</li>
+  <li>Builds a custom {@link android.app.Notification} that displays the download progress and
+any errors or state changes.</li>
+  <li>Allows your application to manually pause and resume the download.</li>
+  <li>Verifies that the shared storage is mounted and available, that the files don't already exist,
+and that there is enough space, all before downloading the expansion files. Then notifies the user
+if any of these are not true.</li>
+</ul>
+
+<p>All you need to do is create a class in your application that extends the {@code
+DownloaderService} class and override three methods to provide specific application details:</p>
+
+<dl>
+  <dt>{@code getPublicKey()}</dt>
+    <dd>This must return a string that is the Base64-encoded RSA public key for your publisher
+account, available from the profile page on the Android Market Developer Console (see <a
+href="{@docRoot}guide/market/licensing/setting-up.html">Setting Up for Licensing</a>).</dd>
+  <dt>{@code getSALT()}</dt>
+    <dd>This must return an array of random bytes that the licensing {@code Policy} uses to
+create an <a
+href="{@docRoot}guide/market/licensing/adding-licensing.html#impl-Obfuscator">{@code
+Obfuscator}</a>. The salt ensures that your obfuscated {@link android.content.SharedPreferences}
+file in which your licensing data is saved will be unique and non-discoverable.</dd>
+  <dt>{@code getAlarmReceiverClassName()}</dt>
+    <dd>This must return the class name of the {@link android.content.BroadcastReceiver} in
+your application that should receive the alarm indicating that the download should be
+restarted (which might happen if the downloader service unexpectedly stops).</dd>
+</dl>
+
+<p>For example, here's a complete implementation of {@code DownloaderService}:</p>
+
+<pre>
+public class SampleDownloaderService extends DownloaderService {
+    // You must use the public key belonging to your publisher account
+    public static final String BASE64_PUBLIC_KEY = "YourAndroidMarketLVLKey";
+    // You should also modify this salt
+    public static final byte[] SALT = new byte[] { 1, 42, -12, -1, 54, 98,
+            -100, -12, 43, 2, -8, -4, 9, 5, -106, -107, -33, 45, -1, 84
+    };
+
+    &#64;Override
+    public String getPublicKey() {
+        return BASE64_PUBLIC_KEY;
+    }
+
+    &#64;Override
+    public byte[] getSALT() {
+        return SALT;
+    }
+
+    &#64;Override
+    public String getAlarmReceiverClassName() {
+        return SampleAlarmReceiver.class.getName();
+    }
+}
+</pre>
+
+<p class="caution"><strong>Notice:</strong> You must update the {@code BASE64_PUBLIC_KEY} value
+to be the public key belonging to your publisher account. You can find the key in the Android
+Market Developer Console under your profile information. This is necessary even when testing
+your downloads.</p>
+
+<p>Remember to declare the service in your manifest file:</p>
+<pre>
+&lt;application ...>
+    &lt;service android:name=".SampleDownloaderService" />
+    ...
+&lt;/application>
+</pre>
+
+
+
+<h3 id="AlarmReceiver">Implementing the alarm receiver</h3>
+
+<p>In order to monitor the progress of the file downloads and restart the download if necessary, the
+{@code DownloaderService} schedules an {@link android.app.AlarmManager#RTC_WAKEUP} alarm that
+delivers an {@link android.content.Intent} to a {@link android.content.BroadcastReceiver} in your
+application. You must define the {@link android.content.BroadcastReceiver} to call an API
+from the Downloader Library that checks the status of the download and restarts
+it if necessary.</p>
+
+<p>You simply need to override the {@link android.content.BroadcastReceiver#onReceive
+onReceive()} method to call {@code
+DownloaderClientMarshaller.startDownloadServiceIfRequired()}.</p>
+
+<p>For example:</p>
+
+<pre>
+public class SampleAlarmReceiver extends BroadcastReceiver {
+    &#64;Override
+    public void onReceive(Context context, Intent intent) {
+        try {
+            DownloaderClientMarshaller.startDownloadServiceIfRequired(context, intent,
+                    SampleDownloaderService.class);
+        } catch (NameNotFoundException e) {
+            e.printStackTrace();
+        }      
+    }
+}
+</pre>
+
+<p>Notice that this is the class for which you must return the name
+in your service's {@code getAlarmReceiverClassName()} method (see the previous section).</p>
+
+<p>Remember to declare the receiver in your manifest file:</p>
+<pre>
+&lt;application ...>
+    &lt;receiver android:name=".SampleAlarmReceiver" />
+    ...
+&lt;/application>
+</pre>
+
+
+
+<h3 id="Download">Starting the download</h3>
+
+<p>The main activity in your application (the one started by your launcher icon) is
+responsible for verifying whether the expansion files are already on the device and initiating
+the download if they are not.</p>
+
+<p>Starting the download using the Downloader Library requires the following
+procedures:</p>
+
+<ol>
+  <li>Check whether the files have been downloaded.
+    <p>The Downloader Library includes some APIs in the {@code Helper} class to
+help with this process:</p>
+  <ul>
+    <li>{@code getExtendedAPKFileName(Context, c, boolean mainFile, int
+versionCode)}</li>
+    <li>{@code doesFileExist(Context c, String fileName, long fileSize)}</li>
+  </ul>
+    <p>For example, the sample app provided in the APK Expansion Library package calls the
+following method in the activity's {@link android.app.Activity#onCreate onCreate()} method to check
+whether the expansion files already exist on the device:</p>
+<pre>
+boolean expansionFilesDelivered() {
+    for (XAPKFile xf : xAPKS) {
+        String fileName = Helpers.getExpansionAPKFileName(this, xf.mIsBase, xf.mFileVersion);
+        if (!Helpers.doesFileExist(this, fileName, xf.mFileSize, false))
+            return false;
+    }
+    return true;
+}        
+</pre>
+    <p>In this case, each {@code XAPKFile} object holds the version number and file size of a known
+expansion file and a boolean as to whether it's the main expansion file.</p>
+    <p>If this method returns false, then the application must begin the download.</p>
+  </li>
+  <li>Start the download by calling the static method {@code
+DownloaderClientMarshaller.startDownloadServiceIfRequired(Context c, PendingIntent
+notificationClient, Class&lt;?> serviceClass)}.
+    <p>The method takes the following parameters:</p>
+    <ul>
+      <li><code>context</code>: Your application's {@link android.content.Context}.</li>
+      <li><code>notificationClient</code>: A {@link android.app.PendingIntent} to start your main
+activity. This is used in the {@link android.app.Notification} that the {@code DownloaderService}
+creates to show the download progress. When the user selects the notification, the system
+invokes the {@link android.app.PendingIntent} you supply here and should open the activity
+that shows the download progress (usually the same activity that started the download).</li>
+      <li><code>serviceClass</code>: The {@link java.lang.Class} object for your implementation of
+{@code DownloaderService}, required to start the service and begin the download if necessary.</li>
+    </ul>
+    <p>The method returns an integer that indicates
+whether or not the download is required. Possible values are:</p>
+    <ul>
+      <li>{@code NO_DOWNLOAD_REQUIRED}: Returned if the files already
+exist or a download is already in progress.</li>
+      <li>{@code LVL_CHECK_REQUIRED}: Returned if a license verification is
+required in order to acquire the expansion file URLs.</li>
+      <li>{@code DOWNLOAD_REQUIRED}: Returned if the expansion file URLs are already known,
+but have not been downloaded.</li>
+    </ul>
+    <p>The behavior for {@code LVL_CHECK_REQUIRED} and {@code DOWNLOAD_REQUIRED} are essentially the
+same and you normally don't need to be concerned about them. In your main activity that calls {@code
+startDownloadServiceIfRequired()}, you can simply check whether or not the response is {@code
+NO_DOWNLOAD_REQUIRED}. If the response is anything <em>other than</em> {@code NO_DOWNLOAD_REQUIRED},
+the Downloader Library begins the download and you should update your activity UI to
+display the download progress (see the next step). If the response <em>is</em> {@code
+NO_DOWNLOAD_REQUIRED}, then the files are available and your application can start.</p>
+    <p>For example:</p>
+<pre>
+&#64;Override
+public void onCreate(Bundle savedInstanceState) {
+    // Check if expansion files are available before going any further
+    if (!expansionFilesDelivered()) {
+        // Build an Intent to start this activity from the Notification
+        Intent notifierIntent = new Intent(this, MainActivity.getClass());
+        notifierIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
+                                Intent.FLAG_ACTIVITY_CLEAR_TOP);
+        ...
+        PendingIntent pendingIntent = PendingIntent.getActivity(this, 0,
+                notifierIntent, PendingIntent.FLAG_UPDATE_CURRENT);
+        
+        // Start the download service (if required)
+        int startResult = DownloaderClientMarshaller.startDownloadServiceIfRequired(this,
+                        pendingIntent, SampleDownloaderService.class);
+        // If download has started, initialize this activity to show download progress
+        if (startResult != DownloaderClientMarshaller.NO_DOWNLOAD_REQUIRED) {
+            // This is where you do set up to display the download progress (next step)
+            ...
+            return;
+        } // If the download wasn't necessary, fall through to start the app
+    }
+    startApp(); // Expansion files are available, start the app
+}
+</pre>
+  </li>
+  <li>When the {@code startDownloadServiceIfRequired()} method returns anything <em>other
+than</em> {@code NO_DOWNLOAD_REQUIRED}, create an instance of {@code IStub} by
+calling {@code DownloaderClientMarshaller.CreateStub(IDownloaderClient client, Class&lt;?>
+downloaderService)}. The {@code IStub} provides a binding between your activity to the downloader
+service such that your activity receives callbacks about the download progress.
+    <p>In order to instantiate your {@code IStub} by calling {@code CreateStub()}, you must pass it
+an implementation of the {@code IDownloaderClient} interface and your {@code DownloaderService}
+implementation. The next section about <a href="#Progress">Receiving download progress</a> discusses
+the {@code IDownloaderClient} interface, which you should usually implement in your {@link
+android.app.Activity} class so you can update the activity UI when the download state changes.</p>
+    <p>We recommend that you call {@code
+CreateStub()} to instantiate your {@code IStub} during your activity's {@link
+android.app.Activity#onCreate onCreate()} method, after {@code startDownloadServiceIfRequired()}
+starts the download. </p>
+    <p>For example, in the previous code sample for {@link android.app.Activity#onCreate
+onCreate()}, you can respond to the {@code startDownloadServiceIfRequired()} result like this:</p>
+<pre>
+        // Start the download service (if required)
+        int startResult = DownloaderClientMarshaller.startDownloadServiceIfRequired(this,
+                        pendingIntent, SampleDownloaderService.class);
+        // If download has started, initialize activity to show progress
+        if (startResult != DownloaderClientMarshaller.NO_DOWNLOAD_REQUIRED) {
+            // Instantiate a member instance of IStub
+            mDownloaderClientStub = DownloaderClientMarshaller.CreateStub(this,
+                    SampleDownloaderService.class);
+            // Inflate layout that shows download progress
+            setContentView(R.layout.downloader_ui);
+            return;
+        }
+</pre>
+
+    <p>After the {@link android.app.Activity#onCreate onCreate()} method returns, your activity
+receives a call to {@link android.app.Activity#onResume onResume()}, which is where you should then
+call {@code connect()} on the {@code IStub}, passing it your application's {@link
+android.content.Context}. Conversely, you should call
+{@code disconnect()} in your activity's {@link android.app.Activity#onStop onStop()} callback.</p>
+<pre>
+&#64;Override
+protected void onResume() {
+    if (null != mDownloaderClientStub) {
+        mDownloaderClientStub.connect(this);
+    }
+    super.onResume();
+}
+
+&#64;Override
+protected void onStop() {
+    if (null != mDownloaderClientStub) {
+        mDownloaderClientStub.disconnect(this);
+    }
+    super.onStop();
+}
+</pre>
+    <p>Calling {@code connect()} on the {@code IStub} binds your activity to the {@code
+DownloaderService} such that your activity receives callbacks regarding changes to the download
+state through the {@code IDownloaderClient} interface.</p>
+  </li>
+</ol>
+
+
+
+<h3 id="Progress">Receiving download progress</h3>
+
+<p>To receive updates regarding the download progress and to interact with the {@code
+DownloaderService}, you must implement the Downloader Library's {@code IDownloaderClient} interface.
+Usually, the activity you use to start the download should implement this interface in order to
+display the download progress and send requests to the service.</p>
+
+<p>The required interface methods for {@code IDownloaderClient} are:</p>
+
+<dl>
+  <dt>{@code onServiceConnected(Messenger m)}</dt>
+    <dd>After you instantiate the {@code IStub} in your activity, you'll receive a call to this
+method, which passes a {@link android.os.Messenger} object that's connected with your instance
+of {@code DownloaderService}. To send requests to the service, such as to pause and resume
+downloads, you must call {@code DownloaderServiceMarshaller.CreateProxy()} to receive the {@code
+IDownloaderService} interface connected to the service.
+    <p>A recommended implementation looks like this:</p>
+<pre>
+private IDownloaderService mRemoteService;
+...
+
+&#64;Override
+public void onServiceConnected(Messenger m) {
+    mRemoteService = DownloaderServiceMarshaller.CreateProxy(m);
+    mRemoteService.onClientUpdated(mDownloaderClientStub.getMessenger());
+}
+</pre>
+    <p>With the {@code IDownloaderService} object initialized, you can send commands to the
+downloader service, such as to pause and resume the download ({@code requestPauseDownload()}
+and {@code requestContinueDownload()}).</p>
+</dd>
+  <dt>{@code onDownloadStateChanged(int newState)}</dt>
+    <dd>The download service calls this when a change in download state occurs, such as the
+download begins or completes.
+      <p>The <code>newState</code> value will be one of several possible values specified in
+by one of the {@code IDownloaderClient} class's {@code STATE_*} constants.</p>
+      <p>To provide a useful message to your users, you can request a corresponding string
+for each state by calling {@code Helpers.getDownloaderStringResourceIDFromState()}. This
+returns the resource ID for one of the strings bundled with the Downloader
+Library. For example, the string "Download paused because you are roaming" corresponds to {@code
+STATE_PAUSED_ROAMING}.</p></dd>
+  <dt>{@code onDownloadProgress(DownloadProgressInfo progress)}</dt>
+    <dd>The download service calls this to deliver a {@code DownloadProgressInfo} object,
+which describes various information about the download progress, including estimated time remaining,
+current speed, overall progress, and total so you can update the download progress UI.</dd>
+</dl>
+<p class="note"><strong>Tip:</strong> For examples of these callbacks that update the download
+progress UI, see the {@code SampleDownloaderActivity} in the sample app provided with the Expansion
+Downloader package.</p>
+
+<p>Some public methods for the {@code IDownloaderService} interface you might find useful are:</p>
+
+<dl>
+  <dt>{@code requestPauseDownload()}</dt>
+    <dd>Pauses the download.</dd>
+  <dt>{@code requestContinueDownload()}</dt>
+    <dd>Resumes a paused download.</dd>
+  <dt>{@code setDownloadFlags(int flags)}</dt>
+    <dd>Sets user preferences for network types on which its OK to download the files. The
+current implementation supports one flag, {@code FLAGS_DOWNLOAD_OVER_CELLULAR}, but you can add
+others. By default, this flag is <em>not</em> enabled, so the user must be on Wi-Fi to download
+expansion files. You might want to provide a user preference to enable downloads over
+the cellular network. In which case, you can call:
+<pre>
+mRemoteService.setDownloadFlags(IDownloaderService.FLAGS_DOWNLOAD_OVER_CELLULAR);
+</pre>
+</dd>
+</dl>
+
+
+
+
+<h2 id="ExpansionPolicy">Using APKExpansionPolicy</h2>
+
+<p>If you decide to build your own downloader service instead of using the Android Market
+<a href="#AboutLibraries">Downloader Library</a>, you should still use the {@code
+APKExpansionPolicy} that's provided in the License Verification Library. The {@code
+APKExpansionPolicy} class is nearly identical to {@code ServerManagedPolicy} (available in the
+Android Market License Verification Library) but includes additional handling for the APK expansion
+file response extras.</p>
+
+<p class="note"><strong>Note:</strong> If you <em>do use</em> the <a
+href="#AboutLibraries">Downloader Library</a> as discussed in the previous section, the
+library performs all interaction with the {@code APKExpansionPolicy} so you don't have to use
+this class directly.</p>
+
+<p>The class includes methods to help you get the necessary information about the available
+expansion files:</p>
+
+<ul>
+  <li>{@code getExpansionURLCount()}</li>
+  <li>{@code getExpansionURL(int index)}</li>
+  <li>{@code getExpansionFileName(int index)}</li>
+  <li>{@code getExpansionFileSize(int index)}</li>
+</ul>
+
+<p>For more information about how to use the {@code APKExpansionPolicy} when you're <em>not</em>
+using the <a
+href="#AboutLibraries">Downloader Library</a>, see the documentation for <a
+href="{@docRoot}guide/market/licensing/adding-licensing.html">Adding Licensing to Your App</a>,
+which explains how to implement a license policy such as this one.</p>
+
+
+
+
+
+
+
+<h2 id="ReadingTheFile">Reading the Expansion File</h2>
+
+<p>Once your APK expansion files are saved on the device, how you read your files
+depends on the type of file you've used. As discussed in the <a href="#Overview">overview</a>, your
+expansion files can be any kind of file you
+want, but are renamed using a particular <a href="#Filename">file name format</a> and are saved to
+{@code &lt;shared-storage&gt;/Android/obb/&lt;package-name&gt;/}.</p>
+
+<p>Regardless of how you read your files, you should always first check that the external
+storage is available for reading. There's a chance that the user has the storage mounted to a
+computer over USB or has actually removed the SD card.</p>
+
+<p class="note"><strong>Note:</strong> When your application starts, you should always check whether
+the external storage space is available and readable by calling {@link
+android.os.Environment#getExternalStorageState()}. This returns one of several possible strings
+that represent the state of the external storage. In order for it to be readable by your
+application, the return value must be {@link android.os.Environment#MEDIA_MOUNTED}.</p>
+
+
+<h3 id="GettingFilenames">Getting the file names</h3>
+
+<p>As described in the <a href="#Overview">overview</a>, your APK expansion files are saved
+using a specific file name format:</p>
+
+<pre class="classic no-pretty-print">
+[main|patch].&lt;expansion-version&gt;.&lt;package-name&gt;.obb
+</pre>
+
+<p>To get the location and names of your expansion files, you should use the
+{@link android.os.Environment#getExternalStorageDirectory()} and {@link
+android.content.Context#getPackageName()} methods to construct the path to your files.</p>
+
+<p>Here's a method you can use in your application to get an array containing the complete path
+to both your expansion files:</p>
+
+<pre>
+// The shared path to all app expansion files
+private final static String EXP_PATH = "/Android/obb/";
+
+static String[] getAPKExpansionFiles(Context ctx, int mainVersion, int patchVersion) {
+    String packageName = ctx.getPackageName();
+    Vector&lt;String> ret = new Vector&lt;String>();
+    if (Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)) {
+        // Build the full path to the app's expansion files
+        File root = Environment.getExternalStorageDirectory();
+        File expPath = new File(root.toString() + EXP_PATH + packageName);
+
+        // Check that expansion file path exists
+        if (expPath.exists()) {
+            if ( mainVersion > 0 ) {
+                String strMainPath = expPath + File.separator + "main." +
+                        mainVersion + "." + packageName + ".obb";
+                File main = new File(strMainPath);
+                if ( main.isFile() ) {
+                        ret.add(strMainPath);
+                }
+            }
+            if ( patchVersion > 0 ) {
+                String strPatchPath = expPath + File.separator + "patch." +
+                        mainVersion + "." + packageName + ".obb";
+                File main = new File(strPatchPath);
+                if ( main.isFile() ) {
+                        ret.add(strPatchPath);
+                }
+            }
+        }
+    }
+    String[] retArray = new String[ret.size()];
+    ret.toArray(retArray);
+    return retArray;
+}
+</pre>
+
+<p>You can call this method by passing it your application {@link android.content.Context}
+and the desired expansion file's version.</p>
+
+<p>There are many ways you could determine the expansion file version number. One simple way is to
+save the version in a {@link android.content.SharedPreferences} file when the download begins, by
+querying the expansion file name with the {@code APKExpansionPolicy} class's {@code
+getExpansionFileName(int index)} method. You can then get the version code by reading the {@link
+android.content.SharedPreferences} file when you want to access the expansion
+file.</p>
+
+<p>For more information about reading from the shared storage, see the <a
+href="{@docRoot}guide/topics/data/data-storage.html#filesExternal">Data Storage</a>
+documentation.</p>
+
+
+
+<h3 id="ZipLib">Using the APK Expansion Zip Library</h3>
+
+<div class="sidebox-wrapper">
+<div class="sidebox">
+  <h3>Reading media files from a ZIP</h3>
+  <p>If you're using your expansion files to store media files, a ZIP file still allows you to
+use Android media playback calls that provide offset and length controls (such as {@link
+android.media.MediaPlayer#setDataSource(FileDescriptor,long,long) MediaPlayer.setDataSource()} and
+{@link android.media.SoundPool#load(FileDescriptor,long,long,int) SoundPool.load()}). In order for
+this to work, you must not perform additional compression on the media files when creating the ZIP
+packages. For example, when using the <code>zip</code> tool, you should use the <code>-n</code>
+option to specify the file suffixes that should not be compressed:</p>
+<p><code>zip -n .mp4;.ogg main_expansion media_files</code></p>
+</div>
+</div>
+
+<p>The Android Market APK Expansion Library package includes a library called the APK
+Expansion Zip Library (located in {@code
+&lt;sdk>/extras/google/google_market_apk_expansion/zip_file/}). This is an optional library that
+helps you read your expansion
+files when they're saved as ZIP files. Using this library allows you to easily read resources from
+your ZIP expansion files as a virtual file system.</p>
+
+<p>The APK Expansion Zip Library includes the following classes and APIs:</p>
+
+<dl>
+  <dt>{@code APKExpansionSupport}</dt>
+    <dd>Provides some methods to access expansion file names and ZIP files:
+      
+      <dl style="margin-top:1em">
+        <dt>{@code getAPKExpansionFiles()}</dt> 
+          <dd>The same method shown above that returns the complete file path to both expansion
+files.</dd>
+        <dt>{@code getAPKExpansionZipFile(Context ctx, int mainVersion, int
+patchVersion)}</dt>
+          <dd>Returns a {@code ZipResourceFile} representing the sum of both the main file and
+patch file. That is, if you specify both the <code>mainVersion</code> and the
+<code>patchVersion</code>, this returns a {@code ZipResourceFile} that provides read access to
+all the data, with the patch file's data merged on top of the main file.</dd>
+      </dl>
+    </dd>
+    
+  <dt>{@code ZipResourceFile}</dt>
+    <dd>Represents a ZIP file on the shared storage and performs all the work to provide a virtual
+file system based on your ZIP files. You can get an instance using {@code
+APKExpansionSupport.getAPKExpansionZipFile()} or with the {@code ZipResourceFile} by passing it the
+path to your expansion file. This class includes a variety of useful methods, but you generally
+don't need to access most of them. A couple of important methods are:
+
+      <dl style="margin-top:1em">
+        <dt>{@code getInputStream(String assetPath)}</dt>
+          <dd>Provides an {@link java.io.InputStream} to read a file within the ZIP file. The
+<code>assetPath</code> must be the path to the desired file, relative to
+the root of the ZIP file contents.</dd>
+        <dt>{@code getAssetFileDescriptor(String assetPath)}</dt>
+          <dd>Provides an {@link android.content.res.AssetFileDescriptor} for a file within the
+ZIP file. The <code>assetPath</code> must be the path to the desired file, relative to
+the root of the ZIP file contents. This is useful for certain Android APIs that require  an {@link
+android.content.res.AssetFileDescriptor}, such as some {@link android.media.MediaPlayer} APIs.</dd>
+      </dl>
+    </dd>
+    
+  <dt>{@code APEZProvider}</dt>
+    <dd>Most applications don't need to use this class. This class defines a {@link
+android.content.ContentProvider} that marshals the data from the ZIP files through a content
+provider {@link android.net.Uri} in order to provide file access for certain Android APIs that
+expect {@link android.net.Uri} access to media files.
+      <p>The sample application available in the
+APK Expansion Library package demonstrates a scenario in which this class is useful
+to specify a video with {@link android.widget.VideoView#setVideoURI
+VideoView.setVideoURI()}. See the sample app's class {@code SampleZipfileProvider} for an
+example of how to extend this class to use in your application.</p></dd>
+</dl>
+
+<h4>Reading from a ZIP file</h4>
+
+<p>When using the APK Expansion Zip Library, reading a file from your ZIP usually requires the
+following:</p>
+
+<pre>
+// Get a ZipResourceFile representing a merger of both the main and patch files
+ZipResourceFile expansionFile = APKExpansionSupport.getAPKExpansionZipFile(appContext,
+        mainVersion, patchVersion);
+        
+// Get an input stream for a known file inside the expansion file ZIPs
+InputStream fileStream = expansionFile.getInputStream(pathToFileInsideZip);
+</pre>
+
+<p>The above code provides access to any file that exists in either your main expansion file or
+patch expansion file, by reading from a merged map of all the files from both files. All you
+need to provide the {@code getAPKExpansionFile()} method is your application {@code
+android.content.Context} and the version number for both the main expansion file and patch
+expansion file.</p>
+
+<p>If you'd rather read from a specific expansion file, you can use the {@code
+ZipResourceFile} constructor with the path to the desired expansion file:</p>
+
+<pre>
+// Get a ZipResourceFile representing a specific expansion file
+ZipResourceFile expansionFile = new ZipResourceFile(filePathToMyZip);
+
+// Get an input stream for a known file inside the expansion file ZIPs
+InputStream fileStream = expansionFile.getInputStream(pathToFileInsideZip);
+</pre>
+
+
+
+
+
+<h2 id="Testing">Testing Your Expansion Files</h2>
+
+<p>Before publishing your application, there are two things you should test: Reading the
+expansion files and downloading the files.</p>
+
+
+<h3 id="TestingReading">Testing file reads</h3>
+
+<p>Before you upload your application to Android Market, you
+should test your application's ability to read the files from the shared storage. All you need to do
+is add the files to the appropriate location on the device shared storage and launch your
+application:</p>
+
+<ol>
+  <li>On your device, create the appropriate directory on the shared storage where Android
+Market will save your files.
+  <p>For example, if your package name is {@code com.example.android}, you need to create
+the directory {@code Android/obb/com.example.android/} on the shared storage space. (Plug in
+your test device to your computer to mount the shared storage and manually create this
+directory.)</p>
+  </li>
+  <li>Manually add the expansion files to that directory. Be sure that you rename your files to
+match the <a href="#Filename">file name format</a> that Android Market will use.
+  <p>For example, regardless of the file type, the main expansion file for the {@code
+com.example.android} application should be {@code main.0300110.com.example.android.obb}.
+The version code can be whatever value you want. Just remember:</p>
+  <ul>
+    <li>The main expansion file always starts with {@code main} and the patch file starts with
+{@code patch}.</li>
+    <li>The package name always matches that of the APK to which the file is attached on
+Android Market.
+  </ul>
+  </li>
+  <li>Now that the expansion file(s) are on the device, you can install and run your application to
+test your expansion file(s).</li>
+</ol>
+
+<p>Here are some reminders about handling the expansion files:</p>
+<ul>
+  <li><strong>Do not delete or rename</strong> the {@code .obb} expansion files (even if you unpack
+the data to a different location). Doing so will cause Android Market (or your app itself) to
+repeatedly download the expansion file.</li>
+  <li><strong>Do not save other data into your <code>obb/</code>
+directory</strong>. If you must unpack some data, save it into the location specified by {@link
+android.content.Context#getExternalFilesDir getExternalFilesDir()}.</li>
+</ul>
+
+
+
+<h3 id="TestingReading">Testing file downloads</h3>
+
+<p>Because your application must sometimes manually download the expansion files when it first
+opens, it's important that you test this process to be sure your application can successfully query
+for the URLs, download the files, and save them to the device.</p>
+
+<p>To test your application's implementation of the manual download procedure, you must upload
+your application to Android Market as a "draft" to make your expansion files available for
+download:</p>
+
+<ol>
+  <li>Upload your APK and corresponding expansion files using the Android Market Developer
+Console.</li>
+  <li>Fill in the necessary application details (title, screenshots, etc.). You can come back and
+finalize these details before publishing your application.
+  <p>Click the <strong>Save</strong> button. <em>Do not click Publish.</em> This saves
+the application as a draft, such that your application is not published for Android Market users,
+but the expansion files are available for you to test the download process.</p></li>
+  <li>Install the application on your test device using the Eclipse tools or <a
+href="{@docRoot}guide/developing/tools/adb.html">{@code adb}</a>.</li>
+  <li>Launch the app.</li>
+</ol>
+
+<p>If everything works as expected, your application should begin downloading the expansion
+files as soon as the main activity starts.</p>
+
+
+
+
+<h2 id="Updating">Updating Your Application</h2>
+
+<p>One of the great benefits to using expansion files on Android Market is the ability to
+update your application without re-downloading all of the original assets. Because Android Market
+allows you to provide two expansion files with each APK, you can use the second file as a "patch"
+that provides updates and new assets. Doing so avoids the
+need to re-download the main expansion file which could be large and expensive for users.</p>
+
+<p>The patch expansion file is technically the same as the main expansion file and neither
+the Android system nor Android Market perform actual patching between your main and patch expansion
+files. Your application code must perform any necessary patches itself.</p>
+
+<p>If you use ZIP files as your expansion files, the <a href="#ZipLib">APK Expansion Zip
+Library</a> that's included with the APK Expansion Library package includes the ability to merge
+your
+patch file with the main expansion file.</p>
+
+<p class="note"><strong>Note:</strong> Even if you only need to make changes to the patch
+expansion file, you must still update the APK in order for Android Market to perform an update.
+If you don't require code changes in the application, you should simply update the <a
+href="{@docRoot}guide/topics/manifest/manifest-element.html#vcode">{@code versionCode}</a> in the
+manifest.</p>
+
+<p>As long as you don't change the main expansion file that's associated with the APK
+in the Android Market Developer Console, users who previously installed your application will not
+download the main expansion file. Existing users receive only the updated APK and the new patch
+expansion file (retaining the previous main expansion file).</p>
+
+<p>Here are a few issues to keep in mind regarding updates to expansion files:</p>
+
+<ul>
+  <li>There can be only two expansion files for your application at a time. One main expansion
+file and one patch expansion file. During an update to a file, Android Market deletes the
+previous version (and so must your application when performing manual updates).</li>
+  <li>When adding a patch expansion file, the Android system does not actually patch your
+application or main expansion file. You must design your application to support the patch data.
+However, the APK Expansion Library package includes a library for using ZIP files
+as expansion files, which merges the data from the patch file into the main expansion file so
+you can easily read all the expansion file data.</li>
+</ul>
+
+
+
+<!-- Tools are not ready.
+     
+<h3>Using OBB tool and APIs</h3>
+
+<pre>
+$ mkobb.sh -d /data/myfiles -k my_secret_key -o /data/data.obb
+$ obbtool a -n com.example.myapp -v 1 -s seed_from_mkobb /data/data.obb
+</pre>
+
+<pre>
+storage = (StorageManager) getSystemService( STORAGE_SERVICE );
+storage.mountObb( obbFilepath, "my_secret_key", myListener );
+obbContentPath = storage.getMountedObbPath( obbFilepath );
+</pre>
+-->
diff --git a/docs/html/guide/market/licensing/adding-licensing.jd b/docs/html/guide/market/licensing/adding-licensing.jd
new file mode 100644
index 0000000..d1fe839
--- /dev/null
+++ b/docs/html/guide/market/licensing/adding-licensing.jd
@@ -0,0 +1,1072 @@
+page.title=Adding Licensing to Your App
+parent.title=Application Licensing
+parent.link=index.html
+@jd:body
+
+
+
+<div id="qv-wrapper">
+<div id="qv">
+  
+  <h2>In this document</h2>
+  <ol>
+  <li><a href="#manifest-permission">Adding the Licensing Permission</a></li>
+  <li><a href="#impl-Policy">Implementing a Policy</a>
+    <ol>
+      <li><a href="#custom-policies">Guidelines for custom policies</a></li>
+      <li><a href="#ServerManagedPolicy">ServerManagedPolicy</a></li>
+      <li><a href="#StrictPolicy">StrictPolicy</a></li>
+    </ol>
+  </li>
+  <li><a href="#impl-Obfuscator">Implementing an Obfuscator</a>
+    <ol>
+      <li><a href="#AESObfuscator">AESObfuscator</a></li>
+    </ol>
+  </li>
+  <li><a href="#impl-lc">Checking the License from an Activity</a>
+    <ol>
+      <li><a href="#lc-overview">Overview of license check and response</a></li>
+      <li><a href="#imports">Add imports</a></li>
+      <li><a href="#lc-impl">Implement LicenseCheckerCallback as a private inner class</a></li>
+      <li><a href="#thread-handler">Create a Handler for posting from LicenseCheckerCallback
+to the UI thread</a></li>
+      <li><a href="#lc-lcc">Instantiate LicenseChecker and LicenseCheckerCallback</a></li>
+      <li><a href="#check-access">Call checkAccess() to initiate the license check</a></li>
+      <li><a href="#account-key">Embed your public key for licensing</a></li>
+      <li><a href="#handler-cleanup">Call your LicenseChecker's onDestroy() method
+to close IPC connections</a></li>
+    </ol>
+  </li>
+  <li><a href="#impl-DeviceLimiter">Implementing a DeviceLimiter</a></li>
+  <li><a href="#app-obfuscation">Obfuscating Your Code</a></li>
+  <li><a href="#app-publishing">Publishing a Licensed Application</a>
+    <ol>
+      <li><a href="#">Removing Copy Protection</a></li>
+    </ol>
+  </li>
+  <li><a href="#support">Where to Get Support</a></li>
+</ol>
+  
+</div>
+</div>
+
+
+
+<p>After you've set up a publisher account and development environment (see <a
+href="setting-up.html">Setting Up for Licensing</a>), you are ready to add license verification to
+your app with the License Verification Library (LVL).</p>
+
+<p>Adding license verification with the LVL involves these tasks:</p>
+
+<ol>
+<li><a href="#manifest-permission">Adding the licensing permission</a> your application's manifest.</li>
+<li><a href="#impl-Policy">Implementing a Policy</a> &mdash; you can choose one of the full implementations provided in the LVL or create your own.</li>
+<li><a href="#impl-Obfuscator">Implementing an Obfuscator</a>, if your {@code Policy} will cache any
+license response data. </li>
+<li><a href="#impl-lc">Adding code to check the license</a> in your application's main
+Activity.</li>
+<li><a href="#impl-DeviceLimiter">Implementing a DeviceLimiter</a> (optional and not recommended for
+most applications).</li>
+</ol>
+
+<p>The sections below describe these tasks. When you are done with the
+integration, you should be able to compile your application successfully and you
+can begin testing, as described in <a
+href="{@docRoot}guide/market/licensing/setting-up.html#test-env">Setting Up the Test
+Environment</a>.</p>
+
+<p>For an overview of the full set of source files included in the LVL, see <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html#lvl-summary">Summary of LVL Classes
+and Interfaces</a>.</p>
+
+
+<h2 id="manifest-permission">Adding the Licensing Permission</h2>
+
+<p>To use the Android Market application for sending a license check to the
+server, your application must request the proper permission,
+<code>com.android.vending.CHECK_LICENSE</code>. If your application does
+not declare the licensing permission but attempts to initiate a license check,
+the LVL throws a security exception.</p>
+
+<p>To request the licensing permission in your application, declare a <a
+href="{@docRoot}guide/topics/manifest/uses-permission-element.html"><code>&lt;uses-permission&gt;</code></a>
+element as a child of <code>&lt;manifest&gt;</code>, as follows: </p>
+
+<p style="margin-left:2em;"><code>&lt;uses-permission
+android:name="com.android.vending.CHECK_LICENSE"&gt;</code></p>
+
+<p>For example, here's how the LVL sample application declares the permission:
+</p>
+
+<pre>&lt;?xml version="1.0" encoding="utf-8"?&gt;
+
+&lt;manifest xmlns:android="http://schemas.android.com/apk/res/android" ..."&gt;
+    &lt;!-- Devices &gt;= 3 have version of Android Market that supports licensing. --&gt;
+    &lt;uses-sdk android:minSdkVersion="3" /&gt;
+    &lt;!-- Required permission to check licensing. --&gt;
+    &lt;uses-permission android:name="com.android.vending.CHECK_LICENSE" /&gt;
+    ...
+&lt;/manifest&gt;
+</pre>
+
+<p class="note"><strong>Note:</strong> Currently, you cannot declare the
+<code>CHECK_LICENSE</code> permission in the LVL library project's manifest,
+because the SDK Tools will not merge it into the manifests of dependent
+applications. Instead, you must declare the permission in each dependent
+application's manifest. </p>
+
+
+<h2 id="impl-Policy">Implementing a Policy</h2>
+
+<div class="sidebox-wrapper">
+<div class="sidebox">
+<h2>ServerManagedPolicy</h2>
+
+<p>The LVL includes a complete {@code Policy} implementation called ServerManagedPolicy
+that makes use of license-management settings provided by the Android Market
+server. </p>
+
+<p style="margin-top:.5em;">Use of ServerManagedPolicy as the basis for your
+Policy is strongly recommended. For more information, see <a
+href="#ServerManagedPolicy">ServerManagedPolicy</a> section, below.</p>
+
+</div>
+</div>
+
+<p>Android Market licensing service does not itself determine whether a
+given user with a given license should be granted access to your application.
+Rather, that responsibility is left to a {@code Policy} implementation that you provide
+in your application.</p>
+
+<p>Policy is an interface declared by the LVL that is designed to hold your
+application's logic for allowing or disallowing user access, based on the result
+of a license check. To use the LVL, your application <em>must</em> provide an
+implementation of {@code Policy}. </p>
+
+<p>The {@code Policy} interface declares two methods, <code>allowAccess()</code> and
+<code>processServerResponse()</code>, which are called by a {@code LicenseChecker}
+instance when processing a response from the license server. It also declares an
+enum called <code>LicenseResponse</code>, which specifies the license response
+value passed in calls to <code>processServerResponse()</code>. </p>
+
+<ul>
+<li><code>processServerResponse()</code> lets you preprocess the raw response
+data received from the licensing server, prior to determining whether to grant
+access.
+
+<p>A typical implementation would extract some or all fields from the license
+response and store the data locally to a persistent store, such as through
+{@link android.content.SharedPreferences} storage, to ensure that the data is
+accessible across application invocations and device power cycles. For example,
+a {@code Policy} would maintain the timestamp of the last successful license check, the
+retry count, the license validity period, and similar information in a
+persistent store, rather than resetting the values each time the application is
+launched.</p>
+
+<p>When storing response data locally, the {@code Policy} must ensure that the data is
+obfuscated (see <a href="#impl-Obfuscator">Implementing an Obfuscator</a>,
+below).</p></li>
+
+<li><code>allowAccess()</code> determines whether to grant the user access to
+your application, based on any available license response data (from the
+licensing server or from cache) or other application-specific information.  For
+example, your implementation of <code>allowAccess()</code> could take into
+account additional criteria, such as usage or other data retrieved from a
+backend server. In all cases, an implementation of <code>allowAccess()</code>
+should only return <code>true</code> if the user is licensed to use the
+application, as determined by the licensing server, or if there is a transient
+network or system problem that prevents the license check from completing. In
+such cases, your implementation can maintain a count of retry responses and
+provisionally allow access until the next license check is complete.</li>
+
+</ul>
+
+<p>To simplify the process of adding licensing to your application and to
+provide an illustration of how a {@code Policy} should be designed, the LVL includes
+two full {@code Policy} implementations that you can use without modification or
+adapt to your needs:</p>
+
+<ul>
+<li><a href="#ServerManagedPolicy">ServerManagedPolicy</a>, a flexible {@code Policy}
+that uses server-provided settings and cached responses to manage access across
+varied network conditions, and</li>
+<li><a href="#StrictPolicy">StrictPolicy</a>, which does not cache any response
+data and allows access <em>only</em> if the server returns a licensed
+response.</li>
+</ul>
+
+<p>For most applications, the use of ServerManagedPolicy is highly
+recommended. ServerManagedPolicy is the LVL default and is integrated with
+the LVL sample application.</p>
+
+
+<h3 id="custom-policies">Guidelines for custom policies</h3>
+
+<p>In your licensing implementation, you can use one of the complete policies
+provided in the LVL (ServerManagedPolicy or StrictPolicy) or you can create a
+custom policy. For any type of custom policy, there are several important design
+points to understand and account for in your implementation.</p>
+
+<p>The licensing server applies general request limits to guard against overuse
+of resources that could result in denial of service. When an application exceeds
+the request limit, the licensing server returns a 503 response, which gets
+passed through to your application as a general server error. This means that no
+license response will be available to the user until the limit is reset, which
+can affect the user for an indefinite period.</p>
+
+<p>If you are designing a custom policy, we recommend that the {@code Policy}:
+<ol>
+<!-- <li>Limits the number of points at which your app calls for a license check
+to the minimum. </li> -->
+<li>Caches (and properly obfuscates) the most recent successful license response
+in local persistent storage.</li>
+<li>Returns the cached response for all license checks, for as long as the
+cached response is valid, rather than making a request to the licensing server.
+Setting the response validity according to the server-provided <code>VT</code>
+extra is highly recommended. See <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html#extras">Server Response Extras</a>
+for more information.</li>
+<li>Uses an exponential backoff period, if retrying any requests the result in
+errors. Note that the Android Market client automatically retries failed
+requests, so in most cases there is no need for your {@code Policy} to retry them.</li>
+<li>Provides for a "grace period" that allows the user to access your
+application for a limited time or number of uses, while a license check is being
+retried. The grace period benefits the user by allowing access until the next
+license check can be completed successfully and it benefits you by placing a
+hard limit on access to your application when there is no valid license response
+available.</li>
+</ol>
+
+<p>Designing your {@code Policy} according to the guidelines listed above is critical,
+because it ensures the best possible experience for users while giving you
+effective control over your application even in error conditions. </p>
+
+<p>Note that any {@code Policy} can use settings provided by the licensing server to
+help manage validity and caching, retry grace period, and more. Extracting the
+server-provided settings is straightforward and making use of them is highly
+recommended. See the ServerManagedPolicy implementation for an example of how to
+extract and use the extras. For a list of server settings and information about
+how to use them, see  <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html#extras">Server Response
+Extras</a>.</p>
+
+<h3 id="ServerManagedPolicy">ServerManagedPolicy</h3>
+
+<div class="sidebox-wrapper">
+<div class="sidebox">
+<h2>Server Response Extras</h2>
+
+<p>For certain types of licensing responses, the licensing server appends extra
+settings to the responses, to help the application manage licensing effectively.
+</p>
+
+<p style="margin-top:.5em;">See <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html#extras">Server Response Extras</a>
+for
+a list of settings and <code>ServerManagedPolicy.java</code> for information
+about how a {@code Policy} can use the extras.</p>
+
+</div>
+</div>
+
+<p>The LVL includes a full and recommended implementation of the {@code Policy}
+interface called ServerManagedPolicy. The implementation is integrated with the
+LVL classes and serves as the default {@code Policy} in the library. </p>
+
+<p>ServerManagedPolicy provides all of the handling for license and retry
+responses. It caches all of the response data locally in a
+{@link android.content.SharedPreferences} file, obfuscating it with the
+application's {@code Obfuscator} implementation. This ensures that the license response
+data is secure and persists across device power cycles. ServerManagedPolicy
+provides concrete implementations of the interface methods
+<code>processServerResponse()</code> and <code>allowAccess()</code> and also
+includes a set of supporting methods and types for managing license
+responses.</p>
+
+<p>Importantly, a key feature of ServerMangedPolicy is its use of
+server-provided settings as the basis for managing licensing across an
+application's refund period and through varying network and error conditions.
+When an application contacts the Android Market server for a license check, the
+server appends several settings as key-value pairs in the extras field of certain
+license response types. For example, the server provides recommended values for the
+application's license validity period, retry grace period, and maximum allowable
+retry count, among others. ServerManagedPolicy extracts the values from the
+license response in its <code>processServerResponse()</code> method and checks
+them in its <code>allowAccess()</code> method. For a list of the server-provided
+settings used by ServerManagedPolicy, see <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html#extras">Server Response
+Extras</a>.</p>
+
+<p>For convenience, best performance, and the benefit of using license settings
+from the Android Market server, <strong>using ServerManagedPolicy as your
+licensing {@code Policy} is strongly recommended</strong>. </p>
+
+<p>If you are concerned about the security of license response data that is
+stored locally in {@link android.content.SharedPreferences}, you can use a stronger obfuscation
+algorithm or design a stricter {@code Policy} that does not store license data. The LVL
+includes an example of such a {@code Policy} &mdash; see <a
+href="#StrictPolicy">StrictPolicy</a> for more information.</p>
+
+<p>To use ServerManagedPolicy, simply import it to your Activity, create an
+instance, and pass a reference to the instance when constructing your
+{@code LicenseChecker}. See <a href="#lc-lcc">Instantiate LicenseChecker and
+LicenseCheckerCallback</a> for more information. </p>
+
+<h3 id="StrictPolicy">StrictPolicy</h3>
+
+<p>The LVL includes an alternative full implementation of the {@code Policy} interface
+called StrictPolicy. The StrictPolicy implementation provides a more restrictive
+Policy than ServerManagedPolicy, in that it does not allow the user to access
+the application unless a license response is received from the server at the
+time of access that indicates that the user is licensed.</p>
+
+<p>The principal feature of StrictPolicy is that it does not store <em>any</em>
+license response data locally, in a persistent store. Because no data is stored,
+retry requests are not tracked and cached responses can not be used to fulfill
+license checks. The {@code Policy} allows access only if:</p>
+
+<ul>
+<li>The license response is received from the licensing server, and </li>
+<li>The license response indicates that the user is licensed to access the
+application. </li>
+</ul>
+
+<p>Using StrictPolicy is appropriate if your primary concern is to ensure that,
+in all possible cases, no user will be allowed to access the application unless
+the user is confirmed to be licensed at the time of use. Additionally, the
+Policy offers slightly more security than ServerManagedPolicy &mdash; since
+there is no data cached locally, there is no way a malicious user could tamper
+with the cached data and obtain access to the application.</p>
+
+<p>At the same time, this {@code Policy} presents a challenge for normal users, since it
+means that they won't be able to access the application when there is no network
+(cell or Wi-Fi) connection available. Another side-effect is that your
+application will send more license check requests to the server, since using a
+cached response is not possible.</p>
+
+<p>Overall, this policy represents a tradeoff of some degree of user convenience
+for absolute security and control over access. Consider the tradeoff carefully
+before using this {@code Policy}.</p>
+
+<p>To use StrictPolicy, simply import it to your Activity, create an instance,
+and pass a reference to it when constructing your {@code LicenseChecker}. See
+<a href="#lc-lcc">Instantiate LicenseChecker and LicenseCheckerCallback</a>
+for more information. </p>
+
+<h2 id="impl-Obfuscator">Implementing an Obfuscator</h2>
+
+<div class="sidebox-wrapper">
+<div class="sidebox">
+<h2>AESObfuscator</h2>
+
+<p>The LVL includes a full {@code Obfuscator} implementation in the
+<code>AESObfuscator.java</code> file. The {@code Obfuscator} uses AES encryption to
+obfuscate/unobfuscate data. If you are using a {@code Policy} (such as
+ServerManagedPolicy) that caches license response data, using AESObfuscator as
+basis for your {@code Obfuscator} implementation is highly recommended. </p>
+
+</div>
+</div>
+
+<p>A typical {@code Policy} implementation needs to save the license response data for
+an application to a persistent store, so that it is accessible across
+application invocations and device power cycles.  For example, a {@code Policy} would
+maintain the timestamp of the last successful license check, the retry count,
+the license validity period, and similar information in a persistent store,
+rather than resetting the values each time the application is launched. The
+default {@code Policy} included in the LVL, ServerManagedPolicy, stores license response
+data in a {@link android.content.SharedPreferences} instance, to ensure that the
+data is persistent. </p>
+
+<p>Because the {@code Policy} will use stored license response data to determine whether
+to allow or disallow access to the application, it <em>must</em> ensure that any
+stored data is secure and cannot be reused or manipulated by a root user on a
+device. Specifically, the {@code Policy} must always obfuscate the data before storing
+it, using a key that is unique for the application and device. Obfuscating using
+a key that is both application-specific and device-specific is critical, because
+it prevents the obfuscated data from being shared among applications and
+devices.</p>
+
+<p>The LVL assists the application with storing its license response data in a
+secure, persistent manner. First, it provides an {@code Obfuscator}
+interface that lets your application supply the obfuscation algorithm of its
+choice for stored data. Building on that, the LVL provides the helper class
+PreferenceObfuscator, which handles most of the work of calling the
+application's {@code Obfuscator} class and reading and writing the obfuscated data in a
+{@link android.content.SharedPreferences} instance. </p>
+
+<p>The LVL provides a full {@code Obfuscator} implementation called
+AESObfuscator that uses AES encryption to obfuscate data. You can
+use AESObfuscator in your application without modification or you
+can adapt it to your needs. For more information, see the next section.</p>
+
+
+<h3 id="AESObfuscator">AESObfuscator</h3>
+
+<p>The LVL includes a full and recommended implementation of the {@code Obfuscator}
+interface called AESObfuscator. The implementation is integrated with the
+LVL sample application and serves as the default {@code Obfuscator} in the library. </p>
+
+<p>AESObfuscator provides secure obfuscation of data by using AES to
+encrypt and decrypt the data as it is written to or read from storage.
+The {@code Obfuscator} seeds the encryption using three data fields provided
+by the application: </p>
+
+<ol>
+<li>A salt &mdash; an array of random bytes to use for each (un)obfuscation. </li>
+<li>An application identifier string, typically the package name of the application.</li>
+<li>A device identifier string, derived from as many device-specific sources
+as possible, so as to make it as unique.</li>
+</ol>
+
+<p>To use AESObfuscator, first import it to your Activity. Declare a private
+static final array to hold the salt bytes and initialize it to 20 randomly
+generated bytes.</p>
+
+<pre>    ...
+    // Generate 20 random bytes, and put them here.
+    private static final byte[] SALT = new byte[] {
+     -46, 65, 30, -128, -103, -57, 74, -64, 51, 88, -95,
+     -45, 77, -117, -36, -113, -11, 32, -64, 89
+     };
+    ...
+</pre>
+
+<p>Next, declare a variable to hold a device identifier and generate a value for
+it in any way needed. For example, the sample application included in the LVL
+queries the system settings for the
+<code>android.Settings.Secure.ANDROID_ID</code>, which is unique to each device.
+</p>
+
+<p>Note that, depending on the APIs you use, your application might need to
+request additional permissions in order to acquire device-specific information.
+For example, to query the {@link android.telephony.TelephonyManager} to obtain
+the device IMEI or related data, the application will also need to request the
+<code>android.permission.READ_PHONE_STATE</code> permission in its manifest.</p>
+
+<p>Before requesting new permissions for the <em>sole purpose</em> of acquiring
+device-specific information for use in your {@code Obfuscator}, consider
+how doing so might affect your application or its filtering on Android Market
+(since some permissions can cause the SDK build tools to add
+the associated <code>&lt;uses-feature&gt;</code>).</p>
+
+<p>Finally, construct an instance of AESObfuscator, passing the salt,
+application identifier, and device identifier. You can construct the instance
+directly, while constructing your {@code Policy} and {@code LicenseChecker}. For example:</p>
+
+<pre>    ...
+    // Construct the LicenseChecker with a Policy.
+    mChecker = new LicenseChecker(
+        this, new ServerManagedPolicy(this,
+            new AESObfuscator(SALT, getPackageName(), deviceId)),
+        BASE64_PUBLIC_KEY  // Your public licensing key.
+        );
+    ...
+</pre>
+
+<p>For a complete example, see MainActivity in the LVL sample application.</p>
+
+
+<h2 id="impl-lc">Checking the License from an Activity</h2>
+
+<p>Once you've implemented a {@code Policy} for managing access to your application, the
+next step is to add a license check to your application, which initiates a query
+to the licensing server if needed and manages access to the application based on
+the license response. All of the work of adding the license check and handling
+the response takes place in your main {@link android.app.Activity} source file.
+</p>
+
+<p>To add the license check and handle the response, you must:</p>
+
+<ol>
+    <li><a href="#imports">Add imports</a></li>
+    <li><a href="#lc-impl">Implement LicenseCheckerCallback</a> as a private inner class</li>
+    <li><a href="#thread-handler">Create a Handler</a> for posting from LicenseCheckerCallback to the UI thread</li>
+    <li><a href="#lc-lcc">Instantiate LicenseChecker</a> and LicenseCheckerCallback</li>
+    <li><a href="#check-access">Call checkAccess()</a> to initiate the license check</li>
+    <li><a href="#account-key">Embed your public key</a> for licensing</li>
+    <li><a href="#handler-cleanup">Call your LicenseChecker's onDestroy() method</a> to close IPC connections.</li>
+</ol>
+
+<p>The sections below describe these tasks. </p>
+
+<h3 id="lc-overview">Overview of license check and response</h3>
+
+<div class="sidebox-wrapper">
+<div class="sidebox">
+<h2>Example: MainActivity</h2>
+
+<p>The sample application included with the LVL provides a full example of how
+to initiate a license check and handle the result, in the
+<code>MainActivity.java</code> file.</p>
+
+</div>
+</div>
+
+<p>In most cases, you should add the license check to your application's main
+{@link android.app.Activity}, in the {@link android.app.Activity#onCreate onCreate()} method. This
+ensures that when the user launches your application directly, the license check
+will be invoked immediately. In some cases, you can add license checks in other
+locations as well. For example, if your application includes multiple Activity
+components that other applications can start by {@link android.content.Intent},
+you could add license checks in those Activities.</p>
+
+<p>A license check consists of two main actions: </p>
+
+<ul>
+<li>A call to a method to initiate the license check &mdash; in the LVL, this is
+a call to the <code>checkAccess()</code> method of a {@code LicenseChecker} object that
+you construct.</li>
+<li>A callback that returns the result of the license check. In the LVL, this is
+a <code>LicenseCheckerCallback</code> interface that you implement. The
+interface declares two methods, <code>allow()</code> and
+<code>dontAllow()</code>, which are invoked by the library based on to the
+result of the license check. You implement these two methods with whatever logic
+you need, to allow or disallow the user access to your application. Note that
+these methods do not determine <em>whether</em> to allow access &mdash; that
+determination is the responsibility of your {@code Policy} implementation. Rather, these
+methods simply provide the application behaviors for <em>how</em> to allow and
+disallow access (and handle application errors).
+  <p>The <code>allow()</code> and <code>dontAllow()</code> methods do provide a "reason"
+for their response, which can be one of the {@code Policy} values, {@code LICENSED},
+{@code NOT_LICENSED}, or {@code RETRY}. In particular, you should handle the case in which
+the method receives the {@code RETRY} response for {@code dontAllow()} and provide the user with an
+"Retry" button, which might have happened because the service was unavailable during the
+request.</p></li>
+</ul>
+
+<div style="margin-bottom:2em;">
+
+<img src="{@docRoot}images/licensing_flow.png" style="text-align:left;margin-bottom:0;margin-left:3em;" />
+<div style="margin:.5em 0 1.5em 2em;padding:0"><strong>Figure 6.</strong> Overview of a
+typical license check interaction.</div>
+</div>
+
+<p>The diagram above illustrates how a typical license check takes place: </p>
+
+<ol>
+<li>Code in the application's main Activity instantiates {@code LicenseCheckerCallback}
+and {@code LicenseChecker} objects. When constructing {@code LicenseChecker}, the code passes in
+{@link android.content.Context}, a {@code Policy} implementation to use, and the
+publisher account's public key for licensing as parameters. </li>
+<li>The code then calls the <code>checkAccess()</code> method on the
+{@code LicenseChecker} object. The method implementation calls the {@code Policy} to determine
+whether there is a valid license response cached locally, in
+{@link android.content.SharedPreferences}.
+  <ul>
+    <li>If so, the <code>checkAccess()</code> implementation calls
+  <code>allow()</code>.</li>
+    <li>Otherwise, the {@code LicenseChecker} initiates a license check request that is sent
+  to the licensing server.</li>
+  </ul>
+
+<p class="note"><strong>Note:</strong> The licensing server always returns
+<code>LICENSED</code> when you perform a license check of a draft application.</p>
+</li>
+<li>When a response is received, {@code LicenseChecker} creates a LicenseValidator that
+verifies the signed license data and extracts the fields of the response, then
+passes them to your {@code Policy} for further evaluation.
+  <ul>
+    <li>If the license is valid, the {@code Policy} caches the response in
+{@link android.content.SharedPreferences} and notifies the validator, which then calls the
+<code>allow()</code> method on the {@code LicenseCheckerCallback} object. </li>
+    <li>If the license not valid, the {@code Policy} notifies the validator, which calls
+the <code>dontAllow()</code> method on {@code LicenseCheckerCallback}. </li>
+  </ul>
+</li>
+<li>In case of a recoverable local or server error, such as when the network is
+not available to send the request, {@code LicenseChecker} passes a {@code RETRY} response to
+your {@code Policy} object's <code>processServerResponse()</code> method. 
+  <p>Also, both the {@code allow()} and {@code dontAllow()} callback methods receive a
+<code>reason</code> argument. The {@code allow()} method's reason is usually {@code
+Policy.LICENSED} or {@code Policy.RETRY} and the {@code dontAllow()} reason is usually {@code
+Policy.NOT_LICENSED} or {@code Policy.RETRY}. These response values are useful so you can show
+an appropriate response for the user, such as by providing a "Retry" button when {@code
+dontAllow()} responds with {@code Policy.RETRY}, which might have been because the service was
+unavailable.</p></li>
+<li>In case of a application error, such as when the application attempts to
+check the license of an invalid package name, {@code LicenseChecker} passes an error
+response to the LicenseCheckerCallback's  <code>applicationError()</code>
+method. </li>
+</ol>
+
+<p>Note that, in addition to initiating the license check and handling the
+result, which are described in the sections below, your application also needs
+to provide a <a href="#impl-Policy">Policy implementation</a> and, if the {@code Policy}
+stores response data (such as ServerManagedPolicy), an <a
+href="#impl-Obfuscator">Obfuscator</a> implementation. </p>
+
+
+<h3 id="imports">Add imports</h3>
+
+<p>First, open the class file of the application's main Activity and import
+{@code LicenseChecker} and {@code LicenseCheckerCallback} from the LVL package.</p>
+
+<pre>    import com.android.vending.licensing.LicenseChecker;
+    import com.android.vending.licensing.LicenseCheckerCallback;</pre>
+
+<p>If you are using the default {@code Policy} implementation provided with the LVL,
+ServerManagedPolicy, import it also, together with the AESObfuscator. If you are
+using a custom {@code Policy} or {@code Obfuscator}, import those instead. </p>
+
+<pre>    import com.android.vending.licensing.ServerManagedPolicy;
+    import com.android.vending.licensing.AESObfuscator;</pre>
+
+<h3 id="lc-impl">Implement LicenseCheckerCallback as a private inner class</h3>
+
+<p>{@code LicenseCheckerCallback} is an interface provided by the LVL for handling
+result of a license check. To support licensing using the LVL, you must
+implement {@code LicenseCheckerCallback} and
+its methods to allow or disallow access to the application.</p>
+
+<p>The result of a license check is always a call to one of the
+{@code LicenseCheckerCallback} methods, made based on the validation of the response
+payload, the server response code itself, and any additional processing provided
+by your {@code Policy}. Your application can implement the methods in any way needed. In
+general, it's best to keep the methods simple, limiting them to managing UI
+state and application access. If you want to add further processing of license
+responses, such as by contacting a backend server or applying custom constraints,
+you should consider incorporating that code into your {@code Policy}, rather than
+putting it in the {@code LicenseCheckerCallback} methods. </p>
+
+<p>In most cases, you should declare your implementation of
+{@code LicenseCheckerCallback} as a private class inside your application's main
+Activity class. </p>
+
+<p>Implement the <code>allow()</code> and <code>dontAllow()</code> methods as
+needed. To start with, you can use simple result-handling behaviors in the
+methods, such as displaying the license result in a dialog. This helps you get
+your application running sooner and can assist with debugging. Later, after you
+have determined the exact behaviors you want, you can add more complex handling.
+</p>
+
+<p>Some suggestions for handling unlicensed responses in
+<code>dontAllow()</code> include: </p>
+
+<ul>
+<li>Display a "Try again" dialog to the user, including a button to initiate a
+new license check if the <code>reason</code> supplied is {@code Policy.RETRY}. </li>
+<li>Display a "Purchase this application" dialog, including a button that
+deep-links the user to the application's details page on Market, from which the
+use can purchase the application. For more information on how to set up such
+links, see <a
+href="{@docRoot}guide/publishing/publishing.html#marketintent">Using Intents to
+Launch the Market Application on a Device</a>. </li>
+<li>Display a Toast notification that indicates that the features of the
+application are limited because it is not licensed. </li>
+</ul>
+
+<p>The example below shows how the LVL sample application implements
+{@code LicenseCheckerCallback}, with methods that display the license check result in a
+dialog. </p>
+
+<pre>
+private class MyLicenseCheckerCallback implements LicenseCheckerCallback {
+    public void allow(int reason) {
+        if (isFinishing()) {
+            // Don't update UI if Activity is finishing.
+            return;
+        }
+        // Should allow user access.
+        displayResult(getString(R.string.allow));
+    }
+
+    public void dontAllow(int reason) {
+        if (isFinishing()) {
+            // Don't update UI if Activity is finishing.
+            return;
+        }
+        displayResult(getString(R.string.dont_allow));
+        
+        if (reason == Policy.RETRY) {
+            // If the reason received from the policy is RETRY, it was probably
+            // due to a loss of connection with the service, so we should give the
+            // user a chance to retry. So show a dialog to retry.
+            showDialog(DIALOG_RETRY);
+        } else {
+            // Otherwise, the user is not licensed to use this app.
+            // Your response should always inform the user that the application
+            // is not licensed, but your behavior at that point can vary. You might
+            // provide the user a limited access version of your app or you can
+            // take them to Android Market to purchase the app.
+            showDialog(DIALOG_GOTOMARKET);
+        }
+    }
+}
+</pre>
+
+<p>Additionally, you should implement the <code>applicationError()</code>
+method, which the LVL calls to let your application handle errors that are not
+retryable. For a list of such errors, see <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html#server-response-codes">Server
+Response Codes</a> in the <a
+href="guide/market/licensing/licensing-reference.html">Licensing Reference</a>. You can implement
+the method in any way needed. In most cases, the
+method should log the error code and call <code>dontAllow()</code>.</p>
+
+<h3 id="thread-handler">Create a Handler for posting from LicenseCheckerCallback
+to the UI thread</h3>
+
+<p>During a license check, the LVL passes the request to the Android Market
+application, which handles communication with the licensing server. The LVL
+passes the request over asynchronous IPC (using {@link android.os.Binder}) so
+the actual processing and network communication do not take place on a thread
+managed by your application. Similarly, when the Android Market application
+receives the result, it invokes a  callback method over IPC, which in turn
+executes in an IPC thread pool in your application's process.</p>
+
+<p>The {@code LicenseChecker} class manages your application's IPC communication with
+the Android Market application, including the call that sends the request and
+the callback that receives the response. {@code LicenseChecker} also tracks open license
+requests and manages their timeouts. </p>
+
+<p>So that it can handle timeouts properly and also process incoming responses
+without affecting your application's UI thread, {@code LicenseChecker} spawns a
+background thread at instantiation. In the thread it does all processing of
+license check results, whether the result is a response received from the server
+or a timeout error. At the conclusion of processing, the LVL calls your
+{@code LicenseCheckerCallback} methods from the background thread. </p>
+
+<p>To your application, this means that:</p>
+
+<ol>
+<li>Your {@code LicenseCheckerCallback} methods will be invoked, in many cases, from a
+background thread.</li>
+<li>Those methods won't be able to update state or invoke any processing in the
+UI thread, unless you create a Handler in the UI thread and have your callback
+methods post to the Handler.</li>
+</ol>
+
+<p>If you want your {@code LicenseCheckerCallback} methods to update the UI thread,
+instantiate a {@link android.os.Handler} in the main Activity's
+{@link android.app.Activity#onCreate(android.os.Bundle) onCreate()} method,
+as shown below. In this example, the LVL sample application's
+{@code LicenseCheckerCallback} methods (see above) call <code>displayResult()</code> to
+update the UI thread through the Handler's
+{@link android.os.Handler#post(java.lang.Runnable) post()} method.</p>
+
+<pre>private Handler mHandler;
+
+    &#64;Override
+    public void onCreate(Bundle savedInstanceState) {
+        ...
+        mHandler = new Handler();
+    }
+</pre>
+
+<p>Then, in your {@code LicenseCheckerCallback} methods, you can use Handler methods to
+post Runnable or Message objects to the Handler. Here's how the sample
+application included in the LVL posts a Runnable to a Handler in the UI thread
+to display the license status.</p>
+
+<pre>    private void displayResult(final String result) {
+        mHandler.post(new Runnable() {
+            public void run() {
+                mStatusText.setText(result);
+                setProgressBarIndeterminateVisibility(false);
+                mCheckLicenseButton.setEnabled(true);
+            }
+        });
+    }
+</pre>
+
+<h3 id="lc-lcc">Instantiate LicenseChecker and LicenseCheckerCallback</h3>
+
+<p>In the main Activity's
+{@link android.app.Activity#onCreate(android.os.Bundle) onCreate()} method,
+create private instances of LicenseCheckerCallback and {@code LicenseChecker}. You must
+instantiate {@code LicenseCheckerCallback} first, because you need to pass a reference
+to that instance when you call the constructor for {@code LicenseChecker}. </p>
+
+<p>When you instantiate {@code LicenseChecker}, you need to pass in these parameters:</p>
+
+<ul>
+<li>The application {@link android.content.Context}</li>
+<li>A reference to the {@code Policy} implementation to use for the license check. In
+most cases, you would use the default {@code Policy} implementation provided by the LVL,
+ServerManagedPolicy. </li>
+<li>The String variable holding your publisher account's public key for
+licensing. </li>
+</ul>
+
+<p>If you are using ServerManagedPolicy, you won't need to access the class
+directly, so you can instantiate it in the {@code LicenseChecker} constructor,
+as shown in the example below. Note that you need to pass a reference to a new
+Obfuscator instance when you construct ServerManagedPolicy.</p>
+
+<p>The example below shows the instantiation of {@code LicenseChecker} and
+{@code LicenseCheckerCallback} from the <code>onCreate()</code> method of an Activity
+class. </p>
+
+<pre>public class MainActivity extends Activity {
+    ...
+    private LicenseCheckerCallback mLicenseCheckerCallback;
+    private LicenseChecker mChecker;
+
+    &#64;Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        ...
+        // Construct the LicenseCheckerCallback. The library calls this when done.
+        mLicenseCheckerCallback = new MyLicenseCheckerCallback();
+
+        // Construct the LicenseChecker with a Policy.
+        mChecker = new LicenseChecker(
+            this, new ServerManagedPolicy(this,
+                new AESObfuscator(SALT, getPackageName(), deviceId)),
+            BASE64_PUBLIC_KEY  // Your public licensing key.
+            );
+        ...
+    }
+}
+</pre>
+
+
+<p>Note that {@code LicenseChecker} calls the {@code LicenseCheckerCallback} methods from the UI
+thread <em>only</em> if there is valid license response cached locally. If the
+license check is sent to the server, the callbacks always originate from the
+background thread, even for network errors. </p>
+
+
+<h3 id="check-access">Call checkAccess() to initiate the license check</h3>
+
+<p>In your main Activity, add a call to the <code>checkAccess()</code> method of the
+{@code LicenseChecker} instance. In the call, pass a reference to your
+{@code LicenseCheckerCallback} instance as a parameter. If you need to handle any
+special UI effects or state management before the call, you might find it useful
+to call <code>checkAccess()</code> from a wrapper method. For example, the LVL
+sample application calls <code>checkAccess()</code> from a
+<code>doCheck()</code> wrapper method:</p>
+
+<pre>    &#64;Override
+    public void onCreate(Bundle savedInstanceState) {
+        super.onCreate(savedInstanceState);
+        ...
+        // Call a wrapper method that initiates the license check
+        doCheck();
+        ...
+    }
+    ...
+    private void doCheck() {
+        mCheckLicenseButton.setEnabled(false);
+        setProgressBarIndeterminateVisibility(true);
+        mStatusText.setText(R.string.checking_license);
+        mChecker.checkAccess(mLicenseCheckerCallback);
+    }
+</pre>
+
+
+<h3 id="account-key">Embed your public key for licensing</h3>
+
+<p>For each publisher account, the Android Market service automatically
+generates a  2048-bit RSA public/private key pair that is used exclusively for
+licensing. The key pair is uniquely associated with the publisher account and is
+shared across all applications that are published through the account. Although
+associated with a publisher account, the key pair is <em>not</em> the same as
+the key that you use to sign your applications (or derived from it).</p>
+
+<p>The Android Market publisher site exposes the public key for licensing to any
+developer signed in to the publisher account, but it keeps the private key
+hidden from all users in a secure location. When an application requests a
+license check for an application published in your account, the licensing server
+signs the license response using the private key of your account's key pair.
+When the LVL receives the response, it uses the public key provided by the
+application to verify the signature of the license response. </p>
+
+<p>To add licensing to an application, you must obtain your publisher account's
+public key for licensing and copy it into your application. Here's how to find
+your account's public key for licensing:</p>
+
+<ol>
+<li>Go to the Android Market <a
+href="http://market.android.com/publish">publisher site</a> and sign in.
+Make sure that you sign in to the account from which the application you are
+licensing is published (or will be published). </li>
+<li>In the account home page, locate the "Edit profile" link and click it. </li>
+<li>In the Edit Profile page, locate the "Licensing" pane, shown below. Your
+public key for licensing is given in the "Public key" text box. </li>
+</ol>
+
+<p>To add the public key to your application, simply copy/paste the key string
+from the text box into your application as the value of the String variable
+<code>BASE64_PUBLIC_KEY</code>. When you are copying, make sure that you have
+selected the entire key string, without omitting any characters. </p>
+
+<p>Here's an example from the LVL sample application:</p>
+
+<pre>    public class MainActivity extends Activity {
+        private static final String BASE64_PUBLIC_KEY = "MIIBIjANBgkqhkiG ... "; //truncated for this example
+    ...
+    }
+</pre>
+
+<h3 id="handler-cleanup">Call your LicenseChecker's onDestroy() method
+to close IPC connections</h3>
+
+<p>Finally, to let the LVL clean up before your application
+{@link android.content.Context} changes, add a call to the {@code LicenseChecker}'s
+<code>onDestroy()</code> method from your Activity's
+{@link android.app.Activity#onDestroy()} implementation. The call causes the
+{@code LicenseChecker} to properly close any open IPC connection to the Android Market
+application's ILicensingService and removes any local references to the service
+and handler.</p>
+
+<p>Failing to call the {@code LicenseChecker}'s <code>onDestroy()</code> method
+can lead to problems over the lifecycle of your application. For example, if the
+user changes screen orientation while a license check is active, the application
+{@link android.content.Context} is destroyed. If your application does not
+properly close the {@code LicenseChecker}'s IPC connection, your application will crash
+when the response is received. Similarly, if the user exits your application
+while a license check is in progress,  your application will crash when the
+response is received, unless it has properly called the
+{@code LicenseChecker}'s <code>onDestroy()</code> method to disconnect from the service.
+</p>
+
+<p>Here's an example from the sample application included in the LVL, where
+<code>mChecker</code> is the {@code LicenseChecker} instance:</p>
+
+<pre>    &#64;Override
+    protected void onDestroy() {
+        super.onDestroy();
+        mChecker.onDestroy();
+        ...
+    }
+</pre>
+
+<p>If you are extending or modifying {@code LicenseChecker}, you might also need to call
+the {@code LicenseChecker}'s <code>finishCheck()</code> method, to clean up any open IPC
+connections.</p>
+
+<h2 id="impl-DeviceLimiter">Implementing a DeviceLimiter</h2>
+
+<p>In some cases, you might want your {@code Policy} to limit the number of actual
+devices that are permitted to use a single license. This would prevent a user
+from moving a licensed application onto a number of devices and using the
+application on those devices under the same account ID. It would also prevent a
+user from "sharing" the application by providing the account information
+associated with the license to other individuals, who could then sign in to that
+account on their devices and access the license to the application. </p>
+
+<p>The LVL supports per-device licensing by providing a
+<code>DeviceLimiter</code> interface, which declares a single method,
+<code>allowDeviceAccess()</code>. When a LicenseValidator is handling a response
+from the licensing server, it calls <code>allowDeviceAccess()</code>, passing a
+user ID string extracted from the response.</p>
+
+<p>If you do not want to support device limitation, <strong>no work is
+required</strong> &mdash; the {@code LicenseChecker} class automatically uses a default
+implementation called NullDeviceLimiter. As the name suggests, NullDeviceLimiter
+is a "no-op" class whose <code>allowDeviceAccess()</code> method simply returns
+a <code>LICENSED</code> response for all users and devices. </p>
+
+<div style="border-left:4px solid #FFCF00;margin:1em;padding: 0 0 0 .5em">
+<p><strong>Caution:</strong> Per-device licensing is <em>not recommended for
+most applications</em> because:</p>
+<ul>
+<li>It requires that you provide a backend server to manage a users and devices
+mapping, and </li>
+<li>It could inadvertently result in a user being denied access to an
+application that they have legitimately purchased on another device.</li>
+</ul>
+</div>
+
+
+
+
+
+
+
+
+
+
+
+<h2 id="app-obfuscation">Obfuscating Your Code</h2>
+
+<p>To ensure the security of your application, particularly for a paid
+application that uses licensing and/or custom constraints and protections, it's
+very important to obfuscate your application code. Properly obfuscating your
+code makes it more difficult for a malicious user to decompile the application's
+bytecode, modify it &mdash; such as by removing the license check &mdash;
+and then recompile it.</p>
+
+<p>Several obfuscator programs are available for Android applications, including
+<a href="http://proguard.sourceforge.net/">ProGuard</a>, which also offers
+code-optimization features. The use of ProGuard or a similar program to obfuscate
+your code is <em>strongly recommended</em> for all applications that use Android
+Market Licensing. </p>
+
+<h2 id="app-publishing">Publishing a Licensed Application</h2>
+
+<p>When you are finished testing your license implementation, you are ready to
+publish the application on Android Market. Follow the normal steps to <a
+href="{@docRoot}guide/publishing/preparing.html">prepare</a>, <a
+href="{@docRoot}guide/publishing/app-signing.html">sign</a>, and then <a
+href="{@docRoot}guide/publishing/publishing.html">publish the application</a>.
+</p>
+
+<h3>Removing Copy Protection</h3>
+
+<p>After uploading your licensed application, remember to remove copy protection
+from the application, if it is currently used. To check and remove copy
+protection, sign in to the publisher site and go the application's upload
+details page. In the Publishing options section, make sure that the Copy
+Protection radio button selection is "Off".</p>
+
+
+<h2 id="support">Where to Get Support</h2>
+
+<p>If you have questions or encounter problems while implementing or deploying
+publishing in your applications, please use the support resources listed in the
+table below. By directing your queries to the correct forum, you can get the
+support you need more quickly. </p>
+
+<p class="table-caption"><strong>Table 2.</strong> Developer support resources
+for Android Market Licensing Service.</p>
+
+<table>
+
+<tr>
+<th>Support Type</th>
+<th>Resource</th>
+<th>Range of Topics</th>
+</tr>
+<tr>
+<td rowspan="2">Development and testing issues</td>
+<td>Google Groups: <a
+href="http://groups.google.com/group/android-developers">android-developers</a>
+</td>
+<td rowspan="2">LVL download and integration, library projects, {@code Policy}
+questions, user experience ideas, handling of responses, {@code Obfuscator}, IPC, test
+environment setup</td>
+</tr>
+<tr>
+<td>Stack Overflow: <a
+href="http://stackoverflow.com/questions/tagged/android">http://stackoverflow.com/questions/tagged/android</a></td>
+</tr>
+<tr>
+<td rowspan="2">Accounts, publishing, and deployment issues</td>
+<td><a href="http://www.google.com/support/forum/p/Android+Market">Android
+Market Help Forum</a></td>
+<td rowspan="2">Publisher accounts, licensing key pair, test accounts, server
+responses, test responses, application deployment and results</td>
+</tr>
+<tr>
+<td><a
+href="http://market.android.com/support/bin/answer.py?answer=186113">Market
+Licensing Support FAQ</a></td>
+</tr>
+<tr>
+<td>LVL issue tracker</td>
+<td><a href="http://code.google.com/p/marketlicensing/issues/">Marketlicensing
+project issue tracker</a></td>
+<td>Bug and issue reports related specifically to the LVL source code classes
+and interface implementations</td>
+</tr>
+
+</table>
+
+<p>For general information about how to post to the groups listed above, see <a
+href="{@docRoot}resources/community-groups.html">Developer Forums</a> document
+in the Resources tab.</p>
+
+
diff --git a/docs/html/guide/market/licensing/index.jd b/docs/html/guide/market/licensing/index.jd
new file mode 100644
index 0000000..f08176d
--- /dev/null
+++ b/docs/html/guide/market/licensing/index.jd
@@ -0,0 +1,61 @@
+page.title=Application Licensing
+@jd:body
+
+
+<p>Android Market offers a licensing service that lets you enforce licensing policies for
+applications that you publish on Android Market. With Android Market Licensing, your application can
+query Android Market at run time to obtain the licensing status for the current user, then allow or
+disallow further use as appropriate. </p>
+
+<p>Using the service, you can apply a flexible licensing policy on an application-by-application
+basis&mdash;each application can enforce licensing in the way most appropriate for it. If necessary,
+an application can apply custom constraints based on the licensing status obtained from Android
+Market. For example, an application can check the licensing status and then apply custom constraints
+that allow the user to run it unlicensed for a specific validity period. An application can also
+restrict use of the application to a specific device, in addition to any other constraints. </p>
+
+<p>The licensing service is a secure means of controlling access to your applications. When an
+application checks the licensing status, the Android Market server signs the licensing status
+response using a key pair that is uniquely associated with the publisher account. Your application
+stores the public key in its compiled <code>.apk</code> file and uses it to verify the licensing
+status response.</p>
+
+<p>Any application that you publish through Android Market can use the Android Market Licensing
+service. No special account or registration is needed. Additionally, because the service uses no
+dedicated framework APIs, you can add licensing to any application that uses a minimum API level of
+3 or higher.</p>
+
+<p class="note"><strong>Note:</strong> The Android Market Licensing service is primarily intended
+for paid applications that wish to verify that the current user did in fact pay for the application
+on Android Market. However, any application (including free apps) may use the licensing service
+to initiate the download of an APK expansion file. In which case, the request that your application
+sends to the licensing service is not to check whether the user paid for the app, but to request the
+URL of the expansion files. For information about downloading expansion files for your application,
+read the guide to <a href="{@docRoot}guide/market/expansion-files.html">APK Expansion Files</a>.</p>
+
+
+<p>To learn more about Android Market's application licensing service and start integrating it into
+your applications, read the following documents:</p>
+
+<dl>
+  <dt><strong><a href="{@docRoot}guide/market/licensing/overview.html">Licensing
+Overview</a></strong></dt>
+    <dd>Describes how the service works and what a typical licensing implementation looks
+like.</dd>
+  <dt><strong><a href="{@docRoot}guide/market/licensing/setting-up.html">Setting Up for
+Licensing</a></strong></dt>
+    <dd>Explains how to set up your Android Market account, development environment, and
+testing environment in order to add licensing to your app.</dd>
+  <dt><strong><a href="{@docRoot}guide/market/licensing/adding-licensing.html">Adding
+Licensing to Your App</a></strong></dt>
+    <dd>Provides a step-by-step guide to add licensing verification to your application.</dd>
+  <dt><strong><a href="{@docRoot}guide/market/licensing/licensing-reference.html">Licensing
+Reference</a></strong></dt>
+    <dd>Provides detailed information about the licensing library's classes and the service response
+codes.</dd>
+</dl>
+
+
+
+
+
diff --git a/docs/html/guide/market/licensing/licensing-reference.jd b/docs/html/guide/market/licensing/licensing-reference.jd
new file mode 100644
index 0000000..ac5d596
--- /dev/null
+++ b/docs/html/guide/market/licensing/licensing-reference.jd
@@ -0,0 +1,439 @@
+page.title=Licensing Reference
+parent.title=Application Licensing
+parent.link=index.html
+@jd:body
+
+
+
+<div id="qv-wrapper">
+<div id="qv">
+  
+  <h2>In this document</h2>
+  <ol>
+    <li><a href="#lvl-summary">LVL Classes and Interfaces</a></li>
+    <li><a href="#server-response-codes">Server Response Codes</a></li>
+    <li><a href="#extras">Server Response Extras</a></li>
+  </ol>
+
+</div>
+</div>
+
+
+<h2 id="lvl-summary">LVL Classes and Interfaces</h2>
+
+<p>Table 1 lists all of the source files in the License Verification
+Library (LVL) available through the Android SDK. All of the files are part of
+the <code>com.android.vending.licensing</code> package.</p>
+
+<p class="table-caption"><strong>Table 1.</strong> Summary of LVL library
+classes and interfaces.</p>
+
+<div style="width:99%">
+<table width="100%">
+
+<tr>
+<th width="15%">Category</th>
+<th width="20%">Name</th>
+<th width="100%">Description</th>
+</tr>
+
+<tr>
+<td rowspan="2">License check and result</td>
+<td>LicenseChecker</td>
+<td>Class that you instantiate (or subclass) to initiate a license check.</td>
+</tr>
+<tr>
+<td><em>LicenseCheckerCallback</em></td>
+<td>Interface that you implement to handle result of the license check.</td>
+</tr>
+
+<tr>
+<td rowspan="3" width="15%">Policy</td>
+<td width="20%"><em>Policy</em></td>
+<td width="100%">Interface that you implement to determine whether to allow
+access to the application, based on the license response. </td>
+</tr>
+<tr>
+<td>ServerManagedPolicy</td>
+<td width="100%">Default {@code Policy} implementation. Uses settings provided by the
+licensing server to manage local storage of license data, license validity,
+retry.</td>
+</tr>
+<tr>
+<td>StrictPolicy</td>
+<td>Alternative {@code Policy} implementation. Enforces licensing based on a direct
+license response from the server only. No caching or request retry.</td>
+</tr>
+
+<tr>
+<td rowspan="2" width="15%">Data obfuscation <br><em>(optional)</em></td>
+<td width="20%"><em>Obfuscator</em></td>
+<td width="100%">Interface that you implement if you are using a {@code Policy} (such as
+ServerManagedPolicy) that caches license response data in a persistent store.
+Applies an obfuscation algorithm to encode and decode data being written or
+read.</td>
+</tr>
+<tr>
+<td>AESObfuscator</td>
+<td>Default Obfuscator implementation that uses AES encryption/decryption
+algorithm to obfuscate/unobfuscate data.</td>
+</tr>
+
+<tr>
+<td rowspan="2" width="15%">Device limitation<br><em>(optional)</em></td>
+<td width="20%"><em>DeviceLimiter</em></td>
+<td width="100%">Interface that you implement if you want to restrict use of an
+application to a specific device. Called from LicenseValidator. Implementing
+DeviceLimiter is not recommended for most applications because it requires a
+backend server and may cause the user to lose access to licensed applications,
+unless designed with care.</td>
+</tr>
+<tr>
+<td>NullDeviceLimiter</td>
+<td>Default DeviceLimiter implementation that is a no-op (allows access to all
+devices).</td>
+</tr>
+
+<tr>
+<td rowspan="6" width="15%">Library core, no integration needed</td>
+<td width="20%">ResponseData</td>
+<td width="100%">Class that holds the fields of a license response.</td>
+</tr>
+<tr>
+<td>LicenseValidator</td>
+<td>Class that decrypts and verifies a response received from the licensing
+server.</td>
+</tr>
+<tr>
+<td>ValidationException</td>
+<td>Class that indicates errors that occur when validating the integrity of data
+managed by an Obfuscator.</td>
+</tr>
+<tr>
+<td>PreferenceObfuscator</td>
+<td>Utility class that writes/reads obfuscated data to the system's
+{@link android.content.SharedPreferences} store.</td>
+</tr>
+<tr>
+<td><em>ILicensingService</em></td>
+<td>One-way IPC interface over which a license check request is passed to the
+Android Market client.</td>
+</tr>
+<tr>
+<td><em>ILicenseResultListener</em></td>
+<td>One-way IPC callback implementation over which the application receives an
+asynchronous response from the licensing server.</td>
+</tr>
+
+</table>
+</div>
+
+
+<h2 id="server-response-codes">Server Response Codes</h2>
+
+<p>Table 2 lists all of the license response codes supported by the
+licensing server. In general, an application should handle all of these response
+codes. By default, the LicenseValidator class in the LVL provides all of the
+necessary handling of these response codes for you. </p>
+
+<p class="table-caption"><strong>Table 2.</strong> Summary of response codes
+returned by the Android Market server in a license response.</p>
+
+<table>
+
+<tr>
+<th>Response Code</th>
+<th>Description</th>
+<th>Signed?</th>
+<th>Extras</th>
+<th>Comments</th>
+</tr>
+<tr>
+<td>{@code LICENSED}</td>
+<td>The application is licensed to the user. The user has purchased the
+application or the application only exists as a draft.</td>
+<td>Yes</td>
+<td><code>VT</code>,&nbsp;<code>GT</code>, <code>GR</code></td>
+<td><em>Allow access according to {@code Policy} constraints.</em></td>
+</tr>
+<tr>
+<td>{@code LICENSED_OLD_KEY}</td>
+<td>The application is licensed to the user, but there is an updated application
+version available that is signed with a different key. </td>
+<td>Yes </td>
+<td><code>VT</code>, <code>GT</code>, <code>GR</code>, <code>UT</code></td>
+<td><em>Optionally allow access according to {@code Policy} constraints.</em>
+<p style="margin-top:.5em;">Can indicate that the key pair used by the installed
+application version is invalid or compromised. The application can allow access
+if needed or inform the user that an upgrade is available and limit further use
+until upgrade.</p>
+</td>
+</tr>
+<tr>
+<td>{@code NOT_LICENSED}</td>
+<td>The application is not licensed to the user.</td>
+<td>No</td>
+<td></td>
+<td><em>Do not allow access.</em></td>
+</tr>
+<tr>
+<td>{@code ERROR_CONTACTING_SERVER}</td>
+<td>Local error &mdash; the Android Market application was not able to reach the
+licensing server, possibly because of network availability problems. </td>
+<td>No</td>
+<td></td>
+<td><em>Retry the license check according to {@code Policy} retry limits.</em></td>
+</tr>
+<tr>
+<td>{@code ERROR_SERVER_FAILURE}</td>
+<td>Server error &mdash; the server could not load the publisher account's key
+pair for licensing.</td>
+<td>No</td>
+<td></td>
+<td><em>Retry the license check according to {@code Policy} retry limits.</em>
+</td>
+</tr>
+<tr>
+<td>{@code ERROR_INVALID_PACKAGE_NAME}</td>
+<td>Local error &mdash; the application requested a license check for a package
+that is not installed on the device. </td>
+<td>No </td>
+<td></td>
+<td><em>Do not retry the license check.</em>
+<p style="margin-top:.5em;">Typically caused by a development error.</p>
+</td>
+</tr>
+<tr>
+<td>{@code ERROR_NON_MATCHING_UID}</td>
+<td>Local error &mdash; the application requested a license check for a package
+whose UID (package, user ID pair) does not match that of the requesting
+application. </td>
+<td>No </td>
+<td></td>
+<td><em>Do not retry the license check.</em>
+<p style="margin-top:.5em;">Typically caused by a development error.</p>
+</td>
+</tr>
+<tr>
+<td>{@code ERROR_NOT_MARKET_MANAGED}</td>
+<td>Server error &mdash; the application (package name) was not recognized by
+Android Market. </td>
+<td>No</td>
+<td></td>
+<td><em>Do not retry the license check.</em>
+<p style="margin-top:.5em;">Can indicate that the application was not published
+through Android Market or that there is an development error in the licensing
+implementation.</p>
+</td>
+</tr>
+
+</table>
+
+<p class="note"><strong>Note:</strong> As documented in <a
+href="{@docRoot}guide/market/licensing/setting-up.html#test-env">
+Setting Up The Testing Environment</a>, the response code can be manually
+overridden for the application developer and any registered test users via the
+Android Market publisher site.
+<br/><br/>
+Additionally, as noted above, applications that are in draft mode (in other
+words, applications that have been uploaded but have <em>never</em> been
+published) will return {@code LICENSED} for all users, even if not listed as a test
+user. Since the application has never been offered for download, it is assumed
+that any users running it must have obtained it from an authorized channel for
+testing purposes.</p>
+
+
+
+
+<h2 id="extras">Server Response Extras</h2>
+
+<p>To assist your application in managing access to the application across the application refund
+period and provide other information, The licensing server includes several pieces of
+information in the license responses. Specifically, the service provides recommended values for the
+application's license validity period, retry grace period, maximum allowable retry count, and other
+settings. If your application uses <a href="{@docRoot}guide/market/expansion-files.html">APK
+expansion files</a>, the response also includes the file names, sizes, and URLs. The server appends
+the settings as key-value pairs in the license response "extras" field. </p>
+
+<p>Any {@code Policy} implementation can extract the extras settings from the license
+response and use them as needed. The LVL default {@code Policy} implementation, <a
+href="{@docRoot}guide/market/licensing/adding-licensing.html#ServerManagedPolicy">{@code
+ServerManagedPolicy}</a>, serves as a working
+implementation and an illustration of how to obtain, store, and use the
+settings. </p>
+
+<p class="table-caption"><strong>Table 3.</strong> Summary of
+license-management settings supplied by the Android Market server in a license
+response.</p>
+
+<table>
+<tr>
+<th>Extra</th><th>Description</th>
+</tr>
+
+<tr>
+  <td>{@code VT}</td>
+  <td>License validity timestamp. Specifies the date/time at which the current
+(cached) license response expires and must be rechecked on the licensing server. See the section
+below about <a href="#VT">License validity period</a>.
+ </td>
+</tr>
+<tr>
+  <td>{@code GT}</td>
+  <td>Grace period timestamp. Specifies the end of the period during which a
+Policy may allow access to the application, even though the response status is
+{@code RETRY}. <p>The value is managed by the server, however a typical value would be 5
+or more days. See the section
+below about <a href="#GTGR">Retry period and maximum retry count</a>.</p></td>
+</tr>
+<tr>
+  <td>{@code GR}</td>
+  <td>Maximum retries count. Specifies how many consecutive {@code RETRY} license checks
+the {@code Policy} should allow, before denying the user access to the application.
+<p>The value is managed by the server, however a typical value would be "10" or
+higher. See the section
+below about <a href="#GTGR">Retry period and maximum retry count</a>.</p></td>
+</tr>
+<tr>
+  <td>{@code UT}</td>
+  <td>Update timestamp. Specifies the day/time when the most recent update to
+this application was uploaded and published. <p>The server returns this extra
+only for {@code LICENSED_OLD_KEYS} responses, to allow the {@code Policy} to determine how much
+time has elapsed since an update was published with new licensing keys before
+denying the user access to the application. </p></td>
+</tr>
+
+
+<!-- APK EXPANSION FILE RESPONSES -->
+
+<tr>
+  <td>{@code FILE_URL1} or {@code FILE_URL2}</td>
+  <td>The URL for an expansion file (1 is for the main file, 2 is the patch file). Use this to
+download the file over HTTP.</td>
+</tr>
+<tr>
+  <td>{@code FILE_NAME1} or {@code FILE_NAME2}</td>
+  <td>The expansion file's name (1 is for the main file, 2 is the patch file). You must use this
+name when saving the file on the device.</td>
+</tr>
+<tr>
+  <td>{@code FILE_SIZE1} or {@code FILE_SIZE2}</td>
+  <td>The size of the file in bytes (1 is for the main file, 2 is the patch file). Use this to
+assist with downloading and to ensure that enough space is available on the device's shared
+storage location before downloading.</td>
+</tr>
+
+</table>
+
+
+
+<h4 id="VT">License validity period</h4>
+
+<p>The Android Market licensing server sets a license validity period for all
+downloaded applications. The period expresses the interval of time over which an
+application's license status should be considered as unchanging and cacheable by
+a licensing {@code Policy} in the application. The licensing server includes the
+validity period in its response to all license checks, appending an
+end-of-validity timestamp to the response as an extra under the key {@code VT}. A
+{@code Policy} can extract the VT key value and use it to conditionally allow access to
+the application without rechecking the license, until the validity period
+expires. </p>
+
+<p>The license validity signals to a licensing {@code Policy} when it must recheck the
+licensing status with the licensing server. It is <em>not</em> intended to imply
+whether an application is actually licensed for use. That is, when an
+application's license validity period expires, this does not mean that the
+application is no longer licensed for use &mdash; rather, it indicates only that
+the {@code Policy} must recheck the licensing status with the server. It follows that,
+as long as the license validity period has not expired, it is acceptable for the
+{@code Policy} to cache the initial license status locally and return the cached license
+status instead of sending a new license check to the server.</p>
+
+<p>The licensing server manages the validity period as a means of helping the
+application properly enforce licensing across the refund period offered by
+Android Market for paid applications. It sets the validity period based on
+whether the application was purchased and, if so, how long ago. Specifically,
+the server sets a validity period as follows:</p>
+
+<ul>
+<li>For a paid application, the server sets the initial license validity period
+so that the license response remains valid for as long as the application is
+refundable. A licensing {@code Policy} in the application may cache the
+result of the initial license check and does not need to recheck the license
+until the validity period has expired.</li>
+<li>When an application is no longer refundable, the server
+sets a longer validity period &mdash; typically a number of days. </li>
+
+<!-- TODO: Verify the following behavior is still true w/ OBB: -->
+<li>For a free application, the server sets the validity period to a very high
+value (<code>long.MAX_VALUE</code>). This ensures that, provided the {@code Policy} has
+cached the validity timestamp locally, it will not need to recheck the
+license status of the application in the future.</li>
+</ul>
+
+<p>The {@code ServerManagedPolicy} implementation uses the extracted timestamp
+(<code>mValidityTimestamp</code>) as a primary condition for determining whether
+to recheck the license status with the server before allowing the user access to
+the application. </p>
+
+
+<h4 id="GTGR">Retry period and maximum retry count</h4>
+
+<p>In some cases, system or network conditions can prevent an application's
+license check from reaching the licensing server, or prevent the server's
+response from reaching the Android Market client application. For example, the
+user might launch an application when there is no cell network or data
+connection available&mdash;such as when on an airplane&mdash;or when the
+network connection is unstable or the cell signal is weak. </p>
+
+<p>When network problems prevent or interrupt a license check, the Android
+Market client notifies the application by returning a {@code RETRY} response code to
+the {@code Policy}'s <code>processServerResponse()</code> method. In the case of system
+problems, such as when the application is unable to bind with Android Market's
+{@code ILicensingService} implementation, the {@code LicenseChecker} library itself calls the
+Policy <code>processServerResonse()</code> method with a {@code RETRY} response code.
+</p>
+
+<p>In general, the {@code RETRY} response code is a signal to the application that an
+error has occurred that has prevented a license check from completing.
+
+<p>The Android Market server helps an application to manage licensing under
+error conditions by setting a retry "grace period" and a recommended maximum
+retries count. The server includes these values in all license check responses,
+appending them as extras under the keys {@code GT} and {@code GR}. </p>
+
+<p>The application {@code Policy} can extract the {@code GT} and {@code GR} extras and use them to
+conditionally allow access to the application, as follows:</p>
+
+<ul>
+<li>For a license check that results in a {@code RETRY} response, the {@code Policy} should
+cache the {@code RETRY} response code and increment a count of {@code RETRY} responses.</li>
+<li>The {@code Policy} should allow the user to access the application, provided that
+either the retry grace period is still active or the maximum retries count has
+not been reached.</li>
+</ul>
+
+<p>The {@code ServerManagedPolicy} uses the server-supplied {@code GT} and {@code GR} values as
+described above. The example below shows the conditional handling of the retry
+responses in the <code>allow()</code> method. The count of {@code RETRY} responses is
+maintained in the <code>processServerResponse()</code> method, not shown. </p>
+
+
+<pre>    
+public boolean allowAccess() {
+    long ts = System.currentTimeMillis();
+    if (mLastResponse == LicenseResponse.LICENSED) {
+        // Check if the LICENSED response occurred within the validity timeout.
+        if (ts &lt;= mValidityTimestamp) {
+            // Cached LICENSED response is still valid.
+            return true;
+        }
+    } else if (mLastResponse == LicenseResponse.RETRY &amp;&amp;
+                ts &lt; mLastResponseTime + MILLIS_PER_MINUTE) {
+        // Only allow access if we are within the retry period or we haven't used up our
+        // max retries.
+        return (ts &lt;= mRetryUntil || mRetryCount &lt;= mMaxRetries);
+    }
+    return false;
+}</pre>
+
diff --git a/docs/html/guide/market/licensing/overview.jd b/docs/html/guide/market/licensing/overview.jd
new file mode 100644
index 0000000..3576e26
--- /dev/null
+++ b/docs/html/guide/market/licensing/overview.jd
@@ -0,0 +1,245 @@
+page.title=Licensing Overview
+parent.title=Application Licensing
+parent.link=index.html
+@jd:body
+
+
+<div id="qv-wrapper">
+<div id="qv">
+  
+  <h2>Quickview</h2>
+  <ul>
+    <li>Licensing allows you to verify your app was purchased from Android Market</li>
+    <li>Your app maintains control of how it enforces its licensing status</li>
+    <li>The service is free for all developers who publish on Android Market</li>
+  </ul>
+  
+  <h2>In this document</h2>
+  <ol>
+  <li><a href="#Secure">License Responses are Secure</a></li>
+  <li><a href="#LVL">Licensing Verification Library</a></li>
+  <li><a href="#Reqs">Requirements and Limitations</a></li>
+  <li><a href="#CopyProtection">Replacement for Copy Protection</a></li>
+</ol>
+  
+</div>
+</div>
+
+
+<p>Android Market Licensing is a network-based service that lets an application query a trusted
+Android Market licensing server to determine whether the application is licensed to the current
+device user. The licensing service is based on the capability of the Android Market licensing server
+to determine whether a given user is licensed to use a given application. Android Market considers a
+user to be licensed if the user is a recorded purchaser of the application.</p>
+
+<p>The request starts when your application makes a request to a service hosted by
+the Android Market client application. The Android Market application then sends a request to
+the licensing server and receives the result. The Android Market application sends
+the result to your application, which can allow or disallow further use of the
+application as needed.</p>
+
+<p class="note"><strong>Note:</strong> If a paid application has been uploaded to Android Market but
+saved only as a draft application (the app is unpublished), the licensing server considers all users
+to be licensed users of the application (because it's not even possible to purchase the app).
+This exception is necessary in order for you to perform testing of your licensing
+implementation.</p>
+
+
+<div class="figure" style="width:469px">
+<img src="{@docRoot}images/licensing_arch.png" alt=""/>
+<p class="img-caption"><strong>Figure 1.</strong> Your application initiates a
+license check through the License Verification Library and the Android Market
+client, which handles communication with the Market server.</p>
+</div>
+
+
+<p>To properly identify the user and determine the license status, the licensing server requires
+information about the application and user&mdash;your application and the Android Market client work
+together to assemble the information and the Android Market client passes it to the server. </p>
+
+<p>To help you add licensing to your application, the Android SDK provides a downloadable set of
+library sources that you can include in your application project: the "Google Market Billing
+package." The License Verification Library (LVL) is a library you can add to your application that
+handles all of the licensing-related communication with the Android Market licensing service. With
+the LVL added to your application, your application can determine its licensing status for the
+current user by simply calling a method and implementing a callback that receives the status
+response.</p>
+
+<p>Your application does not query the licensing server
+directly, but instead calls the Android Market client over remote IPC to
+initiate a license request. In the license request:</p>
+
+<ul>
+<li>Your application provides: its package name, a nonce that is later used to
+validate any response from the server, and a callback over which the
+response can be returned asynchronously.</li>
+<li>The Android Market client collects the necessary information about the user and the device,
+such as the device's primary Google account username, IMSI, and other
+information. It then sends the license check request to the server on behalf of
+your application.</li>
+<li>The Android Market server evaluates the request using all available information, attempting
+to establish the user's identity to a sufficient level of confidence. The server
+then checks the user identity against purchase records for your application and
+returns a license response, which the Android Market client returns to your
+application over the IPC callback.</li>
+</ul>
+
+<p>You can choose when, and how often, you want your application to check its
+license and you have full control over how it handles the response, verifies the
+signed response data, and enforces access controls.</p>
+
+<p>Notice that during a license check, your application does not manage any
+network connections or use any licensing related APIs in the Android platform.</p>
+
+
+
+
+<h2 id="Secure">License Responses are Secure</h2>
+
+<p>To ensure the integrity of each license query, the server signs the license
+response data using an RSA key pair that is shared exclusively between the Android Market
+server and you.</p>
+
+<p>The licensing service generates a single licensing key pair for each
+publisher account and exposes the public key in your account's profile page. You must copy the
+public key from the web site and embed it in your application source code. The server retains the
+private key internally and uses it to sign license responses for the applications you
+publish with that account.</p>
+
+<p>When your application receives a signed response, it uses the embedded public
+key to verify the data. The use of public key cryptography in the licensing
+service makes it possible for the application to detect responses that have been
+tampered with or that are spoofed.</p>
+
+
+
+
+<h2 id="LVL">Licensing Verification Library</h2>
+
+<p>The Android SDK provides a downloadable component called the "Google Market Licensing package,"
+which includes the License Verification Library (LVL). The LVL greatly simplifies the process of
+adding licensing to your application and helps ensure a more secure, robust implementation for your
+application. The LVL provides internal classes that handle most of the standard operations of a
+license query, such as contacting the Android Market client to initiate a license request and
+verifying and validating the responses. It also exposes interfaces that let you easily plug in your
+custom code for defining licensing policy and managing access as needed by your application. The key
+LVL interfaces are: </p>
+
+<dl>
+<dt>{@code Policy}</dt>
+  <dd>Your implementation determines whether to allow access to the
+application, based on the license response received from the server and any
+other data available (such as from a backend server associated with your
+application). The implementation can evaluate the various fields of the license
+response and apply other constraints, if needed. The implementation also lets
+you manage the handling of license checks that result in errors, such as network
+errors.</dd>
+
+<dt>{@code LicenseCheckerCallback}</dt>
+  <dd>Your implementation manages access to the
+application, based on the result of the {@code Policy} object's handling of the license
+response. Your implementation can manage access in any way needed, including
+displaying the license result in the UI or directing the user to purchase the
+application (if not currently licensed).</dd>
+</dl>
+
+
+<p>To help you get started with a {@code Policy}, the LVL provides two fully complete
+{@code Policy} implementations that you can use without modification or adapt to your
+needs:</p>
+
+<dl>
+<dt><a href="adding-licensing.html#ServerManagedPolicy">{@code ServerManagedPolicy}</a></dt>
+  <dd>A flexible {@code Policy}
+that uses settings provided by the licensing server to manage response caching
+and access to the application while the device is offline (such as when the
+user is on an airplane). For most applications, the use of
+{@code ServerManagedPolicy} is highly recommended.</dd>
+
+<dt><a href="adding-licensing.html#StrictPolicy">{@code StrictPolicy}</a></dt>
+  <dd>A restrictive {@code Policy} that
+does not cache any response data and allows the application access <em>only</em>
+when the server returns a licensed response.</dd>
+</dl>
+
+<p>The LVL is available as a downloadable component of the Android SDK. The
+component includes both the LVL itself and an example application that shows how
+the library should be integrated with your application and how your application
+should manage response data, UI interaction, and error conditions. </p>
+
+<p>The LVL sources are provided as an Android <em>library project</em>, which
+means that you can maintain a single set of library sources and share them
+across multiple applications. A full test environment is also available through
+the SDK, so you can develop and test the licensing implementation in your
+applications before publishing them, even if you don't have access to a
+physical device.</p>
+
+
+
+
+<h2 id="Reqs">Requirements and Limitations</h2>
+
+<p>Android Market Licensing is designed to let you apply license controls to
+applications that you publish through Android Market. The service is not
+designed to let you control access to applications that are not published
+through Android Market or that are run on devices that do not offer the Android
+Market client. </p>
+
+<p>Here are some points to keep in mind as you implement licensing in your
+application: </p>
+
+<ul>
+<li>An application can use the service only if the Android Market client is
+installed on its host device and the device is running Android 1.5 (API level 3)
+or higher.</li>
+<li>To complete a license check, the licensing server must be accessible over
+the network. You can implement license caching behaviors to manage access to your application when
+there is no network connectivity. </li>
+<li>The security of your application's licensing controls ultimately relies on
+the design of your implementation itself. The service provides the building
+blocks that let you securely check licensing, but the actual enforcement and
+handling of the license are factors are up to you. By following the best
+practices in the following documents, you can help ensure that your implementation will be
+secure.</li>
+<li>Adding licensing to an application does not affect the way the application
+functions when run on a device that does not offer Android Market.</li>
+<li>You can implement licensing controls for a free app, but only if you're using the service to 
+provide <a
+href="{@docRoot}guide/market/expansion-files.html">APK expansion files</a>.</li>
+</ul>
+
+
+
+<h2 id="CopyProtection">Replacement for Copy Protection</h2>
+
+<p>Android Market Licensing is a flexible, secure mechanism for controlling
+access to your applications. It effectively replaces the Copy Protection
+mechanism offered on Android Market and gives you wider distribution
+potential for your applications. </p>
+
+<ul>
+<li>A limitation of the legacy Copy Protection mechanism on Android Market is
+that applications using it can be installed only on compatible devices that
+provide a secure internal storage environment. For example, a copy-protected
+application cannot be downloaded from Market to a device that provides root
+access, and the application cannot be installed to a device's SD card. </li>
+<li>With Android Market licensing, you can move to a license-based model in
+which access is not bound to the characteristics of the host device, but to your
+publisher account on Android Market and the licensing policy that you define.
+Your application can be installed and controlled on any compatible device on
+any storage, including SD card.</li>
+</ul>
+
+<p>Although no license mechanism can completely prevent all unauthorized use,
+the licensing service lets you control access for most types of normal usage,
+across all compatible devices, locked or unlocked, that run Android 1.5 or
+higher version of the platform.</p>
+
+<p>To begin adding application licensing to your application, continue to <a
+href="{@docRoot}guide/market/licensing/setting-up.html">Setting Up for Licensing</a>.</p>
+
+
+
+
+
+
diff --git a/docs/html/guide/market/licensing/setting-up.jd b/docs/html/guide/market/licensing/setting-up.jd
new file mode 100644
index 0000000..c79f90b
--- /dev/null
+++ b/docs/html/guide/market/licensing/setting-up.jd
@@ -0,0 +1,707 @@
+page.title=Setting Up for Licensing
+parent.title=Application Licensing
+parent.link=index.html
+@jd:body
+
+
+<div id="qv-wrapper">
+<div id="qv">
+  
+  <h2>In this document</h2>
+  <ol>
+  <li><a href="#account">Setting Up a Publisher Account</a></li>
+  <li><a href="#dev-setup">Setting Up the Development Environment</a>
+    <ol>
+      <li><a href="#runtime-setup">Setting up the runtime environment</a></li>
+      <li><a href="#download-lvl">Downloading the LVL</a></li>
+      <li><a href="#lvl-setup">Setting Up the Licensing Verification Library</a></li>
+      <li><a href="#add-library">Including the LVL library project sources in your
+application</a></li>
+    </ol>
+  </li>
+  <li><a href="#test-env">Setting Up the Testing Environment</a>
+    <ol>
+      <li><a href="#test-response">Setting test responses for license checks</a></li>
+      <li><a href="#test-acct-setup">Setting up test accounts</a></li>
+      <li><a href="#acct-signin">Signing in to an authorized account in the runtime
+environment</a></li>
+    </ol>
+  </li>
+</ol>
+</div>
+</div>
+
+<p>Before you start adding license verification to your application, you need to set up your Android
+Market publishing account, your development environment, and test accounts required to verify
+your implementation.</p>
+
+
+<h2 id="account">Setting Up a Publisher Account</h2>
+
+<p>If you don't already have a publisher account for Android Market, you need to register for one
+using your Google account and agree to the terms of service on the Android Market publisher site:</p>
+
+<p style="margin-left:2em;"><a
+href="http://market.android.com/publish">http://market.android.com/publish</a>
+</p>
+
+<p>For more information, see <a
+href="{@docRoot}guide/publishing/publishing.html">Publishing on Android Market</a>.</p>
+
+<p>If you already have a publisher account on Android Market, use your existing
+account to set up licensing.</p>
+
+<p>Using your publisher account on Android Market, you can:</p>
+
+<ul>
+<li>Obtain a public key for licensing</li>
+<li>Debug and test an application's licensing implementation, prior to
+publishing the application</li>
+<li>Publish the applications to which you have added licensing support</li>
+</ul>
+
+<h4>Administrative settings for licensing</h4>
+
+<p>You can manage several
+administrative controls for Android Market licensing on the publisher site. The controls are available
+in the Edit Profile page, in the "Licensing" panel, shown in figure 1. The controls
+let you: </p>
+
+<ul>
+<li>Set up multiple "test accounts," identified by email address. The licensing
+server allows users signed in to test accounts on a device or emulator to send
+license checks and receive static test responses.</li>
+<li>Obtain the account's public key for licensing. When you are implementing
+licensing in an application, you must copy the public key string into the
+application.</li>
+<li>Configure static test responses that the server sends, when it receives a
+license check for an application uploaded to the publisher account, from a user
+signed in to the publisher account or a test account.</li>
+</ul>
+
+
+<img src="{@docRoot}images/licensing_public_key.png" alt=""/>
+<p class="img-caption"><strong>Figure 1.</strong> The Licensing
+panel of your account's Edit Profile page lets you manage administrative
+settings for licensing.</p>
+
+<p>For more information about how to work with test accounts and static test
+responses, see <a href="#test-env">Setting Up a Testing Environment</a>, below.
+
+
+
+<h2 id="dev-setup">Setting Up the Development Environment</h2>
+
+<p>Setting up your environment for licensing involves these tasks:</p>
+
+<ol>
+<li><a href="#runtime-setup">Setting up the runtime environment</a> for development</li>
+<li><a href="#download-lvl">Downloading the LVL</a> into your SDK </li>
+<li><a href="#lvl-setup">Setting up the Licensing Verification Library</a></li>
+<li><a href="#add-library">Including the LVL library project in your application</a></li>
+</ol>
+
+<p>The sections below describe these tasks. When you are done with setup,
+you can begin <a href="{@docRoot}guide/market/licensing/adding-licensing.html">Adding
+Licensing to Your App</a>.</p>
+
+<p>To get started, you need to set up a proper runtime environment on which
+you can run, debug, and test your application's implementation of license
+checking and enforcement. </p>
+
+
+<h3 id="runtime-setup">Setting up the runtime environment</h3>
+
+<p>As described earlier, applications check licensing status not by contacting
+the licensing server directly, but by binding to a service provided by the
+Android Market application and initiating a license check request. The Android
+Market service then handles the direct communication with the licensing server
+and finally routes the response back to your application. To debug and test
+licensing in your application, you need to set up a runtime environment that
+includes the necessary Android Market service, so that your application is able
+to send license check requests to the licensing server. </p>
+
+<p>There are two types of runtime environment that you can use: </p>
+
+<ul>
+<li>An Android-powered device that includes the Android Market application, or</li>
+<li>An Android emulator running the Google APIs Add-on, API level 8 (release 2)
+or higher</li>
+</ul>
+
+<h4 id="runtime-device">Running on a device</h4>
+
+<p>To use an Android-powered device for
+debugging and testing licensing, the device must:</p>
+
+<ul>
+<li>Run a compatible version of Android 1.5 or later (API level
+3 or higher) platform, <em>and</em> </li>
+<li>Run a system image on which the Android Market client application
+is preinstalled. </li>
+</ul>
+
+<p>If Android Market is not preinstalled in the system image, your application won't
+be able to communicate with the Android Market licensing server. </p>
+
+<p>For general information about how to set up a device for use in developing
+Android applications, see <a
+href="{@docRoot}guide/developing/device.html">Using Hardware Devices</a>.</p>
+
+<h4 id="runtime-emulator">Running on an Android emulator</h4>
+
+<p>If you don't have a device available, you can use an Android emulator for debugging and testing
+licensing.</p>
+
+<p>Because the Android platforms provided in the Android SDK <em>do
+not</em> include Android Market, you need to download the Google APIs Add-On
+platform, API level 8 (or higher), from the SDK repository. After downloading
+the add-on, you need to create an AVD configuration that uses that system image.
+</p>
+
+<p>The Google APIs Add-On does not include the full Android Market client.
+However, it does provide: </p>
+
+<ul>
+<li>An Android Market background service that implements the
+<code>ILicensingService</code> remote interface, so that your application can
+send license checks over the network to the licensing server. </li>
+<li>A set of underlying account services that let you add an a Google account on
+the AVD and sign in using your publisher account or test account credentials.
+<p>Signing in using your publisher or test account enables you to debug and test
+your application without having publish it. For more information see <a
+href="#acct-signin">Signing in to an authorized account</a>, below.</p></li>
+</ul>
+
+<p>Several versions of the add-on are available through the SDK Manager, but only
+<strong>Google APIs Add-On, API 8 (release 2) or higher</strong> includes the necessary Android
+Market services.</p>
+
+
+<img src="{@docRoot}images/licensing_gapis_8.png" alt=""/>
+<p class="img-caption"><strong>Figure 2.</strong> Google APIs
+Add-On, API 8 (release 2) or higher lets you debug and test your licensing
+implementation in an emulator.</p>
+
+<p>To set up an emulator for adding licensing to an application, follow
+these steps: </p>
+
+<ol>
+  <li>Launch the Android SDK Manager. </li>
+  <li>In the <strong>Available Packages</strong> panel, select and download the
+SDK component "Google APIs (Google Inc.) - API Level 8" (or higher) from the SDK
+repository, as shown in figure 2.
+  <p>When the download is complete, use the Android SDK Manager to
+create a new AVD based on that component, described next.</p></li>
+  <li>In the <strong>Virtual
+Devices</strong> panel of the Android SDK Manager, click
+<strong>New</strong> and set the configuration details for the new AVD. </li>
+  <li>In the dialog that appears, assign a descriptive name to the AVD and then
+use the "Target" menu to choose the "Google APIs (Google Inc.) - API Level 8" as
+the system image to run on the new AVD. Set the other configuration details as
+needed and then click <strong>Create AVD</strong> to finish. The SDK tools
+create the new AVD configuration, which then appears in the list of available
+Android Virtual Devices.</li>
+</ol>
+
+<p>If you are not familiar with AVDs or how to use them, see <a
+href="{@docRoot}guide/developing/devices/index.html">Managing Virtual Devices</a>.</p>
+
+<h4 id="project-update">Updating your project configuration</h4>
+
+<p>After you set up a runtime environment that meets the requirements described
+above &mdash; either on an actual device or on an emulator &mdash; make sure to
+update your application project or build scripts as needed, so that your compiled
+<code>.apk</code> files that use licensing are deployed into that environment.
+In particular, if you are developing in Eclipse, make sure that you set up a
+Run/Debug Configuration that targets the appropriate device or AVD. </p>
+
+<p>You do not need to make any changes to your application's
+build configuration, provided that the project is already configured to compile
+against a standard Android 1.5 (API level 3) or higher library. For example:
+
+<ul>
+<li>If you have an existing application that is compiled against
+the Android 1.5 library, you do not need to make any changes to your
+build configuration to support licensing. The build target meets the minimum
+requirements for licensing, so you would continue building
+against the same version of the Android platform.</li>
+
+<li>Similarly, if you are building against Android 1.5 (API level 3) but
+are using an emulator running the Google APIs Add-On API 8 as the application's
+runtime environment, there is no need to change your application's build
+configuration. </li>
+</ul>
+
+<p>In general, adding licensing to an application should have no impact
+whatsoever on the application's build configuration.</p>
+
+
+<h3 id="download-lvl">Downloading the LVL</h3>
+
+<p>The License Verification Library (LVL) is a collection of helper classes that
+greatly simplify the work that you need to do to add licensing to your
+application. In all cases, we recommend that you download the LVL and use it as
+the basis for the licensing implementation in your application.</p>
+
+<p>The LVL is available as a downloadable component of the Android SDK. The
+component includes: </p>
+
+<ul>
+<li>The LVL sources, stored inside an Android library project. </li>
+<li>An example application called "sample" that depends on the LVL library
+project. The example illustrates how an application uses the library helper
+classes to check and enforce licensing.</li>
+</ul>
+
+<p>To download the LVL component into your development environment, use the
+Android SDK Manager. Launch the Android SDK Manager and then
+select the "Market Licensing" component, as shown in figure 3.
+Accept the terms and click <strong>Install Selected</strong> to begin the download. </p>
+
+<img src="{@docRoot}images/licensing_package.png" alt=""/>
+<p class="img-caption"><strong>Figure 3.</strong> The Market Licensing package contains the LVL and
+the LVL sample application.</p>
+
+<p>When the download is complete, the Android SDK Manager installs both
+the LVL library project and the example application into these directories: </p>
+
+<p style="margin-left:2em"><code>&lt;<em>sdk</em>&gt;/extras/google/market_licensing/library/</code>
+&nbsp;&nbsp;(the LVL library project)<br />
+<code>&lt;<em>sdk</em>&gt;/extras/google/market_licensing/sample/</code>&nbsp;&nbsp;(the example
+application)</p>
+
+<p>If you aren't familiar with how to download components into your SDK, see the
+<a href="{@docRoot}sdk/adding-components.html">Adding SDK Components</a>
+document. </p>
+
+
+<h3 id="lvl-setup">Setting Up the Licensing Verification Library</h3>
+
+<p>After downloading the LVL to your computer, you need to set it up in your
+development environment, either as an Android library project or by
+copying (or importing) the library sources directly into your existing
+application package. In general, using the LVL as a library project is recommended,
+since it lets you reuse your licensing code across multiple applications and
+maintain it more easily over time. Note that the LVL is not designed to be
+compiled separately and added to an application as a static .jar file. </p>
+
+<h4>Moving the library sources to a new location</h4>
+
+<p>Because you will be customizing the LVL sources to some extent, you should
+make sure to <em>move or copy</em> the library sources (the entire
+directory at <code>&lt;<em>sdk</em>&gt;/market_licensing/library/</code>)
+to a working directory outside of the SDK. You should then use the relocated
+sources as your working set. If you are using a source-code management
+system, add and track the sources that are in the working location rather
+than those in default location in the SDK. </p>
+
+<p>Moving the library sources is important is because, when you later update the
+Market licensing package, the SDK installs the new files to the same location as
+the older files. Moving your working library files to a safe location ensures
+that your work won't be inadvertently overwritten should you download a new
+version of the LVL.</p>
+
+<h4>Creating the LVL as a library project</h4>
+
+<div class="sidebox-wrapper">
+<div class="sidebox">
+<h2>Working with library projects</h2>
+
+<p>The LVL is provided as an Android library project, which means that you can
+share its code and resources across multiple applications. </p>
+
+<p style="margin-top:.5em;">If you aren't familiar with library projects or how
+to use them, see <a href="{@docRoot}guide/developing/projects/index.html#LibraryProjects">
+Managing Projects</a>.
+</p>
+</div>
+</div>
+
+<p>The recommended way of using the LVL is setting it up as a new Android
+<em>library project</em>. A library project is a type of development project
+that holds shared Android source code and resources. Other Android application
+projects can reference the library project and, at build time, include its
+compiled sources in their <code>.apk</code> files. In the context of licensing,
+this means that you can do most of your licensing development once, in a library
+project, then include the library sources in your various application projects.
+In this way, you can easily maintain a uniform implementation of licensing
+across all of your projects and maintain it centrally. </p>
+
+<p>The LVL is provided as a configured library project &mdash; once you have
+downloaded it, you can start using it right away. </p>
+
+<p>If you are working in Eclipse with ADT, you need to add the LVL to your
+workspace as a new development project, in the same way as you would a new
+application project. </p>
+
+<ol>
+<li>Use the New Project Wizard to create a new
+project from existing sources. Select the LVL's <code>library</code> directory
+(the directory containing the library's AndroidManifest.xml file) as the project
+root.</li>
+<li>When you are creating the library project, you can select any application
+name, package, and set other fields as needed. </li>
+<li>For the library's build target, select Android 1.5 (API level 3) or higher.</li>
+</ol>
+
+<p> When created, the project is
+predefined as a library project in its <code>project.properties</code> file, so
+no further configuration is needed. </p>
+
+<p>For more information about how to create an application project or work with
+library projects in Eclipse, see <a
+href="{@docRoot}guide/developing/projects/projects-eclipse.html">Managing Projects from
+Eclipse with ADT</a>.</p>
+
+
+<h4>Copying the LVL sources to your application</h4>
+
+<p>As an alternative to adding the LVL as a library project, you can copy the
+library sources directly into your application. To do so, copy (or import) the
+LVL's <code>library/src/com</code> directory into your application's
+<code>src/</code> directory.</p>
+
+<p>If you add the LVL sources directly to your application, you can skip the
+next section and start working with the library, as described in <a
+href="{@docRoot}guide/market/licensing/adding-licensing.html">Adding
+Licensing to Your App</a>.</p>
+
+
+<h3 id="add-library">Including the LVL library project sources in your
+application</h3>
+
+<p>If you want to use the LVL sources as a library project, you need to add a
+reference to the LVL library project in your application project properties. This tells
+build tools to include the LVL library project sources in your application at
+compile time. The process for adding a reference to a library project depends
+on your development environment, as described below.</p>
+
+<p> If you are developing in Eclipse with ADT, you should already have added the
+library project to your workspace, as described in the previous section. If you
+haven't done that already, do it now before continuing. </p>
+
+<p>Next, open the application's project properties window, as shown below.
+Select the "Android" properties group and click <strong>Add</strong>, then
+choose the LVL library project (com_android_vending_licensing) and click
+<strong>OK</strong>. For more information, see
+<a href="{@docRoot}guide/developing/projects/projects-eclipse.html#SettingUpLibraryProject">
+Managing Projects from Eclipse with ADT</a></p>.
+
+
+<img src="{@docRoot}images/licensing_add_library.png" alt=""/>
+<p class="img-caption"><strong>Figure 4.</strong> If you are
+working in Eclipse with ADT, you can add the LVL library project to your
+application from the application's project properties.</p>
+
+
+<p>If you are developing using the SDK command-line tools, navigate to the
+directory containing your application project and open the
+<code>project.properties</code> file. Add a line to the file that specifies the
+<code>android.library.reference.&lt;n&gt;</code> key and the path to the
+library. For example: </p>
+
+<pre>android.library.reference.1=path/to/library_project</pre>
+
+<p>Alternatively, you can use this command to update the project
+properties, including the reference to the library project:</p>
+
+<pre class="no-pretty-print" style="color:black">android update lib-project
+--target <em>&lt;target_ID&gt;</em> \
+--path <em>path/to/my/app_project</em> \
+--library <em>path/to/my/library_project</em>
+</pre>
+
+<p>For more information about working with library projects,
+see <a href="{@docRoot}guide/developing/projects/projects-cmdline.html#SettingUpLibraryProject">
+Setting up a Library Project</a>.</p>
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+<h2 id="test-env">Setting Up the Testing Environment</h2>
+
+<p>The Android Market publisher site provides configuration tools that let you
+and others test licensing on your application before it is published. As you are
+implementing licensing, you can make use of the publisher site tools to test
+your application's Policy and handling of different licensing responses and
+error conditions.</p>
+
+<p>The main components of the test environment for licensing include: </p>
+
+<ul>
+<li>A "Test response" configuration in your publisher account that lets you
+set the static licensing response returned, when the server processes a
+license check for an application uploaded to the publisher account, from a user
+signed in to the publisher account or a test account.</li>
+<li>An optional set of test accounts that will receive the static test
+response when they check the license of an application that you have uploaded
+(regardless whether the application is published or not).</li>
+<li>A runtime environment for the application that includes the Android Market
+application or Google APIs Add-On, on which the user is signed in to the
+publisher account or one of the test accounts.</li>
+</ul>
+
+<p>Setting up the test environment properly involves:</p>
+
+<ol>
+<li><a href="#test-response">Setting static test responses</a> that are returned by the licensing server.</li>
+<li><a href="#test-acct-setup">Setting up test accounts</a> as needed.</li>
+<li><a href="#acct-signin">Signing in</a> properly to an emulator or device, before initiating a license check test.</li>
+</ol>
+
+<p>The sections below provide more information.</p>
+
+
+<h3 id="test-response">Setting test responses for license checks</h3>
+
+<p>Android Market provides a configuration setting in your publisher account
+that lets you override the normal processing of a license check and return a
+specified static response code. The setting is for testing only and applies
+<em>only</em> to license checks for applications that you have uploaded, made by
+any user signed in to an emulator or device using the credentials of the
+publisher account or a registered test account. For other users, the server
+always processes license checks according to normal rules.  </p>
+
+<p>To set a test response for your account, sign in to your publisher account
+and click "Edit Profile". In the Edit Profile page, locate the Test Response
+menu in the Licensing panel, shown below. You can select from the full set of
+valid server response codes to control the response or condition you want to
+test in your application.</p>
+
+<p>In general, you should make sure to test your application's licensing
+implementation with every response code available in the Test Response menu.
+For a description of the codes, see <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html#server-response-codes">Server
+Response Codes</a> in the <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html">Licensing Reference</a>.</p>
+
+<img src="{@docRoot}images/licensing_test_response.png" alt=""/>
+<p class="img-caption"><strong>Figure 5.</strong> The Licensing
+panel of your account's Edit Profile page, showing the Test Accounts field and the
+Test Response menu.</p>
+
+<p>Note that the test response that you configure applies account-wide &mdash;
+that is, it applies not to a single application, but to <em>all</em>
+applications associated with the publisher account. If you are testing multiple
+applications at once, changing the test response will affect all of those
+applications on their next license check (if the user is signed in to
+the emulator or device using the publisher account or a test account).</p>
+
+<p>Before you can successfully receive a test response for a license check,
+you must sign in to the device or emulator on which the application
+is installed, and from which it is querying the server. Specifically, you must
+sign using either your publisher account or one of the test accounts that you
+have set up. For more information about test accounts, see the next section.</p>
+
+<p>See <a
+href="{@docRoot}guide/market/licensing/licensing-reference.html#server-response-codes">Server
+Response Codes</a> for a list of
+test responses available and their meanings. </p>
+
+
+<h3 id="test-acct-setup">Setting up test accounts</h3>
+
+<p>In some cases, you might want to let multiple teams of developers test
+licensing on applications that will ultimately be published through your
+publisher account, but without giving them access to your publisher account's
+sign-in credentials. To meet that need, the Android Market publisher site lets
+you set up one or more optional <em>test accounts</em> &mdash; accounts that are
+authorized to query the licensing server and receive static test responses from
+your publisher account.</p>
+
+<p>Test accounts are standard Google accounts that you register on your
+publisher account, such that they will receive the test response for
+applications that you have uploaded. Developers can then sign in to their
+devices or emulators using the test account credentials and initiate license
+checks from installed applications. When the licensing server receives a license
+check from a user of a test account, it returns the static test response
+configured for the publisher account.  </p>
+
+<p>Necessarily, there are limitations on the access and permissions given to
+users signed in through test accounts, including:</p>
+
+<ul>
+<li>Test account users can query the licensing server only for applications that
+are already uploaded to the publisher account. </li>
+<li>Test account users do not have permission to upload applications to your
+publisher account.</li>
+<li>Test account users do not have permission to set the publisher account's
+static test response.</li>
+</ul>
+
+<p>The table below summarizes the differences in capabilities, between the
+publisher account, a test account, and any other account.</p>
+
+<p class="table-caption" id="acct-types-table"><strong>Table 1.</strong>
+Differences in account types for testing licensing.</p>
+
+<table>
+<tr>
+<th>Account Type</th>
+<th>Can check license before upload?</th>
+<th>Can receive test response?</th>
+<th>Can set test response?</th>
+</tr>
+
+<tr>
+<td>Publisher account</td>
+<td>Yes</td>
+<td>Yes</td>
+<td>Yes</td>
+</tr>
+
+<tr>
+<td>Test account</td>
+<td>No</td>
+<td>Yes</td>
+<td>No</td>
+</tr>
+
+<tr>
+<td>Other</td>
+<td>No</td>
+<td>No</td>
+<td>No</td>
+</tr>
+</table>
+
+<h4 id="reg-test-acct">Registering test accounts on the publisher account</h4>
+
+<p>To get started, you need to register each test account in your publisher
+account. As shown in Figure 5, you
+register test accounts in the Licensing panel of your publisher account's Edit
+Profile page. Simply enter the accounts as a comma-delimited list and click
+<strong>Save</strong> to save your profile changes.</p>
+
+<p>You can use any Google account as a test account. If you want to own and
+control the test accounts, you can create the accounts yourself and distribute
+the credentials to your developers or testers.</p>
+
+<h4 id="test-app-upload">Handling application upload and distribution for test
+account users</h4>
+
+<p>As mentioned above, users of test accounts can only receive static test
+responses for applications that are uploaded to the publisher account. Since
+those users do not have permission to upload applications, as the publisher you
+will need to work with those users to collect apps for upload and distribute
+uploaded apps for testing. You can handle collection and distribution in any way
+that is convenient. </p>
+
+<p>Once an application is uploaded and becomes known to the licensing server,
+developers and testers can continue modify the application in their local
+development environment, without having to upload new versions. You only need to
+upload a new version if the local application increments the
+<code>versionCode</code> attribute in the manifest file. </p>
+
+<h4 id="test-key">Distributing your public key to test account users</h4>
+
+<p>The licensing server handles static test responses in the normal way,
+including signing the license response data, adding extras parameters, and so
+on. To support developers who are implementing licensing using test accounts,
+rather than the publisher account, you will need to distribute
+your public key to them. Developers without access to the publisher site do not
+have access to your public key, and without the key they won't be able to
+verify license responses. </p>
+
+<p>Note that if you decide to generate a new licensing key pair for your account
+for some reason, you need to notify all users of test accounts. For
+testers, you can embed the new key in the application package and distribute it
+to users. For developers, you will need to distribute the new key to them
+directly. </p>
+
+
+<h3 id="acct-signin">Signing in to an authorized account in the runtime
+environment</h3>
+
+<p>The licensing service is designed to determine whether a given user is
+licensed to use a given application &mdash; during a license check, the Android
+Market application gathers the user ID from the primary account on the system
+and sends it to the server, together with the package name of the application
+and other information. However, if there is no user information available, the
+license check cannot succeed, so the Android Market application terminates the
+request and returns an error to the application. </p>
+
+<p>During testing, to ensure that your application can successfully query the
+licensing server, you must make sure that you sign in to an account <em>on the
+device or emulator</em> using:</p>
+
+<ul>
+<li>The credentials of a publisher account, or</li>
+<li>The credentials of a test account that is registered with a publisher
+account</li>
+</ul>
+
+
+<div class="sidebox-wrapper">
+<div class="sidebox">
+<h2>Signing in to a Google account on an emulator</h2>
+
+<p>If you are testing licensing on an emulator, you need to sign in to a Google
+account on the emulator. If you do not see an option to create a new Google
+account, the problem might be that your AVD is running a standard Android system
+image, rather than the Google APIs Add-On, API 8 (release 2) or higher. </p>
+
+<p style="margin-top:.5em;">For more information, see <a
+href="#runtime-setup">Setting up the runtime environment</a>, above.</p>
+
+</div>
+</div>
+
+<p>Signing in using a publisher account offers the advantage of letting your
+applications receive static test responses even before the applications are
+uploaded to the publisher site.</p>
+
+<p>If you are part of a larger organization or are working with external groups
+on applications that will be published through your site, you will more likely
+want to distribute test accounts instead, then use those to sign in during
+testing. </p>
+
+<p>To sign in on a device or emulator, follow the steps below. The preferred
+approach is to sign in as the primary account &mdash; however, if there are
+other accounts already in use on the device or emulator, you can create an
+additional account and sign in to it using the publisher or test account
+credentials.  </p>
+
+<ol>
+<li>Open Settings &gt; Accounts &amp; sync</li>
+<li>Select <strong>Add Account</strong> and choose to add a "Google" account.
+</li>
+<li>Select <strong>Next</strong> and then <strong>Sign in</strong>.</li>
+<li>Enter the username and password of either the publisher account or a test
+account that is registered in the publisher account.</li>
+<li>Select <strong>Sign in</strong>. The system signs you in to the new
+account.</li>
+</ol>
+
+<p>Once you are signed in, you can begin testing licensing in your application
+(if you have completed the LVL integration steps above). When your application
+initiates a license check, it will receive a response containing the static test
+response configured on the publisher account. </p>
+
+<p>Note that, if you are using an emulator, you will need to sign in to the
+publisher account or test account each time you wipe data when restarting the
+emulator.</p>
+
+<p>Once you've completed the setup procedures, continue to <a
+href="{@docRoot}guide/market/licensing/adding-licensing.html">Adding Licensing to Your App</a>.</p>
+
+
+
diff --git a/docs/html/guide/publishing/licensing.html b/docs/html/guide/publishing/licensing.html
new file mode 100644
index 0000000..8e97f32
--- /dev/null
+++ b/docs/html/guide/publishing/licensing.html
@@ -0,0 +1,11 @@
+<html>
+<head>
+<meta http-equiv="refresh"
+content="0;url=http://developer.android.com/guide/market/licensing/index.html">
+<title>Redirecting...</title>
+</head>
+<body>
+<p>You should have been redirected. Please <a
+href="http://developer.android.com/guide/market/licensing/index.html">click here</a>.</p>
+</body>
+</html>
\ No newline at end of file
diff --git a/docs/html/guide/publishing/licensing.jd b/docs/html/guide/publishing/licensing.jd
deleted file mode 100644
index 609241b..0000000
--- a/docs/html/guide/publishing/licensing.jd
+++ /dev/null
@@ -1,2388 +0,0 @@
-page.title=Application Licensing
-@jd:body
-
-<div id="qv-wrapper">
-<div id="qv">
-
-  <h2>Quickview</h2>
-  <ul>
-    <li>Licensing lets you protect your application on any device that includes Android Market.</li>
-    <li>Your app maintains control of how it enforces its licensing status. </li>
-    <li>Adding licensing to an app is straightforward, using the library available through the SDK.</li>
-    <li>The service is free and is available to all developers who publish on Android Market. </li>
-  </ul>
-
-  <h2>In this document</h2>
-  <ol>
-    <li><a href="#account">Setting Up A Publisher Account</a></li>
-    <li><a href="#dev-setup">Setting Up the Development Environment</a></li>
-    <li><a href="#app-integration">Integrating the LVL with Your Application</a>
-    <ol>
-       <li><a href="#add-library">Including the LVL</a></li>
-       <li><a href="#manifest-permission">Adding the licensing permission</a></li>
-       <li><a href="#impl-Policy">Implementing a Policy</a></li>
-       <li><a href="#impl-Obfuscator">Implementing an Obfuscator</a></li>
-       <li><a href="#impl-lc">Checking the license</a></li>
-       <li><a href="#impl-DeviceLimiter">Implementing a DeviceLimiter</a></li>
-    </ol></li>
-    <li><a href="#test-env">Setting Up the Test Environment</a>
-    <ol>
-       <li><a href="#test-response">Test responses</a></li>
-       <li><a href="#test-acct-setup">Test accounts</a></li>
-       <li><a href="#acct-signin">Signing in on a device or emulator</a></li>
-    </ol></li>
-    <li><a href="#app-obfuscation">Obfuscating Your Application</a></li>
-    <li><a href="#app-publishing">Publishing a Licensed Application</a></li>
-    <li><a href="#support">Where to Get Support</a></li>
-  </ol>
-
-  <h2>Appendix</h2>
-  <ol>
-    <li><a href="#lvl-summary">Summary of LVL Classes and Interfaces</a></li>
-    <li><a href="#server-response-codes">Server Response Codes</a></li>
-    <li><a href="#extras">Server Response Extras</a></li>
-  </ol>
-
-</div>
-</div>
-
-<p>Android Market offers a licensing service that lets you enforce licensing
-policies for paid applications that you publish through Android Market. With
-Android Market Licensing, your applications can query Android Market at run time to
-obtain their licensing status for the current user, then allow or disallow
-further use as appropriate. </p>
-
-<p>Using the service, you can apply a flexible licensing policy on an
-application-by-application basis &mdash; each application can enforce licensing
-in the way most appropriate for it. If necessary, an application can apply custom
-constraints based on the licensing status obtained from Android Market.
-For example, an application can check the licensing status and then apply custom
-constraints that allow the user to run it unlicensed for a specific number
-of times, or for a specific validity period. An application can also restrict use of the
-application to a specific device, in addition to any other constraints. </p>
-
-<p>The licensing service is a secure means of controlling access to your
-applications. When an application checks the licensing status, the Market server
-signs the licensing status response using a key pair that is uniquely associated
-with the publisher account. Your application stores the public key in its
-compiled <code>.apk</code> file and uses it to verify the licensing status
-response.</p>
-
-<p>Any application that you publish through Android Market can use the Android
-Market Licensing service. No special account or registration is needed.
-Additionally, because the service uses no dedicated framework APIs, you can add
-licensing to any legacy application that uses a minimum API level of 3 or
-higher.</p>
-
-<p>To help you add licensing to your application, the Android SDK provides
-library sources that you can include in your application project. The
-License Verification Library (LVL) handles all of
-the licensing-related communication with the Android Market client and the
-licensing service. With the LVL integrated, your application can determine its
-licensing status for the current user by simply calling a library checker method
-and implementing a callback that receives the status.</p>
-
-<p>This document explains how the licensing service works and how to add it to
-your application. </p>
-
-
-<h2 id="overview">Overview</h2>
-
-<p>Android Market Licensing is a network-based service that lets an application
-on an Android-powered device query a trusted licensing server, to determine
-whether the application is licensed to the current device user. After receiving
-the server response, the application can then allow or disallow further use of
-the application as needed. In the service, the role of the licensing server is
-to provide the license status for the current user; the application itself is
-responsible for querying the server and conditionally granting access to the
-application. </p>
-
-<h4>Application, Android Market client, and server</h4>
-
-<p>The licensing service is based on the capability of the Android Market server
-to determine whether a given user is licensed to use a given application. The licensing server
-considers a user to be licensed if the user is a recorded purchaser of an application. If a paid
-application has been uploaded to Android Market but saved only as a draft application (in
-other words, the app is unpublished), the licensing server considers all users to be licensed users
-of the application. Keep in mind, you cannot implement Android Market Licensing in a free
-application.</p>
-
-<p>To properly identify
-the user and determine the license status, the server requires information about
-the application and user &mdash; the application and the Android Market client
-work together to assemble the information and pass it to the server. </p>
-
-<p>In the licensing service, an application does not query the licensing server
-directly, but instead calls the Android Market client over remote IPC to
-initiate a license request. In the license request:</p>
-
-<ul>
-<li>The application provides its package name and a nonce that is later used to
-validate any response from the server, as well as a callback over which the
-response can be returned asynchronously.</li>
-<li>The Android Market client, which has greater permissions than the
-application, collects the necessary information about the user and the device,
-such as the device's primary Google account username, IMSI, and other
-information. It then sends the license check request to the server on behalf of
-the application.</li>
-<li>The server evaluates the request using all available information, attempting
-to establish the user's identity to a sufficient level of confidence. The server
-then checks the user identity against purchase records for the application and
-returns a license response, which the Android Market client returns to the
-application over the IPC callback.</li>
-</ul>
-
-<p>Notice that during a license check, the application does not manage any
-network connections or use any licensing related APIs in the Android platform.
-</p>
-
-<div class="figure" style="width:469px">
-<img src="{@docRoot}images/licensing_arch.png" alt=""/>
-<p class="img-caption"><strong>Figure 1.</strong> Your application initiates a
-license check through the LVL and the Android Market
-client, which handles communication with the Market server.</p>
-</div>
-
-<h4>License responses secured through public key cryptography</h4>
-
-<p>To ensure the integrity of each license query, the server signs the license
-response data using an RSA key pair that is shared exclusively between the
-server and the application publisher.</p>
-
-<p>The licensing service generates a single licensing key pair for each
-publisher account and exposes the public key in the account's profile page. The
-publisher copies the public key and embeds it in the application source code,
-then compiles and publishes the <code>.apk.</code> The server retains the
-private key internally and uses it to sign license responses for applications
-published on that account. </p>
-
-<p>When the application receives a signed response, it uses the embedded public
-key to verify the data. The use of public key cryptography in the licensing
-service makes it possible for the application to detect responses that have been
-tampered with or that are spoofed.</p>
-
-<h4>Use of licensing in your application</h4>
-
-<p>To use licensing in your application, add code to the application to
-initiate a license check request and handle the response when it is received.
-You can choose when, and how often, you want your application to check its
-license and you have full control over how it handles the response, verifies the
-signed response data, and enforces access controls. </p>
-
-<p>To simplify the process of adding support for licensing, download and
-integrate the Licensing Verification Library, described below. Integration is
-straightforward.</p>
-
-<p>When you are finished integrating the LVL, use a test environment
-provided by the publisher site to test your application's handling of server
-responses. </p>
-
-<p>Finally, publish the application <code>.apk</code> on Market using the
-normal process. If you previously used the copy-protection provided by Android
-Market, you can remove it from applications that use licensing. </p>
-
-<h4>Licensing Verification Library simplifies implementation</h4>
-
-<p>The Android SDK includes a License Verification Library (LVL) that you can
-download and use as the basis for your application's licensing implementation.
-The LVL greatly simplifies the process of adding licensing to your application
-and helps ensure a more secure, robust implementation for your application. The
-LVL provides internal classes that handle most of the standard operations of a
-license query, such as contacting Android Market to initiate a license request
-and verifying and validating the responses. It also exposes key interfaces that
-let you easily plug in your custom code for defining licensing policy and
-managing access as needed by your application. The key LVL interfaces are: </p>
-
-<ul>
-<li>Policy &mdash; your implementation determines whether to allow access to the
-application, based on the license response received from the server and any
-other data available (such as from a backend server associated with your
-application). The implementation can evaluate the various fields of the license
-response and apply other constraints, if needed. The implementation also lets
-you manage the handling of license checks that result in errors, such as network
-errors.</li>
-<li>LicenseCheckerCallback &mdash; your implementation manages access to the
-application, based on the result of the Policy's handling of the license
-response. Your implementation can manage access in any way needed, including
-displaying the license result in the UI or directing the user to purchase the
-application (if not currently licensed). </li>
-</ul>
-
-<p>To help you get started with a Policy, the LVL provides two fully complete
-Policy implementations that you can use without modification or adapt to your
-needs:</p>
-
-<ul>
-<li><a href="#ServerManagedPolicy">ServerManagedPolicy</a> is a flexible Policy
-that uses settings provided by the licensing server to manage response caching
-and access to the application while the device is offline (such as when the
-user is on an airplane). For most applications, the use of
-ServerManagedPolicy is highly recommended. </li>
-<li><a href="#StrictPolicy">StrictPolicy</a> is a restrictive Policy that
-does not cache any response data and allows the application access <em>only</em>
-when the server returns a licensed response.</li>
-</ul>
-
-<p>The LVL is available as a downloadable component of the Android SDK. The
-component includes both the LVL itself and an example application that shows how
-the library should be integrated with your application and how your application
-should manage response data, UI interaction, and error conditions. </p>
-
-<p>The LVL sources are provided as an Android <em>library project</em>, which
-means that you can maintain a single set of library sources and share them
-across multiple applications. A full test environment is also available through
-the SDK, so you can develop and test the licensing implementation in your
-applications before publishing them, even if you don't have access to a
-physical device.</p>
-
-<h4>Requirements and limitations</h4>
-
-<p>Android Market Licensing is designed to let you apply license controls to
-applications that you publish through Android Market. The service is not
-designed to let you control access to applications that are not published
-through Android Market or that are run on devices that do not offer the Android
-Market client. </p>
-
-<p>Here are some points to keep in mind as you implement licensing in your
-application: </p>
-
-<ul>
-<li>Only paid applications published through Market can use the
-service.</li>
-<li>An application can use the service only if the Android Market client is
-installed on its host device and the device is running Android 1.5 (API level 3)
-or higher.</li>
-<li>To complete a license check, the licensing server must be accessible over
-the network. You can implement license caching behaviors to manage access when
-there is no network connectivity. </li>
-<li>The security of your application's licensing controls ultimately relies on
-the design of your implementation itself. The service provides the building
-blocks that let you securely check licensing, but the actual enforcement and
-handling of the license are factors in your control. By following the best
-practices in this document, you can help ensure that your implementation will be
-secure.</li>
-<li>Adding licensing to an application does not affect the way the application
-functions when run on a device that does not offer Android Market.</li>
-<li>Licensing is currently for paid apps only, since draft apps are
-licensed for all users. If your application is already published as a free app,
-you won't be able to upload a new version that uses licensing.</li>
-</ul>
-
-<h4>Replacement for Copy Protection</h4>
-
-<p>Android Market Licensing is a flexible, secure mechanism for controlling
-access to your applications. It effectively replaces the Copy Protection
-mechanism offered on Android Market and gives you wider distribution
-potential for your applications. </p>
-
-<ul>
-<li>A limitation of the legacy Copy Protection mechanism on Android Market is
-that applications using it can be installed only on compatible devices that
-provide a secure internal storage environment. For example, a copy-protected
-application cannot be downloaded from Market to a device that provides root
-access, and the application cannot be installed to a device's SD card. </li>
-<li>With Android Market licensing, you can move to a license-based model in
-which access is not bound to the characteristics of the host device, but to your
-publisher account on Android Market and the licensing policy that you define.
-Your application can be installed and controlled on any compatible device on
-any storage, including SD card.</li>
-</ul>
-
-<p>Although no license mechanism can completely prevent all unauthorized use,
-the licensing service lets you control access for most types of normal usage,
-across all compatible devices, locked or unlocked, that run Android 1.5 or
-higher version of the platform.</p>
-
-<p>The sections below describe how to add Android Market licensing to your
-applications. </p>
-
-<h2 id="account">Setting Up a Publisher Account</h2>
-
-<p>Android Market licensing lets you manage access to applications that
-users have downloaded from Android Market. To use licensing in an application,
-you need to have a publisher account on Android Market so that you can
-publish the application to users. </p>
-
-<p>If you don't already have a publisher account, you need to register for one
-using your Google account and agree to the terms of service. Once you are
-registered, you can upload applications at your convenience and begin debugging
-and testing your licensing implementation. For more information about publishing
-on Android Market, see <a
-href="{@docRoot}guide/publishing/publishing.html">Publishing Your
-Applications</a></p>
-
-<p>To register as an Android Market developer and set up your publisher account,
-visit the Android Market publisher site:</p>
-
-<p style="margin-left:2em;"><a
-href="http://market.android.com/publish">http://market.android.com/publish</a>
-</p>
-
-<p>If you already have a publisher account on Android Market, use your existing
-account to set up licensing. You <em>do not</em> need to register for a new
-account to support licensing (and doing so is not recommended, especially if you
-are adding licensing support to applications that you have already published).
-In all cases, if you have published applications, you manage licensing for those
-applications through the account on which the applications are published. </p>
-
-<p>Once your publisher account is set up, use the account to:</p>
-
-<ul>
-<li>Obtain a public key for licensing</li>
-<li>Debug and test an application's licensing implementation, prior to
-publishing the application</li>
-<li>Publish the applications to which you have added licensing support</li>
-</ul>
-
-<h4>Administrative settings for licensing</h4>
-
-<p>Once you are signed into your publisher account, you can manage several
-administrative controls for Android Market licensing. The controls are available
-in the Edit Profile page, in the "Licensing" panel, shown below. The controls
-let you: </p>
-
-<ul>
-<li>Set up multiple "test accounts", identified by email address. The licensing
-server allows users signed into test accounts on a device or emulator to send
-license checks and receive static test responses.</li>
-<li>Obtain the account's public key for licensing. When you are implementing
-licensing in an application, you must copy the public key string into the
-application.</li>
-<li>Configure static test responses that the server sends, when it receives a
-license check for an application uploaded to the publisher account, from a user
-signed in to the publisher account or a test account.</li>
-</ul>
-
-<div style="margin-bottom:2em;">
-
-<img src="{@docRoot}images/licensing_public_key.png" style="text-align:left;margin-bottom:0;" />
-<div style="margin:0 2em;padding:0"><strong>Figure 2.</strong> The Licensing
-panel of your account's Edit Profile page lets you manage administrative
-settings for licensing.</div>
-</div>
-
-<p>For more information about how to work with test accounts and static test
-responses, see <a href="#test-env">Setting Up a Testing Environment</a>, below.
-
-<h2 id="dev-setup">Setting Up the Development Environment</h2>
-
-<p>Once you've set up your publisher account on Android Market, the next step is
-to set up your development environment for licensing. </p>
-
-<p>Setting up your environment for licensing involves these tasks:</p>
-
-<ol>
-<li><a href="#download-sdk">Downloading the latest SDK</a>, if you haven't already done so </li>
-<li><a href="#runtime-setup">Setting up the runtime environment</a> for development</li>
-<li><a href="#download-lvl">Downloading the Market Licensing component</a> into your SDK </li>
-<li><a href="#lvl-setup">Setting up the Licensing Verification Library</a></li>
-<li><a href="#add-library">Including the LVL library project in your application</a></li>
-</ol>
-
-<p>The sections below describe these tasks. When you are done with setup,
-you can begin <a href="#app-integration">integrating the LVL into your applications</a>.</p>
-
-<p>To get started, you need to set up a proper runtime environment on which
-you can run, debug and test your application's implementation of license
-checking and enforcement. </p>
-
-
-<h3 id="download-sdk">Downloading the latest SDK</h3>
-
-<div class="sidebox-wrapper">
-<div class="sidebox">
-<h2>Licensing sample application</h2>
-
-<p>To work with Android Market licensing, you need a functioning Android
-application to which you can add licensing support. </p>
-
-<p style="margin-top:.5em;">If you are new to Android
-and don't yet have a functioning application, the LVL component includes a sample
-application that you can set up as a new application project. The sample provides
-a complete, working example of how licensing works. For more information, see <a
-href="#download-lvl">Downloading the LVL</a>.</p>
-
-</div>
-</div>
-
-<p>If you haven't done so, you need to download the Android SDK before you can
-develop Android applications. The SDK provides the tools that you need to build
-and debug Android applications, including applications that use Android Market
-licensing. For complete information, including installation instructions, see
-the <a href="{@docRoot}sdk/index.html">Android SDK</a>. </p>
-
-<p>If you have already installed the SDK, make sure to update the
-SDK tools and ADT Plugin to the latest versions. You can update the SDK tools
-using the Android SDK and AVD Manager and ADT through <strong>Help</strong> &gt;
-<strong>Software Updates...</strong> in Eclipse. </p>
-
-<p>After you've installed the latest SDK and tools, set up your development
-environment as described below. </p>
-
-
-<h3 id="runtime-setup">Setting up the runtime environment</h3>
-
-<p>As described earlier, applications check licensing status not by contacting
-the licensing server directly, but by binding to a service provided by the
-Android Market application and initiating a license check request. The Android
-Market service then handles the direct communication with the licensing server
-and finally routes the response back to your application. To debug and test
-licensing in your application, you need to set up a runtime environment that
-includes the necessary Android Market service, so that your application is able
-to send license check requests to the licensing server. </p>
-
-<p>There are two types of runtime environment that you can use: </p>
-
-<ul>
-<li>An Android-powered device that includes the Android Market application, or</li>
-<li>An Android emulator running the Google APIs Add-on, API level 8 (release 2)
-or higher</li>
-</ul>
-
-<p>The sections below provide more information. </p>
-
-<h4 id="runtime-device">Running on a device</h4>
-
-<p>You can use an Android-powered device as the runtime environment for
-debugging and testing licensing on your application.</p>
-
-<p>The device you use must:</p>
-
-<ul>
-<li>Run a standard version of the Android 1.5 or later (API level
-3 or higher) platform, <em>and</em> </li>
-<li>Run a system image on which the Android Market client application
-is preinstalled. </li>
-</ul>
-
-<p>If Android Market is not preinstalled in the system image, your application won't
-be able to communicate with the Android Market licensing server. </p>
-
-<p>For general information about how to set up a device for use in developing
-Android applications, see <a
-href="{@docRoot}guide/developing/device.html">Developing on a Device</a>.</p>
-
-<h4 id="runtime-emulator">Running on an Android emulator</h4>
-
-<p>You can also use an Android emulator as your runtime
-environment for debugging and testing licensing.</p>
-
-<p>Because the standard Android platforms provided in the Android SDK <em>do
-not</em> include Android Market, you need to download the Google APIs Add-On
-platform, API Level 8 (or higher), from the SDK repository. After downloading
-the add-on, you need to create an AVD configuration that uses that system image.
-</p>
-
-<p>The Google APIs Add-On does not include the full Android Market client.
-However, it does provide: </p>
-
-<ul>
-<li>An Android Market background service that implements the
-ILicensingService remote interface, so that your application can
-send license checks over the network to the licensing server. </li>
-<li>A set of underlying account services that let you add an a Google account on
-the AVD and sign in using your publisher account or test account credentials.
-Signing in using your publisher or test account enables you to debug and test
-your application without having publish it. For more information see <a
-href="#acct-signin">Signing in to an authorized account</a>, below.</li>
-</ul>
-
-<p>Several versions of the add-on are available in the SDK repository, but only
-<strong>Google APIs Add-On, API 8 (release 2) or higher</strong> version of the
-add-on includes the necessary Android Market services. This means that you
-cannot use Google APIs Add-On API 7 or lower as a runtime environment for
-developing licensing on an emulator.</p>
-
-<div style="margin-bottom:2em;">
-
-<img src="{@docRoot}images/licensing_gapis_8.png" style="text-align:left;margin-bottom:0;" />
-<div style="margin:0 2em;padding:0"><strong>Figure 3.</strong> Google APIs
-Add-On, API 8 (release 2) or higher lets you debug and test your licensing
-implementation in an emulator.</div>
-</div>
-
-<p>To set up an emulator for adding licensing to an application, follow
-these steps: </p>
-
-<ol>
-  <li>Launch the Android SDK and AVD Manager. </li>
-  <li>In the <strong>Available Packages</strong> panel, select and download the
-SDK component "Google APIs (Google Inc.) - API Level 8" (or higher) from the SDK
-repository, as shown in the figure above.
-  <p>When the download is complete, use the Android SDK and AVD Manager to
-create a new AVD based on that component, described next.</p></li>
-  <li>In the <strong>Virtual
-Devices</strong> panel of the Android SDK and AVD Manager, click
-<strong>New</strong> and set the configuration details for the new AVD. </li>
-  <li>In the dialog that appears, assign a descriptive name to the AVD and then
-use the "Target" menu to choose the "Google APIs (Google Inc.) - API Level 8" as
-the system image to run on the new AVD. Set the other configuration details as
-needed and then click <strong>Create AVD</strong> to finish. The SDK tools
-create the new AVD configuration, which then appears in the list of available
-Android Virtual Devices.</li>
-</ol>
-
-<p>If you are not familiar with AVDs or how to use them, see <a
-href="{@docRoot}guide/developing/devices/index.html">Managing Virtual Devices</a>.</p>
-
-<h4 id="project-update">Updating your project configuration</h4>
-
-<p>After you set up a runtime environment that meets the requirements described
-above &mdash; either on an actual device or on an emulator &mdash; make sure to
-update your application project or build scripts as needed, so that your compiled
-<code>.apk</code> files that use licensing are deployed into that environment.
-In particular, if you are developing in Eclipse, make sure that you set up a
-Run/Debug Configuration that targets the appropriate device or AVD. </p>
-
-<p>You do not need to make any changes to your application's
-build configuration, provided that the project is already configured to compile
-against a standard Android 1.5 (API level 3) or higher library. For example:
-
-<ul>
-<li>If you have an existing application that is compiled against
-the Android 1.5 library, you do not need to make any changes to your
-build configuration to support licensing. The build target meets the minimum
-requirements for licensing, so you would continue building
-against the same version of the Android platform.</li>
-
-<li>Similarly, if you are building against Android 1.5 (API level 3) but
-are using an emulator running the Google APIs Add-On API 8 as the application's
-runtime environment, there is no need to change your application's build
-configuration. </li>
-</ul>
-
-<p>In general, adding licensing to an application should have no impact
-whatsoever on the application's build configuration.</p>
-
-
-<h3 id="download-lvl">Downloading the LVL</h3>
-
-<p>The License Verification Library (LVL) is a collection of helper classes that
-greatly simplify the work that you need to do to add licensing to your
-application. In all cases, we recommend that you download the LVL and use it as
-the basis for the licensing implementation in your application.</p>
-
-<p>The LVL is available as a downloadable component of the Android SDK. The
-component includes: </p>
-
-<ul>
-<li>The LVL sources, stored inside an Android library project. </li>
-<li>An example application called "sample" that depends on the LVL library
-project. The example illustrates how an application uses the library helper
-classes to check and enforce licensing.</li>
-</ul>
-
-<p>To download the LVL component into your development environment, use the
-Android SDK and AVD Manager. Launch the Android SDK and AVD Manager and then
-select the "Market Licensing" component, as shown in the figure below.
-Accept the terms and click <strong>Install Selected</strong> to begin the download. </p>
-
-<div style="margin-bottom:2em;">
-
-<img src="{@docRoot}images/licensing_package.png" style="text-align:left;margin-bottom:0;" />
-<div style="margin:0 2em;padding:0"><strong>Figure 4.</strong> The Market
-Licensing package contains the LVL and the LVL sample application. </div>
-</div>
-
-<p>When the download is complete, the Android SDK and AVD Manager installs both
-the LVL library project and the example application into these directories: </p>
-
-<p style="margin-left:2em"><code>&lt;<em>sdk</em>&gt;/extras/google/market_licensing/library/</code>
-&nbsp;&nbsp;(the LVL library project)<br />
-<code>&lt;<em>sdk</em>&gt;/extras/google/market_licensing/sample/</code>&nbsp;&nbsp;(the example
-application)</p>
-
-<p>If you aren't familiar with how to download components into your SDK, see the
-<a href="{@docRoot}sdk/adding-components.html">Adding SDK Components</a>
-document. </p>
-
-
-<h3 id="lvl-setup">Setting Up the Licensing Verification Library</h3>
-
-<p>After downloading the LVL to your computer, you need to set it up in your
-development environment, either as an Android library project or by
-copying (or importing) the library sources directly into your existing
-application package. In general, using the LVL as a library project is recommended,
-since it lets you reuse your licensing code across multiple applications and
-maintain it more easily over time. Note that the LVL is not designed to be
-compiled separately and added to an application as a static .jar file. </p>
-
-<h4>Moving the library sources to a new location</h4>
-
-<p>Because you will be customizing the LVL sources to some extent, you should
-make sure to <em>move or copy</em> the library sources (the entire
-directory at <code>&lt;<em>sdk</em>&gt;/market_licensing/library/</code>)
-to a working directory outside of the SDK. You should then use the relocated
-sources as your working set. If you are using a source-code management
-system, add and track the sources that are in the working location rather
-than those in default location in the SDK. </p>
-
-<p>Moving the library sources is important is because, when you later update the
-Market licensing package, the SDK installs the new files to the same location as
-the older files. Moving your working library files to a safe location ensures
-that your work won't be inadvertently overwritten should you download a new
-version of the LVL.</p>
-
-<h4>Creating the LVL as a library project</h4>
-
-<div class="sidebox-wrapper">
-<div class="sidebox">
-<h2>Working with library projects</h2>
-
-<p>The LVL is provided as an Android library project, which means that you can
-share its code and resources across multiple applications. </p>
-
-<p style="margin-top:.5em;">If you aren't familiar with library projects or how
-to use them, see <a href="{@docRoot}guide/developing/projects/index.html#LibraryProjects">
-Managing Projects</a>.
-</p>
-</div>
-</div>
-
-<p>The recommended way of using the LVL is setting it up as a new Android
-<em>library project</em>. A library project is a type of development project
-that holds shared Android source code and resources. Other Android application
-projects can reference the library project and, at build time, include its
-compiled sources in their <code>.apk</code> files. In the context of licensing,
-this means that you can do most of your licensing development once, in a library
-project, then include the library sources in your various application projects.
-In this way, you can easily maintain a uniform implementation of licensing
-across all of your projects and maintain it centrally. </p>
-
-<p>The LVL is provided as a configured library project &mdash; once you have
-downloaded it, you can start using it right away. </p>
-
-<p>If you are working in Eclipse with ADT, you need to add the LVL to your
-workspace as a new development project, in the same way as you would a new
-application project. </p>
-
-<ol>
-<li>Use the New Project Wizard to create a new
-project from existing sources. Select the LVL's <code>library</code> directory
-(the directory containing the library's AndroidManifest.xml file) as the project
-root.</li>
-<li>When you are creating the library project, you can select any application
-name, package, and set other fields as needed. </li>
-<li>For the library's build target, select Android 1.5 (API level 3) or higher.</li>
-</ol>
-
-<p> When created, the project is
-predefined as a library project in its <code>project.properties</code> file, so
-no further configuration is needed. </p>
-
-<p>For more information about how to create an application project or work with
-library projects in Eclipse, see <a
-href="{@docRoot}guide/developing/projects/projects-eclipse.html">Managing Projects from
-Eclipse with ADT</a></p>.
-
-<h4>Copying the LVL sources to your application</h4>
-
-<p>As an alternative to adding the LVL as a library project, you can copy the
-library sources directly into your application. To do so, copy (or import) the
-LVL's <code>library/src/com</code> directory into your application's
-<code>src/</code> directory.</p>
-
-<p>If you add the LVL sources directly to your application, you can skip the
-next section and start working with the library, as described in <a
-href="#app-integration"></a>.</p>
-
-
-<h3 id="add-library">Including the LVL library project sources in your
-application</h3>
-
-<p>If you want to use the LVL sources as a library project, you need to add a
-reference to the LVL library project in your application project properties. This tells
-build tools to include the LVL library project sources in your application at
-compile time. The process for adding a reference to a library project depends
-on your development environment, as described below.</p>
-
-<p> If you are developing in Eclipse with ADT, you should already have added the
-library project to your workspace, as described in the previous section. If you
-haven't done that already, do it now before continuing. </p>
-
-<p>Next, open the application's project properties window, as shown below.
-Select the "Android" properties group and click <strong>Add</strong>, then
-choose the LVL library project (com_android_vending_licensing) and click
-<strong>OK</strong>. For more information, see
-<a href="{@docRoot}guide/developing/projects/projects-eclipse.html#SettingUpLibraryProject">
-Managing Projects from Eclipse with ADT</a></p>.
-
-<div style="margin-bottom:2em;">
-
-<img src="{@docRoot}images/licensing_add_library.png" style="text-align:left;margin-bottom:0;" />
-<div style="margin:0 2em;padding:0"><strong>Figure 5.</strong> If you are
-working in Eclipse with ADT, you can add the LVL library project to your
-application from the application's project properties.</div>
-</div>
-
-<p>If you are developing using the SDK command-line tools, navigate to the
-directory containing your application project and open the
-<code>project.properties</code> file. Add a line to the file that specifies the
-<code>android.library.reference.&lt;n&gt;</code> key and the path to the
-library. For example: </p>
-
-<pre>android.library.reference.1=path/to/library_project</pre>
-
-<p>Alternatively, you can use this command to update the project
-properties, including the reference to the library project:</p>
-
-<pre class="no-pretty-print" style="color:black">android update lib-project
---target <em>&lt;target_ID&gt;</em> \
---path <em>path/to/my/app_project</em> \
---library <em>path/to/my/library_project</em>
-</pre>
-
-<p>For more information about working with library projects,
-see <a href="{@docRoot}guide/developing/projects/projects-cmdline.html#SettingUpLibraryProject">
-Managing Projects from the Command Line</a></p>.
-
-
-<h2 id="app-integration">Integrating the LVL with Your Application</h2>
-
-<p>Once you've followed the steps above to set up a publisher account and
-development environment, you are ready to begin integrating the LVL with your
-application. </p>
-
-<p>Integrating the LVL with your application code involves these tasks:</p>
-
-<ol>
-<li><a href="#manifest-permission">Adding the licensing permission</a> your application's manifest.</li>
-<li><a href="#impl-Policy">Implementing a Policy</a> &mdash; you can choose one of the full implementations provided in the LVL or create your own.</li>
-<li><a href="#impl-Obfuscator">Implementing an Obfuscator</a>, if your Policy will cache any license response data. </li>
-<li><a href="#impl-lc">Adding code to check the license</a> in your application's main Activity</li>
-<li><a href="#impl-DeviceLimiter">Implementing a DeviceLimiter</a> (optional and not recommended for most applications)</li>
-</ol>
-
-<p>The sections below describe these tasks. When you are done with the
-integration, you should be able to compile your application successfully and you
-can begin testing, as described in <a href="#test-env">Setting Up the Test
-Environment</a>.</p>
-
-<p>For an overview of the full set of source files included in the LVL, see <a
-href="#lvl-summary">Summary of LVL Classes and Interfaces</a>.</p>
-
-
-<h3 id="manifest-permission">Adding the licensing permission to your
-AndroidManifest.xml</h3>
-
-<p>To use the Android Market application for sending a license check to the
-server, your application must request the proper permission,
-<code>com.android.vending.CHECK_LICENSE</code>. If your application does
-not declare the licensing permission but attempts to initiate a license check,
-the LVL throws a security exception.</p>
-
-<p>To request the licensing permission in your application, declare a <a
-href="{@docRoot}guide/topics/manifest/uses-permission-element.html"><code>&lt;uses-permission&gt;</code></a>
-element as a child of <code>&lt;manifest&gt;</code>, as follows: </p>
-
-<p style="margin-left:2em;"><code>&lt;uses-permission
-android:name="com.android.vending.CHECK_LICENSE"&gt;</code></p>
-
-<p>For example, here's how the LVL sample application declares the permission:
-</p>
-
-<pre>&lt;?xml version="1.0" encoding="utf-8"?&gt;
-
-&lt;manifest xmlns:android="http://schemas.android.com/apk/res/android" ..."&gt;
-    &lt;!-- Devices &gt;= 3 have version of Android Market that supports licensing. --&gt;
-    &lt;uses-sdk android:minSdkVersion="3" /&gt;
-    &lt;!-- Required permission to check licensing. --&gt;
-    &lt;uses-permission android:name="com.android.vending.CHECK_LICENSE" /&gt;
-    ...
-&lt;/manifest&gt;
-</pre>
-
-<p class="note"><strong>Note:</strong> Currently, you cannot declare the
-<code>CHECK_LICENSE</code> permission in the LVL library project's manifest,
-because the SDK Tools will not merge it into the manifests of dependent
-applications. Instead, you must declare the permission in each dependent
-application's manifest. </p>
-
-
-<h3 id="impl-Policy">Implementing a Policy</h3>
-
-<div class="sidebox-wrapper">
-<div class="sidebox">
-<h2>ServerManagedPolicy</h2>
-
-<p>The LVL includes a complete Policy implementation called ServerManagedPolicy
-that makes use of license-management settings provided by the Android Market
-server. </p>
-
-<p style="margin-top:.5em;">Use of ServerManagedPolicy as the basis for your
-Policy is strongly recommended. For more information, see <a
-href="#ServerManagedPolicy">ServerManagedPolicy</a> section, below.</p>
-
-</div>
-</div>
-
-<p>Android Market licensing service does not itself determine whether a
-given user with a given license should be granted access to your application.
-Rather, that responsibility is left to a Policy implementation that you provide
-in your application.</p>
-
-<p>Policy is an interface declared by the LVL that is designed to hold your
-application's logic for allowing or disallowing user access, based on the result
-of a license check. To use the LVL, your application <em>must</em> provide an
-implementation of Policy. </p>
-
-<p>The Policy interface declares two methods, <code>allowAccess()</code> and
-<code>processServerResponse()</code>, which are called by a LicenseChecker
-instance when processing a response from the license server. It also declares an
-enum called <code>LicenseResponse</code>, which specifies the license response
-value passed in calls to <code>processServerResponse()</code>. </p>
-
-<ul>
-<li><code>processServerResponse()</code> lets you preprocess the raw response
-data received from the licensing server, prior to determining whether to grant
-access.
-
-<p>A typical implementation would extract some or all fields from the license
-response and store the data locally to a persistent store, such as through
-{@link android.content.SharedPreferences} storage, to ensure that the data is
-accessible across application invocations and device power cycles. For example,
-a Policy would maintain the timestamp of last successful license check, the
-retry count, the license validity period, and similar information in a
-persistent store, rather than resetting the values each time the application is
-launched.</p>
-
-<p>When storing response data locally, the Policy must ensure that the data is
-obfuscated (see <a href="#impl-Obfuscator">Implementing an Obfuscator</a>,
-below).</p></li>
-
-<li><code>allowAccess()</code> determines whether to grant the user access to
-your application, based on any available license response data (from the
-licensing server or from cache) or other application-specific information.  For
-example, your implementation of <code>allowAccess()</code> could take into
-account additional criteria, such as usage or other data retrieved from a
-backend server. In all cases, an implementation of <code>allowAccess()</code>
-should only return <code>true</code> if the user is licensed to use the
-application, as determined by the licensing server, or if there is a transient
-network or system problem that prevents the license check from completing. In
-such cases, your implementation can maintain a count of retry responses and
-provisionally allow access until the next license check is complete.</li>
-
-</ul>
-
-<p>To simplify the process of adding licensing to your application and to
-provide an illustration of how a Policy should be designed, the LVL includes
-two full Policy implementations that you can use without modification or
-adapt to your needs:</p>
-
-<ul>
-<li><a href="#ServerManagedPolicy">ServerManagedPolicy</a>, a flexible Policy
-that uses server-provided settings and cached responses to manage access across
-varied network conditions, and</li>
-<li><a href="#StrictPolicy">StrictPolicy</a>, which does not cache any response
-data and allows access <em>only</em> if the server returns a licensed
-response.</li>
-</ul>
-
-<p>For most applications, the use of ServerManagedPolicy is highly
-recommended. ServerManagedPolicy is the LVL default and is integrated with
-the LVL sample application.</p>
-
-
-<h4 id="custom-policies">Guidelines for custom policies</h4>
-
-<p>In your licensing implementation, you can use one of the complete policies
-provided in the LVL (ServerManagedPolicy or StrictPolicy) or you can create a
-custom policy. For any type of custom policy, there are several important design
-points to understand and account for in your implementation.</p>
-
-<p>The licensing server applies general request limits to guard against overuse
-of resources that could result in denial of service. When an application exceeds
-the request limit, the licensing server returns a 503 response, which gets
-passed through to your application as a general server error. This means that no
-license response will be available to the user until the limit is reset, which
-can affect the user for an indefinite period.</p>
-
-<p>If you are designing a custom policy, we recommend that the Policy:
-<ol>
-<!-- <li>Limits the number of points at which your app calls for a license check
-to the minimum. </li> -->
-<li>Caches (and properly obfuscates) the most recent successful license response
-in local persistent storage.</li>
-<li>Returns the cached response for all license checks, for as long as the
-cached response is valid, rather than making a request to the licensing server.
-Setting the response validity according to the server-provided <code>VT</code>
-extra is highly recommended. See <a href="#extras">Server Response Extras</a>
-for more information.</li>
-<li>Uses an exponential backoff period, if retrying any requests the result in
-errors. Note that the Android Market client automatically retries failed
-requests, so in most cases there is no need for your Policy to retry them.</li>
-<li>Provides for a "grace period" that allows the user to access your
-application for a limited time or number of uses, while a license check is being
-retried. The grace period benefits the user by allowing access until the next
-license check can be completed successfully and it benefits you by placing a
-hard limit on access to your application when there is no valid license response
-available.</li>
-</ol>
-
-<p>Designing your Policy according to the guidelines listed above is critical,
-because it ensures the best possible experience for users while giving you
-effective control over your application even in error conditions. </p>
-
-<p>Note that any Policy can use settings provided by the licensing server to
-help manage validity and caching, retry grace period, and more. Extracting the
-server-provided settings is straightforward and making use of them is highly
-recommended. See the ServerManagedPolicy implementation for an example of how to
-extract and use the extras. For a list of server settings and information about
-how to use them, see  <a href="#extras">Server Response Extras</a> in the
-Appendix of this document.</p>
-
-<h4 id="ServerManagedPolicy">ServerManagedPolicy</h4>
-
-<div class="sidebox-wrapper">
-<div class="sidebox">
-<h2>Server Response Extras</h2>
-
-<p>For certain types of licensing responses, the licensing server appends extra
-settings to the responses, to help the application manage licensing effectively.
-</p>
-
-<p style="margin-top:.5em;">See <a href="#extras">Server Response Extras</a> for
-a list of settings and <code>ServerManagedPolicy.java</code> for information
-about how a Policy can use the extras.</p>
-
-</div>
-</div>
-
-<p>The LVL includes a full and recommended implementation of the Policy
-interface called ServerManagedPolicy. The implementation is integrated with the
-LVL classes and serves as the default Policy in the library. </p>
-
-<p>ServerManagedPolicy provides all of the handling for license and retry
-responses. It caches all of the response data locally in a
-{@link android.content.SharedPreferences} file, obfuscating it with the
-application's Obfuscator implementation. This ensures that the license response
-data is secure and persists across device power cycles. ServerManagedPolicy
-provides concrete implementations of the interface methods
-<code>processServerResponse()</code> and <code>allowAccess()</code> and also
-includes a set of supporting methods and types for managing license
-responses.</p>
-
-<p>Importantly, a key feature of ServerMangedPolicy is its use of
-server-provided settings as the basis for managing licensing across an
-application's refund period and through varying network and error conditions.
-When an application contacts the Android Market server for a license check, the
-server appends several settings as key-value pairs in the extras field of certain
-license response types. For example, the server provides recommended values for the
-application's license validity period, retry grace period, and maximum allowable
-retry count, among others. ServerManagedPolicy extracts the values from the
-license response in its <code>processServerResponse()</code> method and checks
-them in its <code>allowAccess()</code> method. For a list of the server-provided
-settings used by ServerManagedPolicy, see <a href="#extras">Server Response
-Extras</a> in the Appendix of this document.</p>
-
-<p>For convenience, best performance, and the benefit of using license settings
-from the Android Market server, <strong>using ServerManagedPolicy as your
-licensing Policy is strongly recommended</strong>. </p>
-
-<p>If you are concerned about the security of license response data that is
-stored locally in SharedPreferences, you can use a stronger obfuscation
-algorithm or design a stricter Policy that does not store license data. The LVL
-includes an example of such a Policy &mdash; see <a
-href="#StrictPolicy">StrictPolicy</a> for more information.</p>
-
-<p>To use ServerManagedPolicy, simply import it to your Activity, create an
-instance, and pass a reference to the instance when constructing your
-LicenseChecker. See <a href="#lc-lcc">Instantiate LicenseChecker and
-LicenseCheckerCallback</a> for more information. </p>
-
-<h4 id="StrictPolicy">StrictPolicy</h4>
-
-<p>The LVL includes an alternative full implementation of the Policy interface
-called StrictPolicy. The StrictPolicy implementation provides a more restrictive
-Policy than ServerManagedPolicy, in that it does not allow the user to access
-the application unless a license response is received from the server at the
-time of access that indicates that the user is licensed.</p>
-
-<p>The principal feature of StrictPolicy is that it does not store <em>any</em>
-license response data locally, in a persistent store. Because no data is stored,
-retry requests are not tracked and cached responses can not be used to fulfill
-license checks. The Policy allows access only if:</p>
-
-<ul>
-<li>The license response is received from the licensing server, and </li>
-<li>The license response indicates that the user is licensed to access the
-application. </li>
-</ul>
-
-<p>Using StrictPolicy is appropriate if your primary concern is to ensure that,
-in all possible cases, no user will be allowed to access the application unless
-the user is confirmed to be licensed at the time of use. Additionally, the
-Policy offers slightly more security than ServerManagedPolicy &mdash; since
-there is no data cached locally, there is no way a malicious user could tamper
-with the cached data and obtain access to the application.</p>
-
-<p>At the same time, this Policy presents a challenge for normal users, since it
-means that they won't be able to access the application when there is no network
-(cell or wi-fi) connection available. Another side-effect is that your
-application will send more license check requests to the server, since using a
-cached response is not possible.</p>
-
-<p>Overall, this policy represents a tradeoff of some degree of user convenience
-for absolute security and control over access. Consider the tradeoff carefully
-before using this Policy.</p>
-
-<p>To use StrictPolicy, simply import it to your Activity, create an instance,
-and pass a reference to it when constructing your LicenseChecker. See
-<a href="#lc-lcc">Instantiate LicenseChecker and LicenseCheckerCallback</a>
-for more information. </p>
-
-<h3 id="impl-Obfuscator">Implementing an Obfuscator</h3>
-
-<div class="sidebox-wrapper">
-<div class="sidebox">
-<h2>AESObfuscator</h2>
-
-<p>The LVL includes a full Obfuscator implementation in the
-<code>AESObfuscator.java</code> file. The Obfuscator uses AES encryption to
-obfuscate/unobfuscate data. If you are using a Policy (such as
-ServerManagedPolicy) that caches license response data, using AESObfuscator as
-basis for your Obfuscator implementation is highly recommended. </p>
-
-</div>
-</div>
-
-<p>A typical Policy implementation needs to save the license response data for
-an application to a persistent store, so that it is accessible across
-application invocations and device power cycles.  For example, a Policy would
-maintain the timestamp of the last successful license check, the retry count,
-the license validity period, and similar information in a persistent store,
-rather than resetting the values each time the application is launched. The
-default Policy included in the LVL, ServerManagedPolicy, stores license response
-data in a {@link android.content.SharedPreferences} instance, to ensure that the
-data is persistent. </p>
-
-<p>Because the Policy will use stored license response data to determine whether
-to allow or disallow access to the application, it <em>must</em> ensure that any
-stored data is secure and cannot be reused or manipulated by a root user on a
-device. Specifically, the Policy must always obfuscate the data before storing
-it, using a key that is unique for the application and device. Obfuscating using
-a key that is both application-specific and device-specific is critical, because
-it prevents the obfuscated data from being shared among applications and
-devices.</p>
-
-<p>The LVL assists the application with storing its license response data in a
-secure, persistent manner. First, it provides an Obfuscator
-interface that lets your application supply the obfuscation algorithm of its
-choice for stored data. Building on that, the LVL provides the helper class
-PreferenceObfuscator, which handles most of the work of calling the
-application's Obfuscator class and reading and writing the obfuscated data in a
-SharedPreferences instance. </p>
-
-<p>The LVL provides a full Obfuscator implementation called
-AESObfuscator that uses AES encryption to obfuscate data. You can
-use AESObfuscator in your application without modification or you
-can adapt it to your needs. For more information, see the next section.</p>
-
-
-<h4 id="AESObfuscator">AESObfuscator</h4>
-
-<p>The LVL includes a full and recommended implementation of the Obfuscator
-interface called AESObfuscator. The implementation is integrated with the
-LVL sample application and serves as the default Obfuscator in the library. </p>
-
-<p>AESObfuscator provides secure obfuscation of data by using AES to
-encrypt and decrypt the data as it is written to or read from storage.
-The Obfuscator seeds the encryption using three data fields provided
-by the application: </p>
-
-<ol>
-<li>A salt &mdash; an array of random bytes to use for each (un)obfuscation. </li>
-<li>An application identifier string, typically the package name of the application.</li>
-<li>A device identifier string, derived from as many device-specific sources
-as possible, so as to make it as unique.</li>
-</ol>
-
-<p>To use AESObfuscator, first import it to your Activity. Declare a private
-static final array to hold the salt bytes and initialize it to 20 randomly
-generated bytes.</p>
-
-<pre>    ...
-    // Generate 20 random bytes, and put them here.
-    private static final byte[] SALT = new byte[] {
-     -46, 65, 30, -128, -103, -57, 74, -64, 51, 88, -95,
-     -45, 77, -117, -36, -113, -11, 32, -64, 89
-     };
-    ...
-</pre>
-
-<p>Next, declare a variable to hold a device identifier and generate a value for
-it in any way needed. For example, the sample application included in the LVL
-queries the system settings for the
-<code>android.Settings.Secure.ANDROID_ID</code>, which is unique to each device.
-</p>
-
-<p>Note that, depending on the APIs you use, your application might need to
-request additional permissions in order to acquire device-specific information.
-For example, to query the {@link android.telephony.TelephonyManager} to obtain
-the device IMEI or related data, the application will also need to request the
-<code>android.permission.READ_PHONE_STATE</code> permission in its manifest.</p>
-
-<p>Before requesting new permissions for the <em>sole purpose</em> of acquiring
-device-specific information for use in your Obfuscator, consider
-how doing so might affect your application or its filtering on Android Market
-(since some permissions can cause the SDK build tools to add
-the associated <code>&lt;uses-feature&gt;</code>).</p>
-
-<p>Finally, construct an instance of AESObfuscator, passing the salt,
-application identifier, and device identifier. You can construct the instance
-directly, while constructing your Policy and LicenseChecker. For example:</p>
-
-<pre>    ...
-    // Construct the LicenseChecker with a Policy.
-    mChecker = new LicenseChecker(
-        this, new ServerManagedPolicy(this,
-            new AESObfuscator(SALT, getPackageName(), deviceId)),
-        BASE64_PUBLIC_KEY  // Your public licensing key.
-        );
-    ...
-</pre>
-
-<p>For a complete example, see MainActivity in the LVL sample application.</p>
-
-
-<h3 id="impl-lc">Checking the license from your application's main Activity</h3>
-
-<p>Once you've implemented a Policy for managing access to your application, the
-next step is to add a license check to your application, which initiates a query
-to the licensing server if needed and manages access to the application based on
-the license response. All of the work of adding the license check and handling
-the response takes place in your main {@link android.app.Activity} source file.
-</p>
-
-<p>To add the license check and handle the response, you must:</p>
-
-<ol>
-    <li><a href="#imports">Add imports</a></li>
-    <li><a href="#lc-impl">Implement LicenseCheckerCallback</a> as a private inner class</li>
-    <li><a href="#thread-handler">Create a Handler</a> for posting from LicenseCheckerCallback to the UI thread</li>
-    <li><a href="#lc-lcc">Instantiate LicenseChecker</a> and LicenseCheckerCallback</li>
-    <li><a href="#check-access">Call checkAccess()</a> to initiate the license check</li>
-    <li><a href="#account-key">Embed your public key</a> for licensing</li>
-    <li><a href="#handler-cleanup">Call your LicenseChecker's onDestroy() method</a> to close IPC connections.</li>
-</ol>
-
-<p>The sections below describe these tasks. </p>
-
-<h4 id="lc-overview">Overview of license check and response</h4>
-
-<div class="sidebox-wrapper">
-<div class="sidebox">
-<h2>Example: MainActivity</h2>
-
-<p>The sample application included with the LVL provides a full example of how
-to initiate a license check and handle the result, in the
-<code>MainActivity.java</code> file.</p>
-
-</div>
-</div>
-
-<p>In most cases, you should add the license check to your application's main
-{@link android.app.Activity}, in the <code>onCreate()</code> method. This
-ensures that when the user launches your application directly, the license check
-will be invoked immediately. In some cases, you can add license checks in other
-locations as well. For example, if your application includes multiple Activity
-components that other applications can start by {@link android.content.Intent},
-you could add license checks in those Activities.</p>
-
-<p>A license check consists of two main actions: </p>
-
-<ul>
-<li>A call to a method to initiate the license check &mdash; in the LVL, this is
-a call to the <code>checkAccess()</code> method of a LicenseChecker object that
-you construct.</li>
-<li>A callback that returns the result of the license check. In the LVL, this is
-a <code>LicenseCheckerCallback</code> interface that you implement. The
-interface declares two methods, <code>allow()</code> and
-<code>dontAllow()</code>, which are invoked by the library based on to the
-result of the license check. You implement those two methods with whatever logic
-you need, to allow or disallow the user access to your application. Note that
-these methods do not determine <em>whether</em> to allow access &mdash; that
-determination is the responsibility of your Policy implementation. Rather, these
-methods simply provide the application behaviors for <em>how</em> to allow and
-disallow access (and handle application errors).</li>
-</ul>
-
-<div style="margin-bottom:2em;">
-
-<img src="{@docRoot}images/licensing_flow.png" style="text-align:left;margin-bottom:0;margin-left:3em;" />
-<div style="margin:.5em 0 1.5em 2em;padding:0"><strong>Figure 6.</strong> Overview of a
-typical license check interaction.</div>
-</div>
-
-<p>The diagram above illustrates how a typical license check takes place: </p>
-
-<ol>
-<li>Code in the application's main Activity instantiates LicenseCheckerCallback
-and LicenseChecker objects. When constructing LicenseChecker, the code passes in
-{@link android.content.Context}, a Policy implementation to use, and the
-publisher account's public key for licensing as parameters. </li>
-<li>The code then calls the <code>checkAccess()</code> method on the
-LicenseChecker object. The method implementation calls the Policy to determine
-whether there is a valid license response cached locally, in
-{@link android.content.SharedPreferences}.
-<ul>
-<li>If so, the <code>checkAccess()</code> implementation calls
-<code>allow()</code>.</li>
-<li>Otherwise, the LicenseChecker initiates a license check request that is sent
-to the licensing server.</li>
-</ul>
-<p class="note"><strong>Note:</strong> The licensing server always returns
-<code>LICENSED</code> when you perform a license check of a draft application.</p>
-</li>
-<li>When a response is received, LicenseChecker creates a LicenseValidator that
-verifies the signed license data and extracts the fields of the response, then
-passes them to your Policy for further evaluation.
-  <ul>
-    <li>If the license is valid, the Policy caches the response in
-SharedPreferences and notifies the validator, which then calls the
-<code>allow()</code> method on the LicenseCheckerCallback object. </li>
-    <li>If the license not valid, the Policy notifies the validator, which calls
-the <code>dontAllow()</code> method on LicenseCheckerCallback. </li>
-  </ul>
-</li>
-<li>In case of a recoverable local or server error, such as when the network is
-not available to send the request, LicenseChecker passes a RETRY response to
-your Policy's <code>processServerResponse()</code> method. </li>
-<li>In case of a application error, such as when the application attempts to
-check the license of an invalid package name, LicenseChecker passes an error
-response to the LicenseCheckerCallback's  <code>applicationError()</code>
-method. </li>
-</ol>
-
-<p>Note that, in addition to initiating the license check and handling the
-result, which are described in the sections below, your application also needs
-to provide a <a href="#impl-Policy">Policy implementation</a> and, if the Policy
-stores response data (such as ServerManagedPolicy), an <a
-href="#impl-Obfuscator">Obfuscator</a> implementation. </p>
-
-
-<h4 id="imports">Add imports</h4>
-
-<p>First, open the class file of the application's main Activity and import
-LicenseChecker and LicenseCheckerCallback from the LVL package.</p>
-
-<pre>    import com.android.vending.licensing.LicenseChecker;
-    import com.android.vending.licensing.LicenseCheckerCallback;</pre>
-
-<p>If you are using the default Policy implementation provided with the LVL,
-ServerManagedPolicy, import it also, together with the AESObfuscator. If you are
-using a custom Policy or Obfuscator, import those instead. </p>
-
-<pre>    import com.android.vending.licensing.ServerManagedPolicy;
-    import com.android.vending.licensing.AESObfuscator;</pre>
-
-<h4 id="lc-impl">Implement LicenseCheckerCallback as a private inner class</h4>
-
-<p>LicenseCheckerCallback is an interface provided by the LVL for handling
-result of a license check. To support licensing using the LVL, you must
-implement LicenseCheckerCallback and
-its methods to allow or disallow access to the application.</p>
-
-<p>The result of a license check is always a call to one of the
-LicenseCheckerCallback methods, made based on the validation of the response
-payload, the server response code itself, and any additional processing provided
-by your Policy. Your application can implement the methods in any way needed. In
-general, it's best to keep the methods simple, limiting them to managing UI
-state and application access. If you want to add further processing of license
-responses, such as by contacting a backend server or applying custom constraints,
-you should consider incorporating that code into your Policy, rather than
-putting it in the LicenseCheckerCallback methods. </p>
-
-<p>In most cases, you should declare your implementation of
-LicenseCheckerCallback as a private class inside your application's main
-Activity class. </p>
-
-<p>Implement the <code>allow()</code> and <code>dontAllow()</code> methods as
-needed. To start with, you can use simple result-handling behaviors in the
-methods, such as displaying the license result in a dialog. This helps you get
-your application running sooner and can assist with debugging. Later, after you
-have determined the exact behaviors you want, you can add more complex handling.
-</p>
-
-<p>Some suggestions for handling unlicensed responses in
-<code>dontAllow()</code> include: </p>
-
-<ul>
-<li>Display a "Try again" dialog to the user, including a button to initiate a
-new license check. </li>
-<li>Display a "Purchase this application" dialog, including a button that
-deep-links the user to the application's details page on Market, from which the
-use can purchase the application. For more information on how to set up such
-links, see <a
-href="{@docRoot}guide/publishing/publishing.html#marketintent">Using Intents to
-Launch the Market Application on a Device</a>. </li>
-<li>Display a Toast notification that indicates that the features of the
-application are limited because it is not licensed. </li>
-</ul>
-
-<p>The example below shows how the LVL sample application implements
-LicenseCheckerCallback, with methods that display the license check result in a
-dialog. </p>
-
-<pre>    private class MyLicenseCheckerCallback implements LicenseCheckerCallback {
-        public void allow() {
-            if (isFinishing()) {
-                // Don't update UI if Activity is finishing.
-                return;
-            }
-            // Should allow user access.
-            displayResult(getString(R.string.allow));
-        }
-
-        public void dontAllow() {
-            if (isFinishing()) {
-                // Don't update UI if Activity is finishing.
-                return;
-            }
-            displayResult(getString(R.string.dont_allow));
-            // Should not allow access. An app can handle as needed,
-            // typically by informing the user that the app is not licensed
-            // and then shutting down the app or limiting the user to a
-            // restricted set of features.
-            // In this example, we show a dialog that takes the user to Market.
-            showDialog(0);
-        }
-    }
-</pre>
-
-<p>Additionally, you should implement the <code>applicationError()</code>
-method, which the LVL calls to let your application handle errors that are not
-retryable. For a list of such errors, see <a
-href="#server-response-codes">Server Response Codes</a> in the Appendix of this
-document. You can implement the method in any way needed. In most cases, the
-method should log the error code and call <code>dontAllow()</code>.</p>
-
-<h4 id="thread-handler">Create a Handler for posting from LicenseCheckerCallback
-to the UI thread</h4>
-
-<p>During a license check, the LVL passes the request to the Android Market
-application, which handles communication with the licensing server. The LVL
-passes the request over asynchronous IPC (using {@link android.os.Binder}) so
-the actual processing and network communication do not take place on a thread
-managed by your application. Similarly, when the Android Market application
-receives the result, it invokes a  callback method over IPC, which in turn
-executes in an IPC thread pool in your application's process.</p>
-
-<p>The LicenseChecker class manages your application's IPC communication with
-the Android Market application, including the call that sends the request and
-the callback that receives the response. LicenseChecker also tracks open license
-requests and manages their timeouts. </p>
-
-<p>So that it can handle timeouts properly and also process incoming responses
-without affecting your application's UI thread, LicenseChecker spawns a
-background thread at instantiation. In the thread it does all processing of
-license check results, whether the result is a response received from the server
-or a timeout error. At the conclusion of processing, the LVL calls your
-LicenseCheckerCallback methods from the background thread. </p>
-
-<p>To your application, this means that:</p>
-
-<ol>
-<li>Your LicenseCheckerCallback methods will be invoked, in many cases, from a
-background thread.</li>
-<li>Those methods won't be able to update state or invoke any processing in the
-UI thread, unless you create a Handler in the UI thread and have your callback
-methods post to the Handler.</li>
-</ol>
-
-<p>If you want your LicenseCheckerCallback methods to update the UI thread,
-instantiate a {@link android.os.Handler} in the main Activity's
-{@link android.app.Activity#onCreate(android.os.Bundle) onCreate()} method,
-as shown below. In this example, the LVL sample application's
-LicenseCheckerCallback methods (see above) call <code>displayResult()</code> to
-update the UI thread through the Handler's
-{@link android.os.Handler#post(java.lang.Runnable) post()} method.</p>
-
-<pre>private Handler mHandler;
-
-    &#64;Override
-    public void onCreate(Bundle savedInstanceState) {
-        ...
-        mHandler = new Handler();
-    }
-</pre>
-
-<p>Then, in your LicenseCheckerCallback methods, you can use Handler methods to
-post Runnable or Message objects to the Handler. Here's how the sample
-application included in the LVL posts a Runnable to a Handler in the UI thread
-to display the license status.</p>
-
-<pre>    private void displayResult(final String result) {
-        mHandler.post(new Runnable() {
-            public void run() {
-                mStatusText.setText(result);
-                setProgressBarIndeterminateVisibility(false);
-                mCheckLicenseButton.setEnabled(true);
-            }
-        });
-    }
-</pre>
-
-<h4 id="lc-lcc">Instantiate LicenseChecker and LicenseCheckerCallback</h4>
-
-<p>In the main Activity's
-{@link android.app.Activity#onCreate(android.os.Bundle) onCreate()} method,
-create private instances of LicenseCheckerCallback and LicenseChecker. You must
-instantiate LicenseCheckerCallback first, because you need to pass a reference
-to that instance when you call the contructor for LicenseChecker. </p>
-
-<p>When you instantiate LicenseChecker, you need to pass in these parameters:</p>
-
-<ul>
-<li>The application {@link android.content.Context}</li>
-<li>A reference to the Policy implementation to use for the license check. In
-most cases, you would use the default Policy implementation provided by the LVL,
-ServerManagedPolicy. </li>
-<li>The String variable holding your publisher account's public key for
-licensing. </li>
-</ul>
-
-<p>If you are using ServerManagedPolicy, you won't need to access the class
-directly, so you can instantiate it in the LicenseChecker constructor,
-as shown in the example below. Note that you need to pass a reference to a new
-Obfuscator instance when you construct ServerManagedPolicy.</p>
-
-<p>The example below shows the instantiation of LicenseChecker and
-LicenseCheckerCallback from the <code>onCreate()</code> method of an Activity
-class. </p>
-
-<pre>public class MainActivity extends Activity {
-    ...
-    private LicenseCheckerCallback mLicenseCheckerCallback;
-    private LicenseChecker mChecker;
-
-    &#64;Override
-    public void onCreate(Bundle savedInstanceState) {
-        super.onCreate(savedInstanceState);
-        ...
-        // Construct the LicenseCheckerCallback. The library calls this when done.
-        mLicenseCheckerCallback = new MyLicenseCheckerCallback();
-
-        // Construct the LicenseChecker with a Policy.
-        mChecker = new LicenseChecker(
-            this, new ServerManagedPolicy(this,
-                new AESObfuscator(SALT, getPackageName(), deviceId)),
-            BASE64_PUBLIC_KEY  // Your public licensing key.
-            );
-        ...
-    }
-}
-</pre>
-
-
-<p>Note that LicenseChecker calls the LicenseCheckerCallback methods from the UI
-thread <em>only</em> if there is valid license response cached locally. If the
-license check is sent to the server, the callbacks always originate from the
-background thread, even for network errors. </p>
-
-
-<h4 id="check-access">Call checkAccess() to initiate the license check</h4>
-
-<p>In your main Activity, add a call to the <code>checkAccess()</code> method of the
-LicenseChecker instance. In the call, pass a reference to your
-LicenseCheckerCallback instance as a parameter. If you need to handle any
-special UI effects or state management before the call, you might find it useful
-to call <code>checkAccess()</code> from a wrapper method. For example, the LVL
-sample application calls <code>checkAccess()</code> from a
-<code>doCheck()</code> wrapper method:</p>
-
-<pre>    &#64;Override
-    public void onCreate(Bundle savedInstanceState) {
-        super.onCreate(savedInstanceState);
-        ...
-        // Call a wrapper method that initiates the license check
-        doCheck();
-        ...
-    }
-    ...
-    private void doCheck() {
-        mCheckLicenseButton.setEnabled(false);
-        setProgressBarIndeterminateVisibility(true);
-        mStatusText.setText(R.string.checking_license);
-        mChecker.checkAccess(mLicenseCheckerCallback);
-    }
-</pre>
-
-
-<h4 id="account-key">Embed your public key for licensing</h4>
-
-<p>For each publisher account, the Android Market service automatically
-generates a  2048-bit RSA public/private key pair that is used exclusively for
-licensing. The key pair is uniquely associated with the publisher account and is
-shared across all applications that are published through the account. Although
-associated with a publisher account, the key pair is <em>not</em> the same as
-the key that you use to sign your applications (or derived from it).</p>
-
-<p>The Android Market publisher site exposes the public key for licensing to any
-developer signed in to the publisher account, but it keeps the private key
-hidden from all users in a secure location. When an application requests a
-license check for an application published in your account, the licensing server
-signs the license response using the private key of your account's key pair.
-When the LVL receives the response, it uses the public key provided by the
-application to verify the signature of the license response. </p>
-
-<p>To add licensing to an application, you must obtain your publisher account's
-public key for licensing and copy it into your application. Here's how to find
-your account's public key for licensing:</p>
-
-<ol>
-<li>Go to the Android Market <a
-href="http://market.android.com/publish">publisher site</a> and sign in.
-Make sure that you sign in to the account from which the application you are
-licensing is published (or will be published). </li>
-<li>In the account home page, locate the "Edit profile" link and click it. </li>
-<li>In the Edit Profile page, locate the "Licensing" pane, shown below. Your
-public key for licensing is given in the "Public key" text box. </li>
-</ol>
-
-<p>To add the public key to your application, simply copy/paste the key string
-from the text box into your application as the value of the String variable
-<code>BASE64_PUBLIC_KEY</code>. When you are copying, make sure that you have
-selected the entire key string, without omitting any characters. </p>
-
-<p>Here's an example from the LVL sample application:</p>
-
-<pre>    public class MainActivity extends Activity {
-        private static final String BASE64_PUBLIC_KEY = "MIIBIjANBgkqhkiG ... "; //truncated for this example
-    ...
-    }
-</pre>
-
-<h4 id="handler-cleanup">Call your LicenseChecker's onDestroy() method
-to close IPC connections</h4>
-
-<p>Finally, to let the LVL clean up before your application
-{@link android.content.Context} changes, add a call to the LicenseChecker's
-<code>onDestroy()</code> method from your Activity's
-{@link android.app.Activity#onDestroy()} implementation. The call causes the
-LicenseChecker to properly close any open IPC connection to the Android Market
-application's ILicensingService and removes any local references to the service
-and handler.</p>
-
-<p>Failing to call the LicenseChecker's <code>onDestroy()</code> method
-can lead to problems over the lifecycle of your application. For example, if the
-user changes screen orientation while a license check is active, the application
-{@link android.content.Context} is destroyed. If your application does not
-properly close the LicenseChecker's IPC connection, your application will crash
-when the response is received. Similarly, if the user exits your application
-while a license check is in progress,  your application will crash when the
-response is received, unless it has properly called the
-LicenseChecker's <code>onDestroy()</code> method to disconnect from the service.
-</p>
-
-<p>Here's an example from the sample application included in the LVL, where
-<code>mChecker</code> is the LicenseChecker instance:</p>
-
-<pre>    &#64;Override
-    protected void onDestroy() {
-        super.onDestroy();
-        mChecker.onDestroy();
-        ...
-    }
-</pre>
-
-<p>If you are extending or modifying LicenseChecker, you might also need to call
-the LicenseChecker's <code>finishCheck()</code> method, to clean up any open IPC
-connections.</p>
-
-<h3 id="impl-DeviceLimiter">Implementing a DeviceLimiter</h3>
-
-<p>In some cases, you might want your Policy to limit the number of actual
-devices that are permitted to use a single license. This would prevent a user
-from moving a licensed application onto a number of devices and using the
-application on those devices under the same account ID. It would also prevent a
-user from "sharing" the application by providing the account information
-associated with the license to other individuals, who could then sign in to that
-account on their devices and access the license to the application. </p>
-
-<p>The LVL supports per-device licensing by providing a
-<code>DeviceLimiter</code> interface, which declares a single method,
-<code>allowDeviceAccess()</code>. When a LicenseValidator is handling a response
-from the licensing server, it calls <code>allowDeviceAccess()</code>, passing a
-user ID string extracted from the response.</p>
-
-<p>If you do not want to support device limitation, <strong>no work is
-required</strong> &mdash; the LicenseChecker class automatically uses a default
-implementation called NullDeviceLimiter. As the name suggests, NullDeviceLimiter
-is a "no-op" class whose <code>allowDeviceAccess()</code> method simply returns
-a <code>LICENSED</code> response for all users and devices. </p>
-
-<div style="border-left:4px solid #FFCF00;margin:1em;padding: 0 0 0 .5em">
-<p><strong>Caution:</strong> Per-device licensing is <em>not recommended for
-most applications</em> because:</p>
-<ul>
-<li>It requires that you provide a backend server to manage a users and devices
-mapping, and </li>
-<li>It could inadvertently result in a user being denied access to an
-application that they have legitimately purchased on another device.</li>
-</ul>
-</div>
-
-
-<h2 id="test-env">Setting Up the Testing Environment</h2>
-
-<p>The Android Market publisher site provides configuration tools that let you
-and others test licensing on your application before it is published. As you are
-implementing licensing, you can make use of the publisher site tools to test
-your application's Policy and handling of different licensing responses and
-error conditions.</p>
-
-<p>The main components of the test environment for licensing include: </p>
-
-<ul>
-<li>A "Test response" configuration in your publisher account that lets you
-set the static licensing response returned, when the server processes a
-license check for an application uploaded to the publisher account, from a user
-signed in to the publisher account or a test account.</li>
-<li>An optional set of test accounts that will receive the static test
-response when they check the license of an application that you have uploaded
-(regardless whether the application is published or not).</li>
-<li>A runtime environment for the application that includes the Android Market
-application or Google APIs Add-On, on which the user is signed in to the
-publisher account or one of the test accounts.</li>
-</ul>
-
-<p>Setting up the test environment properly involves:</p>
-
-<ol>
-<li><a href="#test-response">Setting static test responses</a> that are returned by the licensing server.</li>
-<li><a href="#test-acct-setup">Setting up test accounts</a> as needed.</li>
-<li><a href="#acct-signin">Signing in</a> properly to an emulator or device, before initiating a license check test.</li>
-</ol>
-
-<p>The sections below provide more information.</p>
-
-
-<h3 id="test-response">Setting test responses for license checks</h3>
-
-<p>Android Market provides a configuration setting in your publisher account
-that lets you override the normal processing of a license check and return a
-specified static response code. The setting is for testing only and applies
-<em>only</em> to license checks for applications that you have uploaded, made by
-any user signed in to an emulator or device using the credentials of the
-publisher account or a registered test account. For other users, the server
-always processes license checks according to normal rules.  </p>
-
-<p>To set a test response for your account, sign in to your publisher account
-and click "Edit Profile". In the Edit Profile page, locate the Test Response
-menu in the Licensing panel, shown below. You can select from the full set of
-valid server response codes to control the response or condition you want to
-test in your application.</p>
-
-<p>In general, you should make sure to test your application's licensing
-implementation with every response code available in the Test Response menu.
-For a description of the codes, see <a href="#server-response-codes">Server
-Response Codes</a> in the Appendix of this document.</p>
-
-<div style="margin-bottom:2em;" id="licensing_test_response">
-
-<img src="{@docRoot}images/licensing_test_response.png" style="text-align:left;margin-bottom:0;" />
-<div style="margin:0 2em;padding:0"><strong>Figure 7.</strong> The Licensing
-panel of your account's Edit Profile page, showing the Test Accounts field and the
-Test Response menu.</div>
-</div>
-
-<p>Note that the test response that you configure applies account-wide &mdash;
-that is, it applies not to a single application, but to <em>all</em>
-applications associated with the publisher account. If you are testing multiple
-applications at once, changing the test response will affect all of those
-applications on their next license check (if the user is signed into
-the emulator or device using the publisher account or a test account).</p>
-
-<p>Before you can successfully receive a test response for a license check,
-you must sign in to the device or emulator on which the application
-is installed, and from which it is querying the server. Specifically, you must
-sign using either your publisher account or one of the test accounts that you
-have set up. For more information about test accounts, see the next section.</p>
-
-<p>See <a href="#server-response-codes">Server Response Codes</a> for a list of
-test responses available and their meanings. </p>
-
-
-<h3 id="test-acct-setup">Setting up test accounts</h3>
-
-<p>In some cases, you might want to let multiple teams of developers test
-licensing on applications that will ultimately be published through your
-publisher account, but without giving them access to your publisher account's
-sign-in credentials. To meet that need, the Android Market publisher site lets
-you set up one or more optional <em>test accounts</em> &mdash; accounts that are
-authorized to query the licensing server and receive static test responses from
-your publisher account.</p>
-
-<p>Test accounts are standard Google accounts that you register on your
-publisher account, such that they will receive the test response for
-applications that you have uploaded. Developers can then sign in to their
-devices or emulators using the test account credentials and initiate license
-checks from installed applications. When the licensing server receives a license
-check from a user of a test account, it returns the static test response
-configured for the publisher account.  </p>
-
-<p>Necessarily, there are limitations on the access and permissions given to
-users signed in through test accounts, including:</p>
-
-<ul>
-<li>Test account users can query the licensing server only for applications that
-are already uploaded to the publisher account. </li>
-<li>Test account users do not have permission to upload applications to your
-publisher account.</li>
-<li>Test account users do not have permission to set the publisher account's
-static test response.</li>
-</ul>
-
-<p>The table below summarizes the differences in capabilities, between the
-publisher account, a test account, and any other account.</p>
-
-<p class="table-caption" id="acct-types-table"><strong>Table 1.</strong>
-Differences in account types for testing licensing.</p>
-
-<table>
-<tr>
-<th>Account Type</th>
-<th>Can check license before upload?</th>
-<th>Can receive test response?</th>
-<th>Can set test response?</th>
-</tr>
-
-<tr>
-<td>Publisher account</td>
-<td>Yes</td>
-<td>Yes</td>
-<td>Yes</td>
-</tr>
-
-<tr>
-<td>Test account</td>
-<td>No</td>
-<td>Yes</td>
-<td>No</td>
-</tr>
-
-<tr>
-<td>Other</td>
-<td>No</td>
-<td>No</td>
-<td>No</td>
-</tr>
-</table>
-
-<h4 id="reg-test-acct">Registering test accounts on the publisher account</h4>
-
-<p>To get started, you need to register each test account in your publisher
-account. As shown in <a href="#licensing_test_response">Figure 7</a>, above, you
-register test accounts in the Licensing panel of your publisher account's Edit
-Profile page. Simply enter the accounts as a comma-delimited list and click
-<strong>Save</strong> to save your profile changes.</p>
-
-<p>You can use any Google account as a test account. If you want to own and
-control the test accounts, you can create the accounts yourself and distribute
-the credentials to your developers or testers.</p>
-
-<h4 id="test-app-upload">Handling application upload and distribution for test
-account users</h4>
-
-<p>As mentioned above, users of test accounts can only receive static test
-responses for applications that are uploaded to the publisher account. Since
-those users do not have permission to upload applications, as the publisher you
-will need to work with those users to collect apps for upload and distribute
-uploaded apps for testing. You can handle collection and distribution in any way
-that is convenient. </p>
-
-<p>Once an application is uploaded and becomes known to the licensing server,
-developers and testers can continue modify the application in their local
-development environment, without having to upload new versions. You only need to
-upload a new version if the local application increments the
-<code>versionCode</code> attribute in the manifest file. </p>
-
-<h4 id="test-key">Distributing your public key to test account users</h4>
-
-<p>The licensing server handles static test responses in the normal way,
-including signing the license response data, adding extras parameters, and so
-on. To support developers who are implementing licensing using test accounts,
-rather than the publisher account, you will need to distribute
-your public key to them. Developers without access to the publisher site do not
-have access to your public key, and without the key they won't be able to
-verify license responses. </p>
-
-<p>Note that if you decide to generate a new licensing key pair for your account
-for some reason, you need to notify all users of test accounts. For
-testers, you can embed the new key in the application package and distribute it
-to users. For developers, you will need to distribute the new key to them
-directly. </p>
-
-
-<h3 id="acct-signin">Signing in to an authorized account in the runtime
-environment</h3>
-
-<p>The licensing service is designed to determine whether a given user is
-licensed to use a given application &mdash; during a license check, the Android
-Market application gathers the user ID from the primary account on the system
-and sends it to the server, together with the package name of the application
-and other information. However, if there is no user information available, the
-license check cannot succeed, so the Android Market application terminates the
-request and returns an error to the application. </p>
-
-<p>During testing, to ensure that your application can successfully query the
-licensing server, you must make sure that you sign in to an account <em>on the
-device or emulator</em> using:</p>
-
-<ul>
-<li>The credentials of a publisher account, or</li>
-<li>The credentials of a test account that is registered with a publisher
-account</li>
-</ul>
-
-
-<div class="sidebox-wrapper">
-<div class="sidebox">
-<h2>Signing in to a Google account on an emulator</h2>
-
-<p>If you are testing licensing on an emulator, you need to sign in to a Google
-account on the emulator. If you do not see an option to create a new Google
-account, the problem might be that your AVD is running a standard Android system
-image, rather than the Google APIs Add-On, API 8 (release 2) or higher. </p>
-
-<p style="margin-top:.5em;">For more information, see <a
-href="#runtime-setup">Setting up the runtime environment</a>, above.</p>
-
-</div>
-</div>
-
-<p>Signing in using a publisher account offers the advantage of letting your
-applications receive static test responses even before the applications are
-uploaded to the publisher site.</p>
-
-<p>If you are part of a larger organization or are working with external groups
-on applications that will be published through your site, you will more likely
-want to distribute test accounts instead, then use those to sign in during
-testing. </p>
-
-<p>To sign in on a device or emulator, follow the steps below. The preferred
-approach is to sign in as the primary account &mdash; however, if there are
-other accounts already in use on the device or emulator, you can create an
-additional account and sign in to it using the publisher or test account
-credentials.  </p>
-
-<ol>
-<li>Open Settings &gt; Accounts &amp; sync</li>
-<li>Select <strong>Add Account</strong> and choose to add a "Google" account.
-</li>
-<li>Select <strong>Next</strong> and then <strong>Sign in</strong>.</li>
-<li>Enter the username and password of either the publisher account or a test
-account that is registered in the publisher account.</li>
-<li>Select <strong>Sign in</strong>. The system signs you in to the new
-account.</li>
-</ol>
-
-<p>Once you are signed in, you can begin testing licensing in your application
-(if you have completed the LVL integration steps above). When your application
-initiates a license check, it will receive a response containing the static test
-response configured on the publisher account. </p>
-
-<p>Note that, if you are using an emulator, you will need to sign in to the
-publisher account or test account each time you wipe data when restarting the
-emulator.</p>
-
-<div style="margin:2em 1em 1em 1em;">
-
-<img src="{@docRoot}images/licensing_device_signin.png" style="text-align:left;" />
-<div style="margin:.25em 1.25em;padding:0"><strong>Figure 8.</strong> Example of
-setting up a Google account on a device or emulator.</div>
-</div>
-
-<h2 id="app-obfuscation">Obfuscating Your Application</h2>
-
-<p>To ensure the security of your application, particularly for a paid
-application that uses licensing and/or custom constraints and protections, it's
-very important to obfuscate your application code. Properly obfuscating your
-code makes it more difficult for a malicious user to decompile the application's
-bytecode, modify it &mdash; such as by removing the license check &mdash;
-and then recompile it.</p>
-
-<p>Several obfuscator programs are available for Android applications, including
-<a href="http://proguard.sourceforge.net/">ProGuard</a>, which also offers
-code-optimization features. The use of ProGuard or a similar program to obfuscate
-your code is <em>strongly recommended</em> for all applications that use Android
-Market Licensing. </p>
-
-<h2 id="app-publishing">Publishing a Licensed Application</h2>
-
-<p>When you are finished testing your license implementation, you are ready to
-publish the application on Android Market. Follow the normal steps to <a
-href="{@docRoot}guide/publishing/preparing.html">prepare</a>, <a
-href="{@docRoot}guide/publishing/app-signing.html">sign</a>, and then <a
-href="{@docRoot}guide/publishing/publishing.html">publish the application</a>.
-</p>
-
-<h4>Removing Copy Protection</h4>
-
-<p>After uploading your licensed application, remember to remove copy protection
-from the application, if it is currently used. To check and remove copy
-protection, sign in to the publisher site and go the application's upload
-details page. In the Publishing options section, make sure that the Copy
-Protection radio button selection is "Off".</p>
-
-<h4>Considerations for Free Apps</h4>
-
-<p>Licensing is currently supported only for paid applications. If you already
-published your application as free, you won't be able to upload an updated
-version that includes licensing (that is, an application that uses the same
-package name and that includes the <a href="#manifest-permission">licensing
-permission</a>). Here are some points to keep in mind:</p>
-
-<ul>
-<li>If you want to offer a free version of your application that provides a
-reduced feature set (or that offers the full feature set for trial period), the
-free version of your application must not include the licensing permission and
-must use a different package name than the paid version of the app.</li>
-<li>If you want to offer a paid version of your free application that uses
-licensing, you can do so under a new package name.</li>
-</ul>
-
-<h2 id="support">Where to Get Support</h2>
-
-<p>If you have questions or encounter problems while implementing or deploying
-publishing in your applications, please use the support resources listed in the
-table below. By directing your queries to the correct forum, you can get the
-support you need more quickly. </p>
-
-<p class="table-caption"><strong>Table 2.</strong> Developer support resources
-for Android Market Licensing Service.</p>
-
-<table>
-
-<tr>
-<th>Support Type</th>
-<th>Resource</th>
-<th>Range of Topics</th>
-</tr>
-<tr>
-<td rowspan="2">Development and testing issues</td>
-<td>Google Groups: <a
-href="http://groups.google.com/group/android-developers">android-developers</a>
-</td>
-<td rowspan="2">LVL download and integration, library projects, Policy
-questions, user experience ideas, handling of responses, Obfuscator, IPC, test
-environment setup</td>
-</tr>
-<tr>
-<td>Stack Overflow: <a
-href="http://stackoverflow.com/questions/tagged/android">http://stackoverflow.com/questions/tagged/android</a></td>
-</tr>
-<tr>
-<td rowspan="2">Accounts, publishing, and deployment issues</td>
-<td><a href="http://www.google.com/support/forum/p/Android+Market">Android
-Market Help Forum</a></td>
-<td rowspan="2">Publisher accounts, licensing key pair, test accounts, server
-responses, test responses, application deployment and results</td>
-</tr>
-<tr>
-<td><a
-href="http://market.android.com/support/bin/answer.py?answer=186113">Market
-Licensing Support FAQ</a></td>
-</tr>
-<tr>
-<td>LVL issue tracker</td>
-<td><a href="http://code.google.com/p/marketlicensing/issues/">Marketlicensing
-project issue tracker</a></td>
-<td>Bug and issue reports related specifically to the LVL source code classes
-and interface implementations</td>
-</tr>
-
-</table>
-
-<p>For general information about how to post to the groups listed above, see <a
-href="{@docRoot}resources/community-groups.html">Developer Forums</a> document
-in the Resources tab.</p>
-
-<h2 id="lvl-summary">Summary of LVL Classes and Interfaces</h2>
-
-<p>The table below lists all of the source files in the License Verification
-Library (LVL) available through the Android SDK. All of the files are part of
-the <code>com.android.vending.licensing</code> package.</p>
-
-<p class="table-caption"><strong>Table A-1.</strong> Summary of LVL library
-classes and interfaces.</p>
-
-<div style="width:99%">
-<table width="100%">
-
-<tr>
-<th width="15%">Category</th>
-<th width="20%">Name</th>
-<th width="100%">Description</th>
-</tr>
-
-<tr>
-<td rowspan="2">License check and result</td>
-<td>LicenseChecker</td>
-<td>Class that you instantiate (or subclass) to initiate a license check.</td>
-</tr>
-<tr>
-<td><em>LicenseCheckerCallback</em></td>
-<td>Interface that you implement to handle result of the license check.</td>
-</tr>
-
-<tr>
-<td rowspan="3" width="15%">Policy</td>
-<td width="20%"><em>Policy</em></td>
-<td width="100%">Interface that you implement to determine whether to allow
-access to the application, based on the license response. </td>
-</tr>
-<tr>
-<td>ServerManagedPolicy</td>
-<td width="100%">Default Policy implementation. Uses settings provided by the
-licensing server to manage local storage of license data, license validity,
-retry.</td>
-</tr>
-<tr>
-<td>StrictPolicy</td>
-<td>Alternative Policy implementation. Enforces licensing based on a direct
-license response from the server only. No caching or request retry.</td>
-</tr>
-
-<tr>
-<td rowspan="2" width="15%">Data obfuscation <br><em>(optional)</em></td>
-<td width="20%"><em>Obfuscator</em></td>
-<td width="100%">Interface that you implement if you are using a Policy (such as
-ServerManagedPolicy) that caches license response data in a persistent store.
-Applies an obfuscation algorithm to encode and decode data being written or
-read.</td>
-</tr>
-<tr>
-<td>AESObfuscator</td>
-<td>Default Obfuscator implementation that uses AES encryption/decryption
-algorithm to obfuscate/unobfuscate data.</td>
-</tr>
-
-<tr>
-<td rowspan="2" width="15%">Device limitation<br><em>(optional)</em></td>
-<td width="20%"><em>DeviceLimiter</em></td>
-<td width="100%">Interface that you implement if you want to restrict use of an
-application to a specific device. Called from LicenseValidator. Implementing
-DeviceLimiter is not recommended for most applications because it requires a
-backend server and may cause the user to lose access to licensed applications,
-unless designed with care.</td>
-</tr>
-<tr>
-<td>NullDeviceLimiter</td>
-<td>Default DeviceLimiter implementation that is a no-op (allows access to all
-devices).</td>
-</tr>
-
-<tr>
-<td rowspan="6" width="15%">Library core, no integration needed</td>
-<td width="20%">ResponseData</td>
-<td width="100%">Class that holds the fields of a license response.</td>
-</tr>
-<tr>
-<td>LicenseValidator</td>
-<td>Class that decrypts and verifies a response received from the licensing
-server.</td>
-</tr>
-<tr>
-<td>ValidationException</td>
-<td>Class that indicates errors that occur when validating the integrity of data
-managed by an Obfuscator.</td>
-</tr>
-<tr>
-<td>PreferenceObfuscator</td>
-<td>Utility class that writes/reads obfuscated data to the system's
-{@link android.content.SharedPreferences} store.</td>
-</tr>
-<tr>
-<td><em>ILicensingService</em></td>
-<td>One-way IPC interface over which a license check request is passed to the
-Android Market client.</td>
-</tr>
-<tr>
-<td><em>ILicenseResultListener</em></td>
-<td>One-way IPC callback implementation over which the application receives an
-asynchronous response from the licensing server.</td>
-</tr>
-
-</table>
-</div>
-
-
-<h2 id="server-response-codes">Server Response Codes</h2>
-
-<p>The table below lists all of the license response codes supported by the
-licensing server. In general, an application should handle all of these response
-codes. By default, the LicenseValidator class in the LVL provides all of the
-necessary handling of these response codes for you. </p>
-
-<p class="table-caption"><strong>Table A-2.</strong> Summary of response codes
-returned by the Android Market server in a license response.</p>
-
-<table>
-
-<tr>
-<th>Response Code</th>
-<th>Description</th>
-<th>Signed?</th>
-<th>Extras</th>
-<th>Comments</th>
-</tr>
-<tr>
-<td>LICENSED</td>
-<td>The application is licensed to the user. The user has purchased the
-application or the application only exists as a draft.</td>
-<td>Yes</td>
-<td><code>VT</code>,&nbsp;<code>GT</code>, <code>GR</code></td>
-<td><em>Allow access according to Policy constraints.</em></td>
-</tr>
-<tr>
-<td>LICENSED_OLD_KEY</td>
-<td>The application is licensed to the user, but there is an updated application
-version available that is signed with a different key. </td>
-<td>Yes </td>
-<td><code>VT</code>, <code>GT</code>, <code>GR</code>, <code>UT</code></td>
-<td><em>Optionally allow access according to Policy constraints.</em>
-<p style="margin-top:.5em;">Can indicate that the key pair used by the installed
-application version is invalid or compromised. The application can allow access
-if needed or inform the user that an upgrade is available and limit further use
-until upgrade.</p>
-</td>
-</tr>
-<tr>
-<td>NOT_LICENSED</td>
-<td>The application is not licensed to the user.</td>
-<td>No</td>
-<td></td>
-<td><em>Do not allow access.</em></td>
-</tr>
-<tr>
-<td>ERROR_CONTACTING_SERVER</td>
-<td>Local error &mdash; the Android Market application was not able to reach the
-licensing server, possibly because of network availability problems. </td>
-<td>No</td>
-<td></td>
-<td><em>Retry the license check according to Policy retry limits.</em></td>
-</tr>
-<tr>
-<td>ERROR_SERVER_FAILURE</td>
-<td>Server error &mdash; the server could not load the publisher account's key
-pair for licensing.</td>
-<td>No</td>
-<td></td>
-<td><em>Retry the license check according to Policy retry limits.</em>
-</td>
-</tr>
-<tr>
-<td>ERROR_INVALID_PACKAGE_NAME</td>
-<td>Local error &mdash; the application requested a license check for a package
-that is not installed on the device. </td>
-<td>No </td>
-<td></td>
-<td><em>Do not retry the license check.</em>
-<p style="margin-top:.5em;">Typically caused by a development error.</p>
-</td>
-</tr>
-<tr>
-<td>ERROR_NON_MATCHING_UID</td>
-<td>Local error &mdash; the application requested a license check for a package
-whose UID (package, user ID pair) does not match that of the requesting
-application. </td>
-<td>No </td>
-<td></td>
-<td><em>Do not retry the license check.</em>
-<p style="margin-top:.5em;">Typically caused by a development error.</p>
-</td>
-</tr>
-<tr>
-<td>ERROR_NOT_MARKET_MANAGED</td>
-<td>Server error &mdash; the application (package name) was not recognized by
-Android Market. </td>
-<td>No</td>
-<td></td>
-<td><em>Do not retry the license check.</em>
-<p style="margin-top:.5em;">Can indicate that the application was not published
-through Android Market or that there is an development error in the licensing
-implementation.</p>
-</td>
-</tr>
-
-</table>
-
-<p class="note"><strong>Note:</strong> As documented in <a href="#test-env">
-Setting Up The Testing Environment</a>, the response code can be manually
-overridden for the application developer and any registered test users via the
-Android Market publisher site.
-<br/><br/>
-Additionally, as noted above, applications that are in draft mode (in other
-words, applicaitons that have been uploaded but have <em>never</em> been
-published) will return LICENSED for all users, even if not listed as a test
-user. Since the application has never been offered for download, it is assumed
-that any users running it must have obtained it from an authorized channel for
-testing purposes.</p>
-
-<h2 id="extras">Server Response Extras</h2>
-
-<p>The licensing server includes several settings in certain types of license
-responses, to assist the application and its Policy in managing access to the
-application across the 24-hour refund period and other conditions. Specifically,
-the server provides recommended values for the application's license validity
-period, retry grace period, maximum allowable retry count, and other settings.
-The server appends the settings as key-value pairs in the license response
-"extras" field. </p>
-
-<p>Any Policy implementation can extract the extras settings from the license
-response and use them as needed. The LVL default Policy implementation, <a
-href="#ServerManagedPolicy">ServerManagedPolicy</a>, serves as a working
-implementation and an illustration of how to obtain, store, and use the
-settings. </p>
-
-<p class="table-caption"><strong>Table A-3.</strong> Summary of
-license-management settings supplied by the Android Market server in a license
-response.</p>
-
-<table>
-<tr>
-<th>Extra</th><th>Description</th>
-</tr>
-
-<tr>
-  <td>VT</td>
-  <td>License validity timestamp. Specifies the date/time at which the current
-(cached) license response expires and must be rechecked on the licensing server.
- </td>
-</tr>
-<tr>
-  <td>GT</td>
-  <td>Grace period timestamp. Specifies the end of the period during which a
-Policy may allow access to the application, even though the response status is
-RETRY. <p>The value is managed by the server, however a typical value would be 5
-or more days.</p></td>
-</tr>
-<tr>
-  <td>GR</td>
-  <td>Maximum retries count. Specifies how many consecutive RETRY license checks
-the Policy should allow, before denying the user access to the application.
-<p>The value is managed by the server, however a typical value would be "10" or
-higher.</p></td>
-</tr>
-<tr>
-  <td>UT</td>
-  <td>Update timestamp. Specifies the day/time when the most recent update to
-this application was uploaded and published. <p>The server returns this extra
-only for LICENSED_OLD_KEYS responses, to allow the Policy to determine how much
-time has elapsed since an update was published with new licensing keys before
-denying the user access to the application. </p></td>
-</tr>
-
-</table>
-
-<p>The sections below provide more information about the server-provided
-settings and how to use them. </p>
-
-<h4>License validity period</h4>
-
-<p>The Android Market licensing server sets a license validity period for all
-downloaded applications. The period expresses the interval of time over which an
-application's license status should be considered as unchanging and cacheable by
-a licensing Policy in the application. The licensing server includes the
-validity period in its response to all license checks, appending an
-end-of-validity timestamp to the response as an extra under the key "VT". A
-Policy can extract the VT key value and use it to conditionally allow access to
-the application without rechecking the license, until the validity period
-expires. </p>
-
-<p>The license validity signals to a licensing Policy when it must recheck the
-licensing status with the licensing server. It is <em>not</em> intended to imply
-whether an application is actually licensed for use. That is, when an
-application's license validity period expires, this does not mean that the
-application is no longer licensed for use &mdash; rather, it indicates only that
-the Policy must recheck the licensing status with the server. It follows that,
-as long as the license validity period is not expired, it is acceptable for the
-Policy to cache the initial license status locally and return the cached license
-status instead of sending a new license check to the server.</p>
-
-<p>The licensing server manages the validity period as a means of helping the
-application properly enforce licensing across the refund period offered by
-Android Market for paid applications. It sets the validity period based on
-whether the application was purchased and, if so, how long ago. Specifically,
-the server sets a validity period as follows:</p>
-
-<ul>
-<li>For a paid application, the server sets the initial license validity period
-so that the license response remains valid for as long as the application is
-refundable. A licensing Policy in the application may cache the
-result of the initial license check and does not need to recheck the license
-until the validity period has expired.</li>
-<li>When an application is no longer refundable, the server
-sets a longer validity period &mdash; typically a number of days. </li>
-<li>For a free application, the server sets the validity period to a very high
-value (<code>long.MAX_VALUE</code>). This ensures that, provided the Policy has
-cached the validity timestamp locally, it will not need to recheck the
-license status of the application in the future.</li>
-</ul>
-
-<p>The ServerManagedPolicy implementation uses the extracted timestamp
-(<code>mValidityTimestamp</code>) as a primary condition for determining whether
-to recheck the license status with the server before allowing the user access to
-the application. </p>
-
-<h4>Retry period and maximum retry count</h4>
-
-<p>In some cases, system or network conditions can prevent an application's
-license check from reaching the licensing server, or prevent the server's
-response from reaching the Android Market client application. For example, the
-user might launch an application when there is no cell network or data
-connection available &mdash; such as when on an airplane &mdash; or when the
-network connection is unstable or the cell signal is weak. </p>
-
-<p>When network problems prevent or interrupt a license check, the Android
-Market client notifies the application by returning a "RETRY" response code to
-the Policy's <code>processServerResponse()</code> method. In the case of system
-problems, such as when the application is unable to bind with Android Market's
-ILicensingService implementation, the LicenseChecker library itself calls the
-Policy <code>processServerResonse()</code> method with a "RETRY" response code.
-</p>
-
-<p>In general, the RETRY response code is a signal to the application that an
-error has occurred that has prevented a license check from completing.
-
-<p>The Android Market server helps an application to manage licensing under
-error conditions by setting a retry "grace period" and a recommended maximum
-retries count. The server includes these values in all license check responses,
-appending them as extras under the keys "GT" and "GR". </p>
-
-<p>The application Policy can extract the GT and GR extras and use them to
-conditionally allow access to the application, as follows:</p>
-
-<ul>
-<li>For a license check that results in a RETRY response, the Policy should
-cache the RETRY response code and increment a count of RETRY responses.</li>
-<li>The Policy should allow the user to access the application, provided that
-either the retry grace period is still active or the maximum retries count has
-not been reached.</li>
-</ul>
-
-<p>The ServerManagedPolicy uses the server-supplied GT and GR values as
-described above. The example below shows the conditional handling of the retry
-responses in the <code>allow()</code> method. The count of RETRY responses is
-maintained in the <code>processServerResponse()</code> method, not shown. </p>
-
-
-<pre>    public boolean allowAccess() {
-        long ts = System.currentTimeMillis();
-        if (mLastResponse == LicenseResponse.LICENSED) {
-            // Check if the LICENSED response occurred within the validity timeout.
-            if (ts &lt;= mValidityTimestamp) {
-                // Cached LICENSED response is still valid.
-                return true;
-            }
-        } else if (mLastResponse == LicenseResponse.RETRY &amp;&amp;
-                   ts &lt; mLastResponseTime + MILLIS_PER_MINUTE) {
-            // Only allow access if we are within the retry period or we haven't used up our
-            // max retries.
-            return (ts &lt;= mRetryUntil || mRetryCount &lt;= mMaxRetries);
-        }
-        return false;
-    }</pre>
-
diff --git a/docs/html/guide/publishing/preparing.jd b/docs/html/guide/publishing/preparing.jd
index 83aa5ee..c355479 100644
--- a/docs/html/guide/publishing/preparing.jd
+++ b/docs/html/guide/publishing/preparing.jd
@@ -291,7 +291,8 @@
 releasing your app through Android Market.</p>
 
 <p>For more information about Android Market Licensing Service and how to use it in your
-application, see <a href="{@docRoot}guide/publishing/licensing.html">Application Licensing</a>.</p>
+application, see <a href="{@docRoot}guide/market/licensing/index.html">Application
+Licensing</a>.</p>
 
 <h2 id="publishing-build">Building Your Application for Release</h2>
 
diff --git a/docs/html/guide/publishing/publishing.jd b/docs/html/guide/publishing/publishing.jd
index 49b34d8..27a87f9 100644
--- a/docs/html/guide/publishing/publishing.jd
+++ b/docs/html/guide/publishing/publishing.jd
@@ -74,7 +74,7 @@
 identify market trends, and control who your applications are being distributed to. You also have
 access to several revenue-enhancing features, such as <a
 href="{@docRoot}guide/market/billing/index.html">in-app billing</a> and
-<a href="{@docRoot}guide/publishing/licensing.html">application licensing</a>.</p>
+<a href="{@docRoot}guide/market/licensing/index.html">application licensing</a>.</p>
 
 <p>Before you can publish applications on Android Market, you need to <a
 href="http://market.android.com/publish">register</a> as an Android Market developer. During the
@@ -254,7 +254,7 @@
 
 <p>For complete information about Android Market Licensing Service and how to
 use it in your application, read <a
-href="{@docRoot}guide/publishing/licensing.html">Application Licensing</a>.</p>
+href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a>.</p>
 
 <h2 id="marketinappbilling">Using Android Market In-app Billing</h2>
 
diff --git a/docs/html/guide/publishing/publishing_overview.jd b/docs/html/guide/publishing/publishing_overview.jd
index 79199c5..c94d201 100755
--- a/docs/html/guide/publishing/publishing_overview.jd
+++ b/docs/html/guide/publishing/publishing_overview.jd
@@ -130,7 +130,8 @@
 identify market trends, and control who your applications are being distributed to. You also have
 access to several revenue-enhancing features that are not available anywhere else, such as <a
 href="{@docRoot}guide/market/billing/index.html">in-app billing</a> and <a
-href="{@docRoot}guide/publishing/licensing.html">application licensing</a>. This rich array of tools
+href="{@docRoot}guide/market/licensing/index.html">application licensing</a>. This rich array of
+tools
 and features, coupled with numerous end-user community features, makes Android Market the premier
 marketplace for selling and buying Android applications.</p>
 
diff --git a/docs/html/guide/topics/fundamentals/activities.jd b/docs/html/guide/topics/fundamentals/activities.jd
index 8736aa8..b79136c 100644
--- a/docs/html/guide/topics/fundamentals/activities.jd
+++ b/docs/html/guide/topics/fundamentals/activities.jd
@@ -62,7 +62,7 @@
 activity can then start another activity in order to perform different actions. Each time a new
 activity starts, the previous activity is stopped, but the system preserves the activity
 in a stack (the "back stack"). When a new activity starts, it is pushed onto the back stack and
-takes user focus. The back stack abides to the basic "last in, first out" queue mechanism,
+takes user focus. The back stack abides to the basic "last in, first out" stack mechanism,
 so, when the user is done with the current activity and presses the <em>Back</em> button, it
 is popped from the stack (and destroyed) and the previous activity resumes. (The back stack is
 discussed more in the <a href="{@docRoot}guide/topics/fundamentals/tasks-and-back-stack.html">Tasks
diff --git a/docs/html/guide/topics/fundamentals/fragments.jd b/docs/html/guide/topics/fundamentals/fragments.jd
index 281cb9d..2a22394 100644
--- a/docs/html/guide/topics/fundamentals/fragments.jd
+++ b/docs/html/guide/topics/fundamentals/fragments.jd
@@ -129,7 +129,7 @@
 
 <p>For example&mdash;to continue with the news application example&mdash;the application can embed
 two fragments in <em>Activity A</em>, when running on a tablet-sized device. However, on a
-handset-sized screen, there's not be enough room for both fragments, so <em>Activity A</em> includes
+handset-sized screen, there's not enough room for both fragments, so <em>Activity A</em> includes
 only the fragment for the list of articles, and when the user selects an article, it starts
 <em>Activity B</em>, which includes the second fragment to read the article. Thus, the application
 supports both tablets and handsets by reusing fragments in different combinations, as illustrated in
diff --git a/docs/html/guide/topics/graphics/hardware-accel.jd b/docs/html/guide/topics/graphics/hardware-accel.jd
index 39ccbf4..04fb564 100644
--- a/docs/html/guide/topics/graphics/hardware-accel.jd
+++ b/docs/html/guide/topics/graphics/hardware-accel.jd
@@ -42,19 +42,20 @@
         <li><a href="{@docRoot}guide/topics/graphics/opengl.html">OpenGL with the Framework
         APIs</a></li>
 
-        <li><a href="{@docRoot}guide/topics/renderscript/index.html">RenderScript</a></li>
+        <li><a href="{@docRoot}guide/topics/renderscript/index.html">Renderscript</a></li>
       </ol>
     </div>
   </div>
 
   <p>Beginning in Android 3.0 (API level 11), the Android 2D rendering pipeline is designed to
   better support hardware acceleration. Hardware acceleration carries out all drawing operations
-  that are performed on a {@link android.view.View}'s canvas using the GPU.</p>
+  that are performed on a {@link android.view.View}'s canvas using the GPU. Because of the
+  increased resources required to enable hardware acceleration, your app will consume more RAM.</p>
 
   <p>The easiest way to enable hardware acceleration is to turn it on
   globally for your entire application. If your application uses only standard views and {@link
   android.graphics.drawable.Drawable}s, turning it on globally should not cause any adverse
-  effects. However, because hardware acceleration is not supported for all of the 2D drawing
+  drawing effects. However, because hardware acceleration is not supported for all of the 2D drawing
   operations, turning it on might affect some of your applications that use custom views or drawing
   calls. Problems usually manifest themselves as invisible elements, exceptions, or wrongly
   rendered pixels. To remedy this, Android gives you the option to enable or disable hardware
diff --git a/docs/html/guide/topics/manifest/activity-element.jd b/docs/html/guide/topics/manifest/activity-element.jd
index f44901b..8b131c8 100644
--- a/docs/html/guide/topics/manifest/activity-element.jd
+++ b/docs/html/guide/topics/manifest/activity-element.jd
@@ -307,7 +307,7 @@
 <dd>Whether or not an existing instance of the activity should be shut down 
 (finished) whenever the user again launches its task (chooses the task on the 
 home screen) &mdash; "{@code true}" if it should be shut down, and "{@code false}" 
-if not.  The default value is "{@code false}". 
+if not. The default value is "{@code false}".
 
 <p>
 If this attribute and 
@@ -321,13 +321,15 @@
 Activity &mdash; "{@code true}" if it should be enabled, and "{@code false}" if
 not. The default value is "{@code false}".
 
+
 <p>Starting from Android 3.0, a hardware-accelerated OpenGL renderer is
 available to applications, to improve performance for many common 2D graphics
 operations. When the hardware-accelerated renderer is enabled, most operations
 in Canvas, Paint, Xfermode, ColorFilter, Shader, and Camera are accelerated.
 This results in smoother animations, smoother scrolling, and improved
 responsiveness overall, even for applications that do not explicitly make use
-the framework's OpenGL libraries. </p>
+the framework's OpenGL libraries. Because of the increased resources required to
+enable hardware acceleration, your app will consume more RAM.</p>
 
 <p>Note that not all of the OpenGL 2D operations are accelerated. If you enable
 the hardware-accelerated renderer, test your application to ensure that it can
@@ -587,9 +589,9 @@
 </p></dd>
 
 <dt><a name="proc"></a>{@code android:process}</dt>
-<dd>The name of the process in which the activity should run.  Normally, 
+<dd>The name of the process in which the activity should run. Normally, 
 all components of an application run in the default process created for the 
-application.  It has the same name as the application package.  The <code><a href="{@docRoot}guide/topics/manifest/application-element.html">&lt;application&gt;</a></code> element's 
+application.  It has the same name as the application package. The <code><a href="{@docRoot}guide/topics/manifest/application-element.html">&lt;application&gt;</a></code> element's 
 <code><a href="{@docRoot}guide/topics/manifest/application-element.html#proc">process</a></code> 
 attribute can set a different default for all components.  But each component 
 can override the default, allowing you to spread your application across 
@@ -706,7 +708,7 @@
 A "{@code true}" setting ensures that the activity can be restarted in the 
 absence of retained state.  For example, the activity that displays the 
 home screen uses this setting to make sure that it does not get removed if it 
-crashes for some reason. 
+crashes for some reason.
 </p></dd>
 
 <dt><a name="aff"></a>{@code android:taskAffinity}</dt>
diff --git a/docs/html/guide/topics/manifest/manifest-element.jd b/docs/html/guide/topics/manifest/manifest-element.jd
index d737a67..c970c72 100644
--- a/docs/html/guide/topics/manifest/manifest-element.jd
+++ b/docs/html/guide/topics/manifest/manifest-element.jd
@@ -152,7 +152,7 @@
 
 <p class="caution"><strong>Caution:</strong> If your application uses the Android Market's Copy 
   Protection feature, it cannot be installed to a device's SD card. However, if you use Android 
-  Market's <a href="{@docRoot}guide/publishing/licensing.html">Application Licensing</a> instead, 
+  Market's <a href="{@docRoot}guide/market/licensing/index.html">Application Licensing</a> instead, 
   your application <em>can</em> be installed to internal or external storage, including SD cards.</p>
 
 <p class="note"><strong>Note:</strong> By default, your application will be installed on the
diff --git a/docs/html/guide/topics/renderscript/graphics.jd b/docs/html/guide/topics/renderscript/graphics.jd
index 1c6d0de..462a990 100644
--- a/docs/html/guide/topics/renderscript/graphics.jd
+++ b/docs/html/guide/topics/renderscript/graphics.jd
@@ -142,7 +142,7 @@
 
       <p class="note"><strong>Note:</strong> The Renderscript runtime makes its best effort to
       refresh the frame at the specified rate. For example, if you are creating a live wallpaper
-      and set the return value to 20, the Renderscript runtime renders the wallpaper at 20fps if it has just
+      and set the return value to 20, the Renderscript runtime renders the wallpaper at 50fps if it has just
       enough or more resources to do so. It renders as fast as it can if not enough resources
       are available.</p>
 
@@ -570,7 +570,7 @@
   vertex 0, 1, and 2 (the vertices are drawn counter-clockwise).</p>
   <pre>
 int float2VtxSize = 2;
-Mesh.TriangleMeshBuilder triangle = new Mesh.TriangleMeshBuilder(renderscriptGL,
+Mesh.TriangleMeshBuilder triangles = new Mesh.TriangleMeshBuilder(renderscriptGL,
 float2VtxSize, Mesh.TriangleMeshBuilder.COLOR);
 triangles.addVertex(300.f, 300.f);
 triangles.addVertex(150.f, 450.f);
diff --git a/docs/html/guide/topics/renderscript/index.jd b/docs/html/guide/topics/renderscript/index.jd
index a0e8876..24b9750 100644
--- a/docs/html/guide/topics/renderscript/index.jd
+++ b/docs/html/guide/topics/renderscript/index.jd
@@ -231,7 +231,8 @@
 
 <p>
 If you want the Renderscript code to send a value back to the Android framework, use the
-<code>rsSendToClient()</code> function.
+<a href="{@docRoot}reference/renderscript/rs__core_8rsh.html"><code>rsSendToClient()</code></a>
+function.
 </p>
 
 <h3 id="var">Variables</h3>
@@ -256,53 +257,6 @@
 }
   </pre>
 
-  <h3 id="pointer">Pointers</h3>
-  <p>Pointers are reflected into the script class itself, located in
-<code>project_root/gen/package/name/ScriptC_renderscript_filename</code>. You
-can declare pointers to a <code>struct</code> or any of the supported Renderscript types, but a
-<code>struct</code> cannot contain pointers or nested arrays. For example, if you declare the
-following pointers to a <code>struct</code> and <code>int32_t</code></p>
-
-<pre>
-typedef struct Point {
-    float2 point;
-} Point_t;
-
-Point_t *touchPoints;
-int32_t *intPointer;
-</pre>
-  <p>then the following code is generated in:</p>
-
-  <pre>
-private ScriptField_Point mExportVar_touchPoints;
-public void bind_touchPoints(ScriptField_Point v) {
-    mExportVar_touchPoints = v;
-    if (v == null) bindAllocation(null, mExportVarIdx_touchPoints);
-    else bindAllocation(v.getAllocation(), mExportVarIdx_touchPoints);
-    }
-
-    public ScriptField_Point get_touchPoints() {
-    return mExportVar_touchPoints;
-    }
-
-    private Allocation mExportVar_intPointer;
-    public void bind_intPointer(Allocation v) {
-    mExportVar_intPointer = v;
-    if (v == null) bindAllocation(null, mExportVarIdx_intPointer);
-    else bindAllocation(v, mExportVarIdx_intPointer);
-    }
-
-    public Allocation get_intPointer() {
-        return mExportVar_intPointer;
-    }
-  </pre>
-
-<p>A <code>get</code> method and a special method named <code>bind_<em>pointer_name</em></code>
-(instead of a <code>set()</code> method) is generated. This method allows you to bind the memory
-that is allocated in the Android VM to the Renderscript runtime (you cannot allocate
-memory in your <code>.rs</code> file). For more information, see <a href="#memory">Working
-with Allocated Memory</a>.
-</p>
 
   <h3 id="struct">Structs</h3>
   <p>Structs are reflected into their own classes, located in
@@ -311,7 +265,8 @@
     specified number of <code>struct</code>s. For example, if you declare the following struct:</p>
 <pre>
 typedef struct Point {
-float2 point;
+    float2 position;
+    float size;
 } Point_t;
 </pre>
 
@@ -478,7 +433,8 @@
       </pre>
 
       <p>If you modify the memory in one memory space and want to push the updates to the rest of
-        the memory spaces, call <code>rsgAllocationSyncAll()</code> in your Renderscript code to
+        the memory spaces, call <a href="{@docRoot}reference/renderscript/rs__graphics_8rsh.html">
+        <code>rsgAllocationSyncAll()</code></a> in your Renderscript code to
         synchronize the memory.</p>
     </li>
 
@@ -511,6 +467,56 @@
 properties that are not yet synchronized.</li>
     </ul>
 
+  <h3 id="pointer">Pointers</h3>
+  <p>Pointers are reflected into the script class itself, located in
+<code>project_root/gen/package/name/ScriptC_renderscript_filename</code>. You
+can declare pointers to a <code>struct</code> or any of the supported Renderscript types, but a
+<code>struct</code> cannot contain pointers or nested arrays. For example, if you declare the
+following pointers to a <code>struct</code> and <code>int32_t</code></p>
+
+<pre>
+typedef struct Point {
+    float2 position;
+    float size;
+} Point_t;
+
+Point_t *touchPoints;
+int32_t *intPointer;
+</pre>
+  <p>then the following code is generated in:</p>
+
+<pre>
+private ScriptField_Point mExportVar_touchPoints;
+public void bind_touchPoints(ScriptField_Point v) {
+    mExportVar_touchPoints = v;
+    if (v == null) bindAllocation(null, mExportVarIdx_touchPoints);
+    else bindAllocation(v.getAllocation(), mExportVarIdx_touchPoints);
+}
+
+public ScriptField_Point get_touchPoints() {
+    return mExportVar_touchPoints;
+}
+
+private Allocation mExportVar_intPointer;
+public void bind_intPointer(Allocation v) {
+    mExportVar_intPointer = v;
+    if (v == null) bindAllocation(null, mExportVarIdx_intPointer);
+    else bindAllocation(v, mExportVarIdx_intPointer);
+}
+
+public Allocation get_intPointer() {
+    return mExportVar_intPointer;
+}
+  </pre>
+
+<p>A <code>get</code> method and a special method named <code>bind_<em>pointer_name</em></code>
+(instead of a <code>set()</code> method) is generated. This method allows you to bind the memory
+that is allocated in the Android VM to the Renderscript runtime (you cannot allocate
+memory in your <code>.rs</code> file). For more information, see <a href="#memory">Working
+with Allocated Memory</a>.
+</p>
+
+
   <h2 id="mem-allocation">Memory Allocation APIs</h2>
 
  <p>Applications that use Renderscript still run in the Android VM. The actual Renderscript code, however, runs natively and
@@ -693,7 +699,8 @@
 that is set from the Android framework is always returned during a call to a <code>get</code>
 method. However, when Android framework code modifies a variable, that change can be communicated to
 the Renderscript runtime automatically or synchronized at a later time. If you need to send data
-from the Renderscript runtime to the Android framework layer, you can use the <code>rsSendToClient()</code> function
+from the Renderscript runtime to the Android framework layer, you can use the
+<a href="{@docRoot}reference/renderscript/rs__core_8rsh.html"><code>rsSendToClient()</code></a> function
 to overcome this limitation.
 </p>
 <p>When working with dynamically allocated memory, any changes at the Renderscript runtime layer are propagated
diff --git a/docs/html/guide/topics/wireless/bluetooth.jd b/docs/html/guide/topics/wireless/bluetooth.jd
index 76da08e..0567799 100644
--- a/docs/html/guide/topics/wireless/bluetooth.jd
+++ b/docs/html/guide/topics/wireless/bluetooth.jd
@@ -249,12 +249,20 @@
 <p>A dialog will appear requesting user permission to enable Bluetooth, as shown
 in Figure 1. If the user responds "Yes," the system will begin to enable Bluetooth
 and focus will return to your application once the process completes (or fails).</p> 
-<p>If enabling Bluetooth succeeds, your Activity will receive the {@link
+
+<p>The {@code REQUEST_ENABLE_BT} constant passed to {@link
+android.app.Activity#startActivityForResult(Intent,int) startActivityForResult()} is a locally
+defined integer (which must be greater than 0), that the system passes back to you in your
+{@link
+android.app.Activity#onActivityResult(int,int,Intent) onActivityResult()} implementation as the
+<code>requestCode</code> parameter.</p>
+
+<p>If enabling Bluetooth succeeds, your activity receives the {@link
 android.app.Activity#RESULT_OK} result code in the {@link
 android.app.Activity#onActivityResult(int,int,Intent) onActivityResult()}
 callback. If Bluetooth was not enabled
-due to an error (or the user responded "No") then the result code will be {@link
-android.app.Activity#RESULT_CANCELED}.</p> 
+due to an error (or the user responded "No") then the result code is {@link
+android.app.Activity#RESULT_CANCELED}.</p>
 </li> 
 </ol> 
  
@@ -431,11 +439,11 @@
  
 <p>A dialog will be displayed, requesting user permission to make the device
 discoverable, as shown in Figure 2. If the user responds "Yes," then the device
-will become discoverable for the specified amount of time. Your Activity will
+will become discoverable for the specified amount of time. Your activity will
 then receive a call to the {@link android.app.Activity#onActivityResult(int,int,Intent)
 onActivityResult())} callback, with the result code equal to the duration that the device
 is discoverable. If the user responded "No" or if an error occurred, the result code will
-be Activity.RESULT_CANCELLED.</p> 
+be {@link android.app.Activity#RESULT_CANCELED}.</p> 
  
 <p class="note"><strong>Note:</strong> If Bluetooth has not been enabled on the device,
 then enabling device discoverability will automatically enable Bluetooth.</p> 
@@ -568,7 +576,7 @@
 </ol> 
  
 <p>The {@link android.bluetooth.BluetoothServerSocket#accept()} call should not
-be executed in the main Activity UI thread because it is a blocking call and
+be executed in the main activity UI thread because it is a blocking call and
 will prevent any other interaction with the application. It usually makes
 sense to do all work with a {@link android.bluetooth.BluetoothServerSocket} or {@link
 android.bluetooth.BluetoothSocket} in a new
@@ -696,7 +704,7 @@
 12 seconds), then it will throw an exception.</p> 
 <p>Because {@link
 android.bluetooth.BluetoothSocket#connect()} is a blocking call, this connection
-procedure should always be performed in a thread separate from the main Activity
+procedure should always be performed in a thread separate from the main activity
 thread.</p> 
 <p class="note">Note: You should always ensure that the device is not performing
 device discovery when you call {@link
@@ -838,7 +846,7 @@
             try {
                 // Read from the InputStream
                 bytes = mmInStream.read(buffer);
-                // Send the obtained bytes to the UI Activity
+                // Send the obtained bytes to the UI activity
                 mHandler.obtainMessage(MESSAGE_READ, bytes, -1, buffer)
                         .sendToTarget();
             } catch (IOException e) {
@@ -847,14 +855,14 @@
         }
     }
  
-    /* Call this from the main Activity to send data to the remote device */
+    /* Call this from the main activity to send data to the remote device */
     public void write(byte[] bytes) {
         try {
             mmOutStream.write(bytes);
         } catch (IOException e) { }
     }
  
-    /* Call this from the main Activity to shutdown the connection */
+    /* Call this from the main activity to shutdown the connection */
     public void cancel() {
         try {
             mmSocket.close();
@@ -866,12 +874,12 @@
 <p>The constructor acquires the necessary streams and once executed, the thread
 will wait for data to come through the InputStream. When {@link
 java.io.InputStream#read(byte[])} returns with
-bytes from the stream, the data is sent to the main Activity using a member
+bytes from the stream, the data is sent to the main activity using a member
 Handler from the parent class. Then it goes back and waits for more bytes from
 the stream.</p> 
  
 <p>Sending outgoing data is as simple as calling the thread's
-<code>write()</code> method from the main Activity and passing in the bytes to
+<code>write()</code> method from the main activity and passing in the bytes to
 be sent. This method then simply calls {@link
 java.io.OutputStream#write(byte[])} to send the data to the remote device.</p> 
  
diff --git a/docs/html/resources/tutorials/notepad/notepad-ex2.jd b/docs/html/resources/tutorials/notepad/notepad-ex2.jd
index ed06778..1334d7a 100644
--- a/docs/html/resources/tutorials/notepad/notepad-ex2.jd
+++ b/docs/html/resources/tutorials/notepad/notepad-ex2.jd
@@ -87,7 +87,7 @@
     menu callback used for the options menu. Here, we add just one line, which will add a menu item
     to delete a note. Call <code>menu.add()</code> like so:
       <pre>
-public void onCreateContextMenu(Menu menu, View v, ContextMenuInfo menuInfo) {
+public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
     super.onCreateContextMenu(menu, v, menuInfo);
     menu.add(0, DELETE_ID, 0, R.string.menu_delete);
 }</pre>
diff --git a/docs/html/resources/tutorials/views/hello-formstuff.jd b/docs/html/resources/tutorials/views/hello-formstuff.jd
index b9f6c16..1ddd1df 100644
--- a/docs/html/resources/tutorials/views/hello-formstuff.jd
+++ b/docs/html/resources/tutorials/views/hello-formstuff.jd
@@ -91,31 +91,30 @@
         android:layout_width="wrap_content"
         android:layout_height="wrap_content"
         android:padding="10dp"
-        android:background="@drawable/android_button" />
+        android:background="@drawable/android_button"
+        android:onClick="onButtonClicked"/>
 </pre>
 	<p>The <code>android:background</code> attribute specifies the drawable resource to use for the
 button background (which, when saved at <code>res/drawable/android.xml</code>, is
 referenced as <code>@drawable/android</code>). This replaces the normal background image
-used for buttons throughout the system. In order for the drawable to change its image based on
-the button state, the image must be applied to the background.</p>
+applied by the system with the drawable created above, which changes its image based on
+the button state.</p>
+    <p>The attribute <code>android:onClick</code> specifies the name of a method in your activity 
+that the system should call when the user clicks the button. You'll create that method next.</p>
 </li>
 
 <li>To make the button do something when pressed, add the following
-code at the end of the {@link android.app.Activity#onCreate(Bundle) onCreate()} method:
+method inside your {@link android.app.Activity} class:
 <pre>
-final Button button = (Button) findViewById(R.id.button);
-button.setOnClickListener(new OnClickListener() {
-    public void onClick(View v) {
-        // Perform action on clicks
-        Toast.makeText(HelloFormStuff.this, "Beep Bop", Toast.LENGTH_SHORT).show();
-    }
-});
+public void onButtonClicked(View v) {
+    // Do something when the button is clicked
+    Toast.makeText(HelloFormStuff.this, "Button clicked", Toast.LENGTH_SHORT).show();
+}
 </pre>
-<p>This captures the {@link android.widget.Button} from the layout, then adds an {@link
-android.view.View.OnClickListener}. The {@link android.view.View.OnClickListener}
-must implement the {@link android.view.View.OnClickListener#onClick(View)} callback method, which
-defines the action to be made when the button is clicked. In this example, a
-{@link android.widget.Toast} message will be displayed.</p>
+<p>When you specify this kind of method, which is used in your layout file with the {@code
+android:onClick} attribute, the method must be <code>public</code>, have a <code>void</code> return
+value, and accept a single {@code android.view.View} parameter. When the system calls this method,
+it passes the {@code android.view.View} that was clicked.</p>
 </li>
 <li>Now run the application.</li>
 </ol>
@@ -183,34 +182,33 @@
     &lt;CheckBox android:id="@+id/checkbox"
         android:layout_width="wrap_content"
         android:layout_height="wrap_content"
-        android:text="check it out" />
+        android:text="check it out"
+        android:onClick="onCheckboxClicked"/>
 </pre>
+    <p>The attribute <code>android:onClick</code> specifies the name of a method in your activity 
+that the system should call when the user clicks the check box. You'll create that method next.</p>
 </li>
-<li>To do something when the state is changed, add the following code
-to the end of the {@link android.app.Activity#onCreate(Bundle) onCreate()} method:
+<li>To do something when the state is changed, add the following method inside your {@link
+android.app.Activity} class:</p>
+
 <pre>
-final CheckBox checkbox = (CheckBox) findViewById(R.id.checkbox);
-checkbox.setOnClickListener(new OnClickListener() {
-    public void onClick(View v) {
-        // Perform action on clicks, depending on whether it's now checked
-        if (((CheckBox) v).isChecked()) {
-            Toast.makeText(HelloFormStuff.this, "Selected", Toast.LENGTH_SHORT).show();
-        } else {
-            Toast.makeText(HelloFormStuff.this, "Not selected", Toast.LENGTH_SHORT).show();
-        }
+public void onCheckboxClicked(View v) {
+    // Perform action on clicks, depending on whether it's now checked
+    if (((CheckBox) v).isChecked()) {
+        Toast.makeText(HelloFormStuff.this, "Selected", Toast.LENGTH_SHORT).show();
+    } else {
+        Toast.makeText(HelloFormStuff.this, "Not selected", Toast.LENGTH_SHORT).show();
     }
-});
+}
 </pre>
-<p>This captures the {@link android.widget.CheckBox} element from the layout, then adds an {@link
-android.view.View.OnClickListener}. The {@link android.view.View.OnClickListener} must implement the
-{@link android.view.View.OnClickListener#onClick(View)} callback method, which
-defines the action to be made when the checkbox is clicked. When clicked, {@link
-android.widget.CompoundButton#isChecked()} is called to check the new state of the check box. If it
-has been checked, then a {@link android.widget.Toast} displays the message "Selected", otherwise it
-displays "Not selected". Note that the {@link android.view.View} object that is passed in the {@link
-android.view.View.OnClickListener#onClick(View)} callback must be cast to a {@link
-android.widget.CheckBox} because the {@link android.widget.CompoundButton#isChecked()} method is
-not defined by the parent {@link android.view.View} class. The {@link android.widget.CheckBox}
+
+<p>When you specify this kind of method, which is used in your layout file with the {@code
+android:onClick}
+attribute, the method must be <code>public</code>, have a <code>void</code> return value, and
+accept a single {@code android.view.View} parameter. When the system calls this method, it
+passes the {@code android.view.View} that was clicked. In this example, the {@code
+android.view.View} is cast to a {@link android.widget.CheckBox} to determine whether the widget
+has been checked or unchecked. The {@link android.widget.CheckBox} widget
 handles its own state changes, so you only need to query the current state.</p>
 </li>
 <li>Run it.</li>
@@ -240,44 +238,44 @@
       &lt;RadioButton android:id="@+id/radio_red"
           android:layout_width="wrap_content"
           android:layout_height="wrap_content"
-          android:text="Red" />
+          android:text="Red"
+          android:onClick="onRadioButtonClicked"/>
       &lt;RadioButton android:id="@+id/radio_blue"
           android:layout_width="wrap_content"
           android:layout_height="wrap_content"
-          android:text="Blue" />
+          android:text="Blue"
+          android:onClick="onRadioButtonClicked"/>
     &lt;/RadioGroup>
 </pre>
 <p>It's important that the {@link android.widget.RadioButton}s are grouped together by the {@link
 android.widget.RadioGroup} element so that no more than one can be selected at a time. This logic
 is automatically handled by the Android system. When one {@link android.widget.RadioButton} within
 a group is selected, all others are automatically deselected.</p>
+    <p>The attribute <code>android:onClick</code> specifies the name of a method in your activity 
+that the system should call when the user clicks the radio button. You'll create that method
+next.</p>
 </li>
 
-<li>To do something when each {@link android.widget.RadioButton} is selected, you need an
-{@link android.view.View.OnClickListener}. In this case, you want the listener to be re-usable, so
-add the following code to create a new member in the <code>HelloFormStuff</code> Activity:
+<li>To do something when each {@link android.widget.RadioButton} is selected, add the following
+method inside your {@link android.app.Activity} class:</p>
+
 <pre>
-private OnClickListener radio_listener = new OnClickListener() {
-    public void onClick(View v) {
-        // Perform action on clicks
-        RadioButton rb = (RadioButton) v;
-        Toast.makeText(HelloFormStuff.this, rb.getText(), Toast.LENGTH_SHORT).show();
-    }
-};
+public void onRadioButtonClicked(View v) {
+    // Perform action on clicks
+    RadioButton rb = (RadioButton) v;
+    Toast.makeText(HelloFormStuff.this, rb.getText(), Toast.LENGTH_SHORT).show();
+}
 </pre>
-<p>First, the {@link android.view.View} that is passed to the {@link
-android.view.View.OnClickListener#onClick(View)} method is cast into a RadioButton. Then a
-{@link android.widget.Toast} message displays the selected radio button's text.</p>
-<li>Now, at the bottom of the {@link android.app.Activity#onCreate(Bundle) onCreate()} method, add
-the following:
-<pre>
-  final RadioButton radio_red = (RadioButton) findViewById(R.id.radio_red);
-  final RadioButton radio_blue = (RadioButton) findViewById(R.id.radio_blue);
-  radio_red.setOnClickListener(radio_listener);
-  radio_blue.setOnClickListener(radio_listener);
-</pre>
-<p>This captures each of the {@link android.widget.RadioButton}s from the layout and adds the
-newly-created {@link android.view.View.OnClickListener} to each.</p>
+
+<p>When you specify this kind of method, which is used in your layout file with the {@code
+android:onClick}
+attribute, the method must be <code>public</code>, have a <code>void</code> return value, and
+accept a single {@code android.view.View} parameter. When the system calls this method, it
+passes the {@code android.view.View} that was clicked.</p>
+<p>Because each {@link android.widget.RadioButton} widget is grouped into a {@link
+android.widget.RadioGroup}, each widget handles its own state changes when a new button is
+selected.</p>
+</li>
 <li>Run the application.</li>
 </ol>
 
@@ -303,31 +301,35 @@
         android:layout_width="wrap_content"
         android:layout_height="wrap_content"
         android:textOn="Vibrate on"
-        android:textOff="Vibrate off"/>
+        android:textOff="Vibrate off"
+        android:onClick="onToggleClicked"/>
 </pre>
   <p>The attributes <code>android:textOn</code> and <code>android:textOff</code> specify the text
 for the button when the button has been toggled on or off. The default values are "ON" and
 "OFF".</p>
+    <p>The attribute <code>android:onClick</code> specifies the name of a method in your activity 
+that the system should call when the user clicks the button. You'll create that method next.</p>
 </li>
-<li>To do something when the state is changed, add the following code
-to the end of the {@link android.app.Activity#onCreate(Bundle) onCreate()} method:
+<li>To do something when the user clicks the button, add the following
+method inside your {@link android.app.Activity} class:</p>
+
 <pre>
-final ToggleButton togglebutton = (ToggleButton) findViewById(R.id.togglebutton);
-togglebutton.setOnClickListener(new OnClickListener() {
-    public void onClick(View v) {
-        // Perform action on clicks
-        if (togglebutton.isChecked()) {
-            Toast.makeText(HelloFormStuff.this, "Checked", Toast.LENGTH_SHORT).show();
-        } else {
-            Toast.makeText(HelloFormStuff.this, "Not checked", Toast.LENGTH_SHORT).show();
-        }
+public void onToggleClicked(View v) {
+    // Perform action on clicks
+    if (((ToggleButton) v).isChecked()) {
+        Toast.makeText(HelloFormStuff.this, "Toggle on", Toast.LENGTH_SHORT).show();
+    } else {
+        Toast.makeText(HelloFormStuff.this, "Toggle off", Toast.LENGTH_SHORT).show();
     }
-});
+}
 </pre>
-<p>This captures the {@link android.widget.ToggleButton} element from the layout, then adds an
-{@link android.view.View.OnClickListener}. The {@link android.view.View.OnClickListener} must
-implement the {@link android.view.View.OnClickListener#onClick(View)} callback method, which
-defines the action to perform when the button is clicked. In this example, the callback
+
+<p>When you specify this kind of method, which is used in your layout file with the {@code
+android:onClick}
+attribute, the method must be <code>public</code>, have a <code>void</code> return value, and
+accept a single {@code android.view.View} parameter. When the system calls this method, it
+passes the {@code android.view.View} that was clicked.</p>
+<p>In this example, the callback
 method checks the new state of the button, then shows a {@link android.widget.Toast} message that
 indicates the current state.</p>
 
diff --git a/docs/html/resources/tutorials/views/hello-mapview.jd b/docs/html/resources/tutorials/views/hello-mapview.jd
index ac5e826..7a0bedf 100644
--- a/docs/html/resources/tutorials/views/hello-mapview.jd
+++ b/docs/html/resources/tutorials/views/hello-mapview.jd
@@ -208,7 +208,7 @@
   new class constructor:
 <pre>
 public HelloItemizedOverlay(Drawable defaultMarker, Context context) {
-  super(defaultMarker);
+  super(boundCenterBottom(defaultMarker));
   mContext = context;
 }
 </pre>
diff --git a/docs/html/sitemap.txt b/docs/html/sitemap.txt
index cfbda2b..958fe56 100644
--- a/docs/html/sitemap.txt
+++ b/docs/html/sitemap.txt
@@ -108,7 +108,7 @@
 http://developer.android.com/guide/topics/testing/contentprovider_testing.html
 http://developer.android.com/guide/topics/testing/service_testing.html
 http://developer.android.com/guide/topics/testing/what_to_test.html
-http://developer.android.com/guide/publishing/licensing.html
+http://developer.android.com/guide/market/licensing/index.html
 http://developer.android.com/guide/market/billing/index.html
 http://developer.android.com/guide/market/billing/billing_about.html
 http://developer.android.com/guide/market/billing/billing_overview.html
diff --git a/drm/java/android/drm/DrmConvertedStatus.java b/drm/java/android/drm/DrmConvertedStatus.java
index cecb135..f6e570a 100755
--- a/drm/java/android/drm/DrmConvertedStatus.java
+++ b/drm/java/android/drm/DrmConvertedStatus.java
@@ -18,36 +18,67 @@
 
 /**
  * An entity class that wraps converted data, conversion status, and the
- * offset for appending the header and body signature to the converted data. An instance of this
- * class is returned by the {@link DrmManagerClient#convertData convertData()} and
- * {@link DrmManagerClient#closeConvertSession closeConvertSession()} methods. The offset is provided only when a
- * conversion session is closed by calling {@link DrmManagerClient#closeConvertSession closeConvertSession()}.
+ * offset for appending the header and body signature to the converted data.
+ * An instance of this class may be created two ways by the drm framework:
+ * a) a call to {@link DrmManagerClient#convertData DrmManagerClient.convertData()} and
+ * b) a call to {@link DrmManagerClient#closeConvertSession DrmManagerClient.closeConvertSession()}.
+ * An valid offset value is provided only from a success call to
+ * {@link DrmManagerClient#closeConvertSession DrmManagerClient.closeConvertSession()}.
  *
  */
 public class DrmConvertedStatus {
-    // Should be in sync with DrmConvertedStatus.cpp
+    // The following status code constants must be in sync with
+    // DrmConvertedStatus.cpp. Please also update isValidStatusCode()
+    // when more status code constants are added.
+    /**
+     * Indicate the conversion status is successful.
+     */
     public static final int STATUS_OK = 1;
+    /**
+     * Indicate a failed conversion status due to input data.
+     */
     public static final int STATUS_INPUTDATA_ERROR = 2;
+    /**
+     * Indicate a general failed conversion status.
+     */
     public static final int STATUS_ERROR = 3;
 
-    /** Status code for the conversion.*/
+    /**
+     * Status code for the conversion. Must be one of the defined status
+     * constants above.
+     */
     public final int statusCode;
-    /** Converted data.*/
+    /**
+     * Converted data. It is optional and thus can be null.
+     */
     public final byte[] convertedData;
-    /** Offset value for the body and header signature.*/
+    /**
+     * Offset value for the body and header signature.
+     */
     public final int offset;
 
     /**
      * Creates a <code>DrmConvertedStatus</code> object with the specified parameters.
      *
-     * @param _statusCode Conversion status.
-     * @param _convertedData Converted data.
-     * @param _offset Offset value for appending the header and body signature.
+     * @param statusCode Conversion status. Must be one of the status code constants
+     * defined above.
+     * @param convertedData Converted data. It can be null.
+     * @param offset Offset value for appending the header and body signature.
      */
-    public DrmConvertedStatus(int _statusCode, byte[] _convertedData, int _offset) {
-        statusCode = _statusCode;
-        convertedData = _convertedData;
-        offset = _offset;
+    public DrmConvertedStatus(int statusCode, byte[] convertedData, int offset) {
+        if (!isValidStatusCode(statusCode)) {
+            throw new IllegalArgumentException("Unsupported status code: " + statusCode);
+        }
+
+        this.statusCode = statusCode;
+        this.convertedData = convertedData;
+        this.offset = offset;
+    }
+
+    private boolean isValidStatusCode(int statusCode) {
+        return statusCode == STATUS_OK ||
+               statusCode == STATUS_INPUTDATA_ERROR ||
+               statusCode == STATUS_ERROR;
     }
 }
 
diff --git a/drm/java/android/drm/DrmInfoStatus.java b/drm/java/android/drm/DrmInfoStatus.java
index 2fe0a78..9a3a7df 100755
--- a/drm/java/android/drm/DrmInfoStatus.java
+++ b/drm/java/android/drm/DrmInfoStatus.java
@@ -17,53 +17,81 @@
 package android.drm;
 
 /**
- * An entity class that wraps the result of communication between a device and an online DRM
- * server. Specifically, when the {@link DrmManagerClient#processDrmInfo processDrmInfo()} method
- * is called, an instance of <code>DrmInfoStatus</code> is returned.
+ * An entity class that wraps the result of communication between a device
+ * and an online DRM server. Specifically, when the
+ * {@link DrmManagerClient#processDrmInfo DrmManagerClient.processDrmInfo()}
+ * method is called, an instance of <code>DrmInfoStatus</code> is returned.
  *<p>
- * This class contains the {@link ProcessedData} object, which can be used to instantiate a
- * {@link DrmRights} object during license acquisition.
+ * This class contains the {@link ProcessedData} object, which can be used
+ * to instantiate a {@link DrmRights} object during license acquisition.
  *
  */
 public class DrmInfoStatus {
-    // Should be in sync with DrmInfoStatus.cpp
+    // The following status code constants must be in sync with DrmInfoStatus.cpp
+    // Please update isValidStatusCode() if more status codes are added.
+    /**
+     * Indicate successful communication.
+     */
     public static final int STATUS_OK = 1;
+
+    /**
+     * Indicate failed communication.
+     */
     public static final int STATUS_ERROR = 2;
 
     /**
-     * The status of the communication.
+     * The status of the communication. Must be one of the defined status
+     * constants above.
      */
     public final int statusCode;
     /**
-     * The type of DRM information processed.
+     * The type of DRM information processed. Must be one of the valid type
+     * constants defined in {@link DrmInfoRequest}.
      */
     public final int infoType;
     /**
-     * The MIME type of the content.
+     * The MIME type of the content. Must not be null or an empty string.
      */
     public final String mimeType;
     /**
-     * The processed data.
+     * The processed data. It is optional and thus could be null. When it
+     * is null, it indicates that a particular call to
+     * {@link DrmManagerClient#processDrmInfo DrmManagerClient.processDrmInfo()}
+     * does not return any additional useful information except for the status code.
      */
     public final ProcessedData data;
 
     /**
      * Creates a <code>DrmInfoStatus</code> object with the specified parameters.
      *
-     * @param _statusCode The status of the communication.
-     * @param _infoType The type of the DRM information processed.
-     * @param _data The processed data.
-     * @param _mimeType The MIME type.
+     * @param statusCode The status of the communication. Must be one of the defined
+     * status constants above.
+     * @param infoType The type of the DRM information processed. Must be a valid
+     * type for {@link DrmInfoRequest}.
+     * @param data The processed data.
+     * @param mimeType The MIME type.
      */
-    public DrmInfoStatus(int _statusCode, int _infoType, ProcessedData _data, String _mimeType) {
-        if (!DrmInfoRequest.isValidType(_infoType)) {
-            throw new IllegalArgumentException("infoType: " + _infoType);
+    public DrmInfoStatus(int statusCode, int infoType, ProcessedData data, String mimeType) {
+        if (!DrmInfoRequest.isValidType(infoType)) {
+            throw new IllegalArgumentException("infoType: " + infoType);
         }
 
-        statusCode = _statusCode;
-        infoType = _infoType;
-        data = _data;
-        mimeType = _mimeType;
+        if (!isValidStatusCode(statusCode)) {
+            throw new IllegalArgumentException("Unsupported status code: " + statusCode);
+        }
+
+        if (mimeType == null || mimeType == "") {
+            throw new IllegalArgumentException("mimeType is null or an empty string");
+        }
+
+        this.statusCode = statusCode;
+        this.infoType = infoType;
+        this.data = data;
+        this.mimeType = mimeType;
+    }
+
+    private boolean isValidStatusCode(int statusCode) {
+        return statusCode == STATUS_OK || statusCode == STATUS_ERROR;
     }
 }
 
diff --git a/drm/java/android/drm/DrmManagerClient.java b/drm/java/android/drm/DrmManagerClient.java
index 14d5fae..482ab0a 100755
--- a/drm/java/android/drm/DrmManagerClient.java
+++ b/drm/java/android/drm/DrmManagerClient.java
@@ -49,6 +49,8 @@
      */
     public static final int ERROR_UNKNOWN = -2000;
 
+    HandlerThread mInfoThread;
+    HandlerThread mEventThread;
     private static final String TAG = "DrmManagerClient";
 
     static {
@@ -105,6 +107,7 @@
 
     private int mUniqueId;
     private int mNativeContext;
+    private boolean mReleased;
     private Context mContext;
     private InfoHandler mInfoHandler;
     private EventHandler mEventHandler;
@@ -238,32 +241,73 @@
      */
     public DrmManagerClient(Context context) {
         mContext = context;
-
-        HandlerThread infoThread = new HandlerThread("DrmManagerClient.InfoHandler");
-        infoThread.start();
-        mInfoHandler = new InfoHandler(infoThread.getLooper());
-
-        HandlerThread eventThread = new HandlerThread("DrmManagerClient.EventHandler");
-        eventThread.start();
-        mEventHandler = new EventHandler(eventThread.getLooper());
+        mReleased = false;
 
         // save the unique id
-        mUniqueId = _initialize(new WeakReference<DrmManagerClient>(this));
+        mUniqueId = _initialize();
     }
 
     protected void finalize() {
-        _finalize(mUniqueId);
+        if (!mReleased) {
+            Log.w(TAG, "You should have called release()");
+            release();
+        }
     }
 
     /**
+     * Releases resources associated with the current session of DrmManagerClient.
+     *
+     * It is considered good practice to call this method when the {@link DrmManagerClient} object
+     * is no longer needed in your application. After release() is called,
+     * {@link DrmManagerClient} is no longer usable since it has lost all of its required resource.
+     */
+    public void release() {
+        if (mReleased) {
+            Log.w(TAG, "You have already called release()");
+            return;
+        }
+        mReleased = true;
+        if (mEventHandler != null) {
+            mEventThread.quit();
+            mEventThread = null;
+        }
+        if (mInfoHandler != null) {
+            mInfoThread.quit();
+            mInfoThread = null;
+        }
+        mEventHandler = null;
+        mInfoHandler = null;
+        mOnEventListener = null;
+        mOnInfoListener = null;
+        mOnErrorListener = null;
+        _release(mUniqueId);
+    }
+
+
+    private void createListeners() {
+        if (mEventHandler == null && mInfoHandler == null) {
+            mInfoThread = new HandlerThread("DrmManagerClient.InfoHandler");
+            mInfoThread.start();
+            mInfoHandler = new InfoHandler(mInfoThread.getLooper());
+
+            mEventThread = new HandlerThread("DrmManagerClient.EventHandler");
+            mEventThread.start();
+            mEventHandler = new EventHandler(mEventThread.getLooper());
+            _setListeners(mUniqueId, new WeakReference<DrmManagerClient>(this));
+        }
+    }
+
+
+    /**
      * Registers an {@link DrmManagerClient.OnInfoListener} callback, which is invoked when the 
      * DRM framework sends status or warning information during registration or rights acquisition.
      *
      * @param infoListener Interface definition for the callback.
      */
     public synchronized void setOnInfoListener(OnInfoListener infoListener) {
+        mOnInfoListener = infoListener;
         if (null != infoListener) {
-            mOnInfoListener = infoListener;
+            createListeners();
         }
     }
 
@@ -274,8 +318,9 @@
      * @param eventListener Interface definition for the callback.
      */
     public synchronized void setOnEventListener(OnEventListener eventListener) {
+        mOnEventListener = eventListener;
         if (null != eventListener) {
-            mOnEventListener = eventListener;
+            createListeners();
         }
     }
 
@@ -286,8 +331,9 @@
      * @param errorListener Interface definition for the callback.
      */
     public synchronized void setOnErrorListener(OnErrorListener errorListener) {
+        mOnErrorListener = errorListener;
         if (null != errorListener) {
-            mOnErrorListener = errorListener;
+            createListeners();
         }
     }
 
@@ -793,9 +839,11 @@
     }
 
     // private native interfaces
-    private native int _initialize(Object weak_this);
+    private native int _initialize();
 
-    private native void _finalize(int uniqueId);
+    private native void _setListeners(int uniqueId, Object weak_this);
+
+    private native void _release(int uniqueId);
 
     private native void _installDrmEngine(int uniqueId, String engineFilepath);
 
diff --git a/drm/java/android/drm/DrmSupportInfo.java b/drm/java/android/drm/DrmSupportInfo.java
index 6484fa7..3694ff4 100755
--- a/drm/java/android/drm/DrmSupportInfo.java
+++ b/drm/java/android/drm/DrmSupportInfo.java
@@ -36,8 +36,16 @@
      * Adds the specified MIME type to the list of MIME types this DRM plug-in supports.
      *
      * @param mimeType MIME type that can be handles by this DRM plug-in.
+     * Must not be null or an empty string.
      */
     public void addMimeType(String mimeType) {
+        if (mimeType == null) {
+            throw new IllegalArgumentException("mimeType is null");
+        }
+        if (mimeType == "") {
+            throw new IllegalArgumentException("mimeType is an empty string");
+        }
+
         mMimeTypeList.add(mimeType);
     }
 
@@ -45,8 +53,14 @@
      * Adds the specified file suffix to the list of file suffixes this DRM plug-in supports.
      *
      * @param fileSuffix File suffix that can be handled by this DRM plug-in.
+     * it could be null but not an empty string. When it is null, it indicates
+     * that some DRM content comes with no file suffix.
      */
     public void addFileSuffix(String fileSuffix) {
+        if (fileSuffix == "") {
+            throw new IllegalArgumentException("fileSuffix is an empty string");
+        }
+
         mFileSuffixList.add(fileSuffix);
     }
 
@@ -73,12 +87,18 @@
     /**
      * Sets a description for the DRM plug-in (agent).
      *
-     * @param description Unique description of plug-in.
+     * @param description Unique description of plug-in. Must not be null
+     * or an empty string.
      */
     public void setDescription(String description) {
-        if (null != description) {
-            mDescription = description;
+        if (description == null) {
+            throw new IllegalArgumentException("description is null");
         }
+        if (description == "") {
+            throw new IllegalArgumentException("description is an empty string");
+        }
+
+        mDescription = description;
     }
 
     /**
@@ -93,7 +113,10 @@
     }
 
     /**
-     * Retrieves the DRM plug-in (agent) description.
+     * Retrieves the DRM plug-in (agent) description. Even if null or an empty
+     * string is not allowed in {@link #setDescription(String)}, if
+     * {@link #setDescription(String)} is not called, description returned
+     * from this method is an empty string.
      *
      * @return The plug-in description.
      */
@@ -111,20 +134,21 @@
     }
 
     /**
-     * Overridden <code>equals</code> implementation.
+     * Overridden <code>equals</code> implementation. Two DrmSupportInfo objects
+     * are considered being equal if they support exactly the same set of mime
+     * types, file suffixes, and has exactly the same description.
      *
      * @param object The object to be compared.
      * @return True if equal; false if not equal.
      */
     public boolean equals(Object object) {
-        boolean result = false;
-
         if (object instanceof DrmSupportInfo) {
-            result = mFileSuffixList.equals(((DrmSupportInfo) object).mFileSuffixList) &&
-                    mMimeTypeList.equals(((DrmSupportInfo) object).mMimeTypeList) &&
-                    mDescription.equals(((DrmSupportInfo) object).mDescription);
+            DrmSupportInfo info = (DrmSupportInfo) object;
+            return mFileSuffixList.equals(info.mFileSuffixList) &&
+                   mMimeTypeList.equals(info.mMimeTypeList) &&
+                   mDescription.equals(info.mDescription);
         }
-        return result;
+        return false;
     }
 
     /**
@@ -132,11 +156,17 @@
      *
      * @param mimeType MIME type.
      * @return True if Mime type is supported; false if MIME type is not supported.
+     * Null or empty string is not a supported mimeType.
      */
     /* package */ boolean isSupportedMimeType(String mimeType) {
         if (null != mimeType && !mimeType.equals("")) {
             for (int i = 0; i < mMimeTypeList.size(); i++) {
                 String completeMimeType = mMimeTypeList.get(i);
+
+                // The reason that equals() is not used is that sometimes,
+                // content distributor might just append something to
+                // the basic MIME type. startsWith() is used to avoid
+                // frequent update of DRM agent.
                 if (completeMimeType.startsWith(mimeType)) {
                     return true;
                 }
diff --git a/drm/jni/android_drm_DrmManagerClient.cpp b/drm/jni/android_drm_DrmManagerClient.cpp
index dfc7fb2..191648c 100644
--- a/drm/jni/android_drm_DrmManagerClient.cpp
+++ b/drm/jni/android_drm_DrmManagerClient.cpp
@@ -57,29 +57,16 @@
 };
 
 String8 Utility::getStringValue(JNIEnv* env, jobject object, const char* fieldName) {
-    String8 dataString("");
-
     /* Look for the instance field with the name fieldName */
     jfieldID fieldID
         = env->GetFieldID(env->GetObjectClass(object), fieldName , "Ljava/lang/String;");
 
     if (NULL != fieldID) {
         jstring valueString = (jstring) env->GetObjectField(object, fieldID);
-
-        if (NULL != valueString && valueString != env->NewStringUTF("")) {
-            char* bytes = const_cast< char* > (env->GetStringUTFChars(valueString, NULL));
-
-            const int length = strlen(bytes) + 1;
-            char *data = new char[length];
-            strncpy(data, bytes, length);
-            dataString = String8(data);
-
-            env->ReleaseStringUTFChars(valueString, bytes);
-            delete [] data; data = NULL;
-        } else {
-            ALOGV("Failed to retrieve the data from the field %s", fieldName);
-        }
+        return Utility::getStringValue(env, valueString);
     }
+
+    String8 dataString("");
     return dataString;
 }
 
@@ -102,24 +89,16 @@
 
 char* Utility::getByteArrayValue(
             JNIEnv* env, jobject object, const char* fieldName, int* dataLength) {
-    char* data = NULL;
+
     *dataLength = 0;
 
     jfieldID fieldID = env->GetFieldID(env->GetObjectClass(object), fieldName , "[B");
 
     if (NULL != fieldID) {
         jbyteArray byteArray = (jbyteArray) env->GetObjectField(object, fieldID);
-        if (NULL != byteArray) {
-            jint length = env->GetArrayLength(byteArray);
-
-            *dataLength = length;
-            if (0 < *dataLength) {
-                data = new char[length];
-                env->GetByteArrayRegion(byteArray, (jint)0, length, (jbyte *) data);
-            }
-        }
+        return Utility::getByteArrayValue(env, byteArray, dataLength);
     }
-    return data;
+    return NULL;
 }
 
 char* Utility::getByteArrayValue(JNIEnv* env, jbyteArray byteArray, int* dataLength) {
@@ -225,25 +204,32 @@
 }
 
 static jint android_drm_DrmManagerClient_initialize(
-        JNIEnv* env, jobject thiz, jobject weak_thiz) {
+        JNIEnv* env, jobject thiz) {
     ALOGV("initialize - Enter");
 
     int uniqueId = 0;
     sp<DrmManagerClientImpl> drmManager = DrmManagerClientImpl::create(&uniqueId, false);
     drmManager->addClient(uniqueId);
 
-    // Set the listener to DrmManager
-    sp<DrmManagerClient::OnInfoListener> listener = new JNIOnInfoListener(env, thiz, weak_thiz);
-    drmManager->setOnInfoListener(uniqueId, listener);
-
     setDrmManagerClientImpl(env, thiz, drmManager);
     ALOGV("initialize - Exit");
-
     return uniqueId;
 }
 
-static void android_drm_DrmManagerClient_finalize(JNIEnv* env, jobject thiz, jint uniqueId) {
-    ALOGV("finalize - Enter");
+static void android_drm_DrmManagerClient_setListeners(
+        JNIEnv* env, jobject thiz, jint uniqueId, jobject weak_thiz) {
+    ALOGV("setListeners - Enter");
+
+    // Set the listener to DrmManager
+    sp<DrmManagerClient::OnInfoListener> listener = new JNIOnInfoListener(env, thiz, weak_thiz);
+    getDrmManagerClientImpl(env, thiz)->setOnInfoListener(uniqueId, listener);
+
+    ALOGV("setListeners - Exit");
+}
+
+static void android_drm_DrmManagerClient_release(
+        JNIEnv* env, jobject thiz, jint uniqueId) {
+    ALOGV("release - Enter");
     DrmManagerClientImpl::remove(uniqueId);
     getDrmManagerClientImpl(env, thiz)->setOnInfoListener(uniqueId, NULL);
 
@@ -252,7 +238,7 @@
         oldClient->setOnInfoListener(uniqueId, NULL);
         oldClient->removeClient(uniqueId);
     }
-    ALOGV("finalize - Exit");
+    ALOGV("release - Exit");
 }
 
 static jobject android_drm_DrmManagerClient_getConstraintsFromContent(
@@ -412,7 +398,7 @@
                                 Utility::getStringValue(env, contentPath));
     }
 
-    delete mData; mData = NULL;
+    delete[] mData; mData = NULL;
     ALOGV("saveRights - Exit");
     return result;
 }
@@ -503,7 +489,7 @@
                 processedData, env->NewStringUTF(pDrmInfoStatus->mimeType.string()));
     }
 
-    delete mData; mData = NULL;
+    delete[] mData; mData = NULL;
     delete pDrmInfoStatus; pDrmInfoStatus = NULL;
 
     ALOGV("processDrmInfo - Exit");
@@ -668,7 +654,7 @@
                              statusCode, dataArray, pDrmConvertedStatus->offset);
     }
 
-    delete mData; mData = NULL;
+    delete[] mData; mData = NULL;
     delete pDrmConvertedStatus; pDrmConvertedStatus = NULL;
 
     ALOGV("convertData - Exit");
@@ -714,11 +700,14 @@
 
 static JNINativeMethod nativeMethods[] = {
 
-    {"_initialize", "(Ljava/lang/Object;)I",
+    {"_initialize", "()I",
                                     (void*)android_drm_DrmManagerClient_initialize},
 
-    {"_finalize", "(I)V",
-                                    (void*)android_drm_DrmManagerClient_finalize},
+    {"_setListeners", "(ILjava/lang/Object;)V",
+                                    (void*)android_drm_DrmManagerClient_setListeners},
+
+    {"_release", "(I)V",
+                                    (void*)android_drm_DrmManagerClient_release},
 
     {"_getConstraints", "(ILjava/lang/String;I)Landroid/content/ContentValues;",
                                     (void*)android_drm_DrmManagerClient_getConstraintsFromContent},
diff --git a/graphics/java/android/graphics/drawable/AnimationDrawable.java b/graphics/java/android/graphics/drawable/AnimationDrawable.java
index 4ad5b9f..7c7cd01 100644
--- a/graphics/java/android/graphics/drawable/AnimationDrawable.java
+++ b/graphics/java/android/graphics/drawable/AnimationDrawable.java
@@ -102,7 +102,12 @@
 
     /**
      * <p>Starts the animation, looping if necessary. This method has no effect
-     * if the animation is running.</p>
+     * if the animation is running. Do not call this in the {@link android.app.Activity#onCreate}
+     * method of your activity, because the {@link android.graphics.drawable.AnimationDrawable} is
+     * not yet fully attached to the window. If you want to play
+     * the animation immediately, without requiring interaction, then you might want to call it
+     * from the {@link android.app.Activity#onWindowFocusChanged} method in your activity,
+     * which will get called when Android brings your window into focus.</p>
      *
      * @see #isRunning()
      * @see #stop()
diff --git a/graphics/java/android/renderscript/Mesh.java b/graphics/java/android/renderscript/Mesh.java
index b6ca58c..f641117 100644
--- a/graphics/java/android/renderscript/Mesh.java
+++ b/graphics/java/android/renderscript/Mesh.java
@@ -636,7 +636,7 @@
         }
 
         /**
-        * Sets the texture coordinate for the last added vertex
+        * Sets the texture coordinate for the vertices that are added after this method call.
         *
         * @param s texture coordinate s
         * @param t texture coordinate t
@@ -653,7 +653,7 @@
         }
 
         /**
-        * Sets the normal vector for the last added vertex
+        * Sets the normal vector for the vertices that are added after this method call.
         *
         * @param x normal vector x
         * @param y normal vector y
@@ -672,7 +672,7 @@
         }
 
         /**
-        * Sets the color for the last added vertex
+        * Sets the color for the vertices that are added after this method call.
         *
         * @param r red component
         * @param g green component
diff --git a/include/media/AudioRecord.h b/include/media/AudioRecord.h
index b0c581a..4fbeb38 100644
--- a/include/media/AudioRecord.h
+++ b/include/media/AudioRecord.h
@@ -299,7 +299,7 @@
 
     /* obtains a buffer of "frameCount" frames. The buffer must be
      * filled entirely. If the track is stopped, obtainBuffer() returns
-     * STOPPED instead of NO_ERROR as long as there are buffers availlable,
+     * STOPPED instead of NO_ERROR as long as there are buffers available,
      * at which point NO_MORE_BUFFERS is returned.
      * Buffers will be returned until the pool (buffercount())
      * is exhausted, at which point obtainBuffer() will either block
@@ -317,13 +317,14 @@
 
 
     /* As a convenience we provide a read() interface to the audio buffer.
-     * This is implemented on top of lockBuffer/unlockBuffer.
+     * This is implemented on top of obtainBuffer/releaseBuffer.
      */
             ssize_t     read(void* buffer, size_t size);
 
-    /* Return the amount of input frames lost in the audio driver since the last call of this function.
-     * Audio driver is expected to reset the value to 0 and restart counting upon returning the current value by this function call.
-     * Such loss typically occurs when the user space process is blocked longer than the capacity of audio driver buffers.
+    /* Return the amount of input frames lost in the audio driver since the last call of this
+     * function.  Audio driver is expected to reset the value to 0 and restart counting upon
+     * returning the current value by this function call.  Such loss typically occurs when the
+     * user space process is blocked longer than the capacity of audio driver buffers.
      * Unit: the number of input audio frames
      */
             unsigned int  getInputFramesLost() const;
diff --git a/include/media/IMediaPlayer.h b/include/media/IMediaPlayer.h
index 6425886..39d58ab 100644
--- a/include/media/IMediaPlayer.h
+++ b/include/media/IMediaPlayer.h
@@ -23,6 +23,10 @@
 #include <utils/KeyedVector.h>
 #include <system/audio.h>
 
+// Fwd decl to make sure everyone agrees that the scope of struct sockaddr_in is
+// global, and not in android::
+struct sockaddr_in;
+
 namespace android {
 
 class Parcel;
@@ -59,6 +63,7 @@
     virtual status_t        attachAuxEffect(int effectId) = 0;
     virtual status_t        setParameter(int key, const Parcel& request) = 0;
     virtual status_t        getParameter(int key, Parcel* reply) = 0;
+    virtual status_t        setRetransmitEndpoint(const struct sockaddr_in* endpoint) = 0;
 
     // Invoke a generic method on the player by using opaque parcels
     // for the request and reply.
diff --git a/include/media/MediaPlayerInterface.h b/include/media/MediaPlayerInterface.h
index 23a3e49..f7491d8 100644
--- a/include/media/MediaPlayerInterface.h
+++ b/include/media/MediaPlayerInterface.h
@@ -29,6 +29,10 @@
 #include <media/AudioSystem.h>
 #include <media/Metadata.h>
 
+// Fwd decl to make sure everyone agrees that the scope of struct sockaddr_in is
+// global, and not in android::
+struct sockaddr_in;
+
 namespace android {
 
 class Parcel;
@@ -141,6 +145,14 @@
     virtual status_t    setParameter(int key, const Parcel &request) = 0;
     virtual status_t    getParameter(int key, Parcel *reply) = 0;
 
+    // Right now, only the AAX TX player supports this functionality.  For now,
+    // provide a default implementation which indicates a lack of support for
+    // this functionality to make life easier for all of the other media player
+    // maintainers out there.
+    virtual status_t setRetransmitEndpoint(const struct sockaddr_in* endpoint) {
+        return INVALID_OPERATION;
+    }
+
     // Invoke a generic method on the player by using opaque parcels
     // for the request and reply.
     //
diff --git a/include/media/mediaplayer.h b/include/media/mediaplayer.h
index d0b87c8..9cd5f9f 100644
--- a/include/media/mediaplayer.h
+++ b/include/media/mediaplayer.h
@@ -17,6 +17,8 @@
 #ifndef ANDROID_MEDIAPLAYER_H
 #define ANDROID_MEDIAPLAYER_H
 
+#include <arpa/inet.h>
+
 #include <binder/IMemory.h>
 #include <media/IMediaPlayerClient.h>
 #include <media/IMediaPlayer.h>
@@ -204,6 +206,7 @@
             status_t        attachAuxEffect(int effectId);
             status_t        setParameter(int key, const Parcel& request);
             status_t        getParameter(int key, Parcel* reply);
+            status_t        setRetransmitEndpoint(const char* addrString, uint16_t port);
 
 private:
             void            clear_l();
@@ -212,6 +215,7 @@
             status_t        getDuration_l(int *msec);
             status_t        attachNewPlayer(const sp<IMediaPlayer>& player);
             status_t        reset_l();
+            status_t        doSetRetransmitEndpoint(const sp<IMediaPlayer>& player);
 
     sp<IMediaPlayer>            mPlayer;
     thread_id_t                 mLockThreadId;
@@ -234,6 +238,8 @@
     int                         mVideoHeight;
     int                         mAudioSessionId;
     float                       mSendLevel;
+    struct sockaddr_in          mRetransmitEndpoint;
+    bool                        mRetransmitEndpointValid;
 };
 
 }; // namespace android
diff --git a/include/media/stagefright/ACodec.h b/include/media/stagefright/ACodec.h
index 6735aff..fa1a416 100644
--- a/include/media/stagefright/ACodec.h
+++ b/include/media/stagefright/ACodec.h
@@ -118,6 +118,7 @@
     sp<FlushingState> mFlushingState;
 
     AString mComponentName;
+    uint32_t mQuirks;
     sp<IOMX> mOMX;
     IOMX::node_id mNode;
     sp<MemoryDealer> mDealer[2];
diff --git a/include/media/stagefright/MediaCodecList.h b/include/media/stagefright/MediaCodecList.h
new file mode 100644
index 0000000..14dc1b8
--- /dev/null
+++ b/include/media/stagefright/MediaCodecList.h
@@ -0,0 +1,95 @@
+/*
+ * Copyright 2012, 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.
+ */
+
+#ifndef MEDIA_CODEC_LIST_H_
+
+#define MEDIA_CODEC_LIST_H_
+
+#include <media/stagefright/foundation/ABase.h>
+#include <media/stagefright/foundation/AString.h>
+
+#include <sys/types.h>
+#include <utils/Errors.h>
+#include <utils/KeyedVector.h>
+#include <utils/Vector.h>
+
+namespace android {
+
+struct MediaCodecList {
+    static const MediaCodecList *getInstance();
+
+    ssize_t findCodecByType(
+            const char *type, bool encoder, size_t startIndex = 0) const;
+
+    ssize_t findCodecByName(const char *name) const;
+
+    const char *getCodecName(size_t index) const;
+    bool codecHasQuirk(size_t index, const char *quirkName) const;
+
+private:
+    enum Section {
+        SECTION_TOPLEVEL,
+        SECTION_DECODERS,
+        SECTION_DECODER,
+        SECTION_ENCODERS,
+        SECTION_ENCODER,
+    };
+
+    struct CodecInfo {
+        AString mName;
+        bool mIsEncoder;
+        uint32_t mTypes;
+        uint32_t mQuirks;
+    };
+
+    static MediaCodecList *sCodecList;
+
+    status_t mInitCheck;
+    Section mCurrentSection;
+    int32_t mDepth;
+
+    Vector<CodecInfo> mCodecInfos;
+    KeyedVector<AString, size_t> mCodecQuirks;
+    KeyedVector<AString, size_t> mTypes;
+
+    MediaCodecList();
+    ~MediaCodecList();
+
+    status_t initCheck() const;
+    void parseXMLFile(FILE *file);
+
+    static void StartElementHandlerWrapper(
+            void *me, const char *name, const char **attrs);
+
+    static void EndElementHandlerWrapper(void *me, const char *name);
+
+    void startElementHandler(const char *name, const char **attrs);
+    void endElementHandler(const char *name);
+
+    status_t addMediaCodecFromAttributes(bool encoder, const char **attrs);
+    void addMediaCodec(bool encoder, const char *name, const char *type = NULL);
+
+    status_t addQuirk(const char **attrs);
+    status_t addTypeFromAttributes(const char **attrs);
+    void addType(const char *name);
+
+    DISALLOW_EVIL_CONSTRUCTORS(MediaCodecList);
+};
+
+}  // namespace android
+
+#endif  // MEDIA_CODEC_LIST_H_
+
diff --git a/include/media/stagefright/OMXCodec.h b/include/media/stagefright/OMXCodec.h
index e541c18..392ea87 100644
--- a/include/media/stagefright/OMXCodec.h
+++ b/include/media/stagefright/OMXCodec.h
@@ -26,6 +26,7 @@
 
 namespace android {
 
+struct MediaCodecList;
 class MemoryDealer;
 struct OMXCodecObserver;
 struct CodecProfileLevel;
@@ -82,12 +83,35 @@
     // from MediaBufferObserver
     virtual void signalBufferReturned(MediaBuffer *buffer);
 
+    enum Quirks {
+        kNeedsFlushBeforeDisable              = 1,
+        kWantsNALFragments                    = 2,
+        kRequiresLoadedToIdleAfterAllocation  = 4,
+        kRequiresAllocateBufferOnInputPorts   = 8,
+        kRequiresFlushCompleteEmulation       = 16,
+        kRequiresAllocateBufferOnOutputPorts  = 32,
+        kRequiresFlushBeforeShutdown          = 64,
+        kDefersOutputBufferAllocation         = 128,
+        kDecoderLiesAboutNumberOfChannels     = 256,
+        kInputBufferSizesAreBogus             = 512,
+        kSupportsMultipleFramesPerInputBuffer = 1024,
+        kAvoidMemcopyInputRecordingFrames     = 2048,
+        kRequiresLargerEncoderOutputBuffer    = 4096,
+        kOutputBuffersAreUnreadable           = 8192,
+    };
+
     // for use by ACodec
     static void findMatchingCodecs(
             const char *mime,
             bool createEncoder, const char *matchComponentName,
             uint32_t flags,
-            Vector<String8> *matchingCodecs);
+            Vector<String8> *matchingCodecs,
+            Vector<uint32_t> *matchingCodecQuirks = NULL);
+
+    static uint32_t getComponentQuirks(
+            const MediaCodecList *list, size_t index);
+
+    static bool findCodecQuirks(const char *componentName, uint32_t *quirks);
 
 protected:
     virtual ~OMXCodec();
@@ -125,23 +149,6 @@
         SHUTTING_DOWN,
     };
 
-    enum Quirks {
-        kNeedsFlushBeforeDisable              = 1,
-        kWantsNALFragments                    = 2,
-        kRequiresLoadedToIdleAfterAllocation  = 4,
-        kRequiresAllocateBufferOnInputPorts   = 8,
-        kRequiresFlushCompleteEmulation       = 16,
-        kRequiresAllocateBufferOnOutputPorts  = 32,
-        kRequiresFlushBeforeShutdown          = 64,
-        kDefersOutputBufferAllocation         = 128,
-        kDecoderLiesAboutNumberOfChannels     = 256,
-        kInputBufferSizesAreBogus             = 512,
-        kSupportsMultipleFramesPerInputBuffer = 1024,
-        kAvoidMemcopyInputRecordingFrames     = 2048,
-        kRequiresLargerEncoderOutputBuffer    = 4096,
-        kOutputBuffersAreUnreadable           = 8192,
-    };
-
     enum BufferStatus {
         OWNED_BY_US,
         OWNED_BY_COMPONENT,
@@ -327,9 +334,6 @@
 
     status_t configureCodec(const sp<MetaData> &meta);
 
-    static uint32_t getComponentQuirks(
-            const char *componentName, bool isEncoder);
-
     void restorePatchedDataPointer(BufferInfo *info);
 
     status_t applyRotation();
diff --git a/include/utils/Vector.h b/include/utils/Vector.h
index b908e2a..5b5296b 100644
--- a/include/utils/Vector.h
+++ b/include/utils/Vector.h
@@ -186,8 +186,8 @@
      inline const_iterator end() const   { return array() + size(); }
      inline void reserve(size_t n) { setCapacity(n); }
      inline bool empty() const{ return isEmpty(); }
-     inline void push_back(const TYPE& item)  { insertAt(item, size()); }
-     inline void push_front(const TYPE& item) { insertAt(item, 0); }
+     inline void push_back(const TYPE& item)  { insertAt(item, size(), 1); }
+     inline void push_front(const TYPE& item) { insertAt(item, 0, 1); }
      inline iterator erase(iterator pos) {
          return begin() + removeItemsAt(pos-array());
      }
diff --git a/keystore/java/android/security/KeyChain.java b/keystore/java/android/security/KeyChain.java
index 0fe7bd8..fba5bab 100644
--- a/keystore/java/android/security/KeyChain.java
+++ b/keystore/java/android/security/KeyChain.java
@@ -224,9 +224,6 @@
      * <p>{@code alias} allows the chooser to preselect an existing
      * alias which will still be subject to user confirmation.
      *
-     * <p>This method requires the caller to hold the permission
-     * {@link android.Manifest.permission#USE_CREDENTIALS}.
-     *
      * @param activity The {@link Activity} context to use for
      *     launching the new sub-Activity to prompt the user to select
      *     a private key; used only to call startActivity(); must not
@@ -294,9 +291,6 @@
      * Returns the {@code PrivateKey} for the requested alias, or null
      * if no there is no result.
      *
-     * <p>This method requires the caller to hold the permission
-     * {@link android.Manifest.permission#USE_CREDENTIALS}.
-     *
      * @param alias The alias of the desired private key, typically
      * returned via {@link KeyChainAliasCallback#alias}.
      * @throws KeyChainException if the alias was valid but there was some problem accessing it.
@@ -325,9 +319,6 @@
      * Returns the {@code X509Certificate} chain for the requested
      * alias, or null if no there is no result.
      *
-     * <p>This method requires the caller to hold the permission
-     * {@link android.Manifest.permission#USE_CREDENTIALS}.
-     *
      * @param alias The alias of the desired certificate chain, typically
      * returned via {@link KeyChainAliasCallback#alias}.
      * @throws KeyChainException if the alias was valid but there was some problem accessing it.
diff --git a/libs/gui/BufferQueue.cpp b/libs/gui/BufferQueue.cpp
index d761680..f0641e0 100644
--- a/libs/gui/BufferQueue.cpp
+++ b/libs/gui/BufferQueue.cpp
@@ -828,6 +828,7 @@
         buffer->mTransform = mSlots[buf].mTransform;
         buffer->mScalingMode = mSlots[buf].mScalingMode;
         buffer->mFrameNumber = mSlots[buf].mFrameNumber;
+        buffer->mTimestamp = mSlots[buf].mTimestamp;
         buffer->mBuf = buf;
         mSlots[buf].mAcquireCalled = true;
 
diff --git a/libs/hwui/DisplayListRenderer.cpp b/libs/hwui/DisplayListRenderer.cpp
index 8153823..babfd04 100644
--- a/libs/hwui/DisplayListRenderer.cpp
+++ b/libs/hwui/DisplayListRenderer.cpp
@@ -599,7 +599,6 @@
                 continue;
             } else {
                 op &= ~OP_MAY_BE_SKIPPED_MASK;
-                ALOGD("%s", OP_NAMES[op]);
             }
         }
         logBuffer.writeCommand(level, op);
diff --git a/libs/hwui/DisplayListRenderer.h b/libs/hwui/DisplayListRenderer.h
index 5d1b460..96b87cc 100644
--- a/libs/hwui/DisplayListRenderer.h
+++ b/libs/hwui/DisplayListRenderer.h
@@ -391,8 +391,9 @@
         mHasDrawOps = mHasDrawOps || drawOp >= DisplayList::DrawDisplayList;
         if (reject) {
             mWriter.writeInt(OP_MAY_BE_SKIPPED_MASK | drawOp);
-            mWriter.writeInt(0);
-            uint32_t* location = reject ? mWriter.peek32(mWriter.size() - 4) : NULL;
+            mWriter.writeInt(0xdeaddead);
+            uint32_t* location = reject ?
+                    mWriter.peek32(mWriter.size() - sizeof(int32_t)) : NULL;
             return location;
         }
         mWriter.writeInt(drawOp);
@@ -401,7 +402,8 @@
 
     inline void addSkip(uint32_t* location) {
         if (location) {
-            *location = (int32_t) (mWriter.peek32(mWriter.size() - 4) - location);
+            *location = (int32_t) (mWriter.peek32(
+                    mWriter.size() - sizeof(int32_t)) - location);
         }
     }
 
diff --git a/libs/rs/driver/rsdGL.cpp b/libs/rs/driver/rsdGL.cpp
index 1b12235..63bf7cc 100644
--- a/libs/rs/driver/rsdGL.cpp
+++ b/libs/rs/driver/rsdGL.cpp
@@ -41,6 +41,8 @@
 #include "rsdVertexArray.h"
 #include "rsdFrameBufferObj.h"
 
+#include <gui/SurfaceTextureClient.h>
+
 using namespace android;
 using namespace android::renderscript;
 
@@ -171,15 +173,12 @@
     }
 }
 
-bool rsdGLInit(const Context *rsc) {
-    RsdHal *dc = (RsdHal *)rsc->mHal.drv;
+void getConfigData(const Context *rsc,
+                   EGLint *configAttribs, size_t configAttribsLen,
+                   uint32_t numSamples) {
+    memset(configAttribs, 0, configAttribsLen*sizeof(*configAttribs));
 
-    dc->gl.egl.numConfigs = -1;
-    EGLint configAttribs[128];
     EGLint *configAttribsPtr = configAttribs;
-    EGLint context_attribs2[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE };
-
-    memset(configAttribs, 0, sizeof(configAttribs));
 
     configAttribsPtr[0] = EGL_SURFACE_TYPE;
     configAttribsPtr[1] = EGL_WINDOW_BIT;
@@ -219,8 +218,25 @@
         configAttribsPtr += 2;
     }
 
+    if (numSamples > 1) {
+        configAttribsPtr[0] = EGL_SAMPLE_BUFFERS;
+        configAttribsPtr[1] = 1;
+        configAttribsPtr[2] = EGL_SAMPLES;
+        configAttribsPtr[3] = numSamples;
+        configAttribsPtr += 4;
+    }
+
     configAttribsPtr[0] = EGL_NONE;
-    rsAssert(configAttribsPtr < (configAttribs + (sizeof(configAttribs) / sizeof(EGLint))));
+    rsAssert(configAttribsPtr < (configAttribs + configAttribsLen));
+}
+
+bool rsdGLInit(const Context *rsc) {
+    RsdHal *dc = (RsdHal *)rsc->mHal.drv;
+
+    dc->gl.egl.numConfigs = -1;
+
+    EGLint configAttribs[128];
+    EGLint context_attribs2[] = { EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE };
 
     ALOGV("%p initEGL start", rsc);
     rsc->setWatchdogGL("eglGetDisplay", __LINE__, __FILE__);
@@ -235,8 +251,18 @@
 
     EGLint numConfigs = -1, n = 0;
     rsc->setWatchdogGL("eglChooseConfig", __LINE__, __FILE__);
-    ret = eglChooseConfig(dc->gl.egl.display, configAttribs, 0, 0, &numConfigs);
-    checkEglError("eglGetConfigs", ret);
+
+    // Try minding a multisample config that matches the user request
+    uint32_t minSample = rsc->mUserSurfaceConfig.samplesMin;
+    uint32_t prefSample = rsc->mUserSurfaceConfig.samplesPref;
+    for (uint32_t sampleCount = prefSample; sampleCount >= minSample; sampleCount--) {
+        getConfigData(rsc, configAttribs, (sizeof(configAttribs) / sizeof(EGLint)), sampleCount);
+        ret = eglChooseConfig(dc->gl.egl.display, configAttribs, 0, 0, &numConfigs);
+        checkEglError("eglGetConfigs", ret);
+        if (numConfigs > 0) {
+            break;
+        }
+    }
 
     eglSwapInterval(dc->gl.egl.display, 0);
 
@@ -299,14 +325,15 @@
     }
     gGLContextCount++;
 
+    sp<SurfaceTexture> st(new SurfaceTexture(123));
+    sp<SurfaceTextureClient> stc(new SurfaceTextureClient(st));
+    dc->gl.egl.surfaceDefault = eglCreateWindowSurface(dc->gl.egl.display, dc->gl.egl.config,
+                                                       static_cast<ANativeWindow*>(stc.get()),
+                                                       NULL);
 
-    EGLint pbuffer_attribs[] = { EGL_WIDTH, 1, EGL_HEIGHT, 1, EGL_NONE };
-    rsc->setWatchdogGL("eglCreatePbufferSurface", __LINE__, __FILE__);
-    dc->gl.egl.surfaceDefault = eglCreatePbufferSurface(dc->gl.egl.display, dc->gl.egl.config,
-                                                        pbuffer_attribs);
-    checkEglError("eglCreatePbufferSurface");
+    checkEglError("eglCreateWindowSurface");
     if (dc->gl.egl.surfaceDefault == EGL_NO_SURFACE) {
-        ALOGE("eglCreatePbufferSurface returned EGL_NO_SURFACE");
+        ALOGE("eglCreateWindowSurface returned EGL_NO_SURFACE");
         rsdGLShutdown(rsc);
         rsc->setWatchdogGL(NULL, 0, NULL);
         return false;
diff --git a/libs/ui/GraphicBufferAllocator.cpp b/libs/ui/GraphicBufferAllocator.cpp
index d344737..ff550d9 100644
--- a/libs/ui/GraphicBufferAllocator.cpp
+++ b/libs/ui/GraphicBufferAllocator.cpp
@@ -16,11 +16,13 @@
 */
 
 #define LOG_TAG "GraphicBufferAllocator"
+#define ATRACE_TAG ATRACE_TAG_GRAPHICS
 
 #include <cutils/log.h>
 
 #include <utils/Singleton.h>
 #include <utils/String8.h>
+#include <utils/Trace.h>
 
 #include <ui/GraphicBufferAllocator.h>
 
@@ -91,6 +93,7 @@
 status_t GraphicBufferAllocator::alloc(uint32_t w, uint32_t h, PixelFormat format,
         int usage, buffer_handle_t* handle, int32_t* stride)
 {
+    ATRACE_CALL();
     // make sure to not allocate a N x 0 or 0 x N buffer, since this is
     // allowed from an API stand-point allocate a 1x1 buffer instead.
     if (!w || !h)
@@ -128,6 +131,7 @@
 
 status_t GraphicBufferAllocator::free(buffer_handle_t handle)
 {
+    ATRACE_CALL();
     status_t err;
 
     err = mAllocDev->free(mAllocDev, handle);
diff --git a/libs/ui/GraphicBufferMapper.cpp b/libs/ui/GraphicBufferMapper.cpp
index b173c85..967da98 100644
--- a/libs/ui/GraphicBufferMapper.cpp
+++ b/libs/ui/GraphicBufferMapper.cpp
@@ -15,12 +15,14 @@
  */
 
 #define LOG_TAG "GraphicBufferMapper"
+#define ATRACE_TAG ATRACE_TAG_GRAPHICS
 
 #include <stdint.h>
 #include <errno.h>
 
 #include <utils/Errors.h>
 #include <utils/Log.h>
+#include <utils/Trace.h>
 
 #include <ui/GraphicBufferMapper.h>
 #include <ui/Rect.h>
@@ -46,6 +48,7 @@
 
 status_t GraphicBufferMapper::registerBuffer(buffer_handle_t handle)
 {
+    ATRACE_CALL();
     status_t err;
 
     err = mAllocMod->registerBuffer(mAllocMod, handle);
@@ -57,6 +60,7 @@
 
 status_t GraphicBufferMapper::unregisterBuffer(buffer_handle_t handle)
 {
+    ATRACE_CALL();
     status_t err;
 
     err = mAllocMod->unregisterBuffer(mAllocMod, handle);
@@ -69,6 +73,7 @@
 status_t GraphicBufferMapper::lock(buffer_handle_t handle, 
         int usage, const Rect& bounds, void** vaddr)
 {
+    ATRACE_CALL();
     status_t err;
 
     err = mAllocMod->lock(mAllocMod, handle, usage,
@@ -81,6 +86,7 @@
 
 status_t GraphicBufferMapper::unlock(buffer_handle_t handle)
 {
+    ATRACE_CALL();
     status_t err;
 
     err = mAllocMod->unlock(mAllocMod, handle);
diff --git a/media/java/android/media/MediaPlayer.java b/media/java/android/media/MediaPlayer.java
index 4c70e9d..e663e91 100644
--- a/media/java/android/media/MediaPlayer.java
+++ b/media/java/android/media/MediaPlayer.java
@@ -35,6 +35,7 @@
 
 import java.io.FileDescriptor;
 import java.io.IOException;
+import java.net.InetSocketAddress;
 import java.util.Map;
 import java.util.Set;
 import java.lang.ref.WeakReference;
@@ -1486,6 +1487,52 @@
      */
     public native static int native_pullBatteryData(Parcel reply);
 
+    /**
+     * Sets the target UDP re-transmit endpoint for the low level player.
+     * Generally, the address portion of the endpoint is an IP multicast
+     * address, although a unicast address would be equally valid.  When a valid
+     * retransmit endpoint has been set, the media player will not decode and
+     * render the media presentation locally.  Instead, the player will attempt
+     * to re-multiplex its media data using the Android@Home RTP profile and
+     * re-transmit to the target endpoint.  Receiver devices (which may be
+     * either the same as the transmitting device or different devices) may
+     * instantiate, prepare, and start a receiver player using a setDataSource
+     * URL of the form...
+     *
+     * aahRX://&lt;multicastIP&gt;:&lt;port&gt;
+     *
+     * to receive, decode and render the re-transmitted content.
+     *
+     * setRetransmitEndpoint may only be called before setDataSource has been
+     * called; while the player is in the Idle state.
+     *
+     * @param endpoint the address and UDP port of the re-transmission target or
+     * null if no re-transmission is to be performed.
+     * @throws IllegalStateException if it is called in an invalid state
+     * @throws IllegalArgumentException if the retransmit endpoint is supplied,
+     * but invalid.
+     *
+     * {@hide} pending API council
+     */
+    public void setRetransmitEndpoint(InetSocketAddress endpoint)
+            throws IllegalStateException, IllegalArgumentException
+    {
+        String addrString = null;
+        int port = 0;
+
+        if (null != endpoint) {
+            addrString = endpoint.getAddress().getHostAddress();
+            port = endpoint.getPort();
+        }
+
+        int ret = native_setRetransmitEndpoint(addrString, port);
+        if (ret != 0) {
+            throw new IllegalArgumentException("Illegal re-transmit endpoint; native ret " + ret);
+        }
+    }
+
+    private native final int native_setRetransmitEndpoint(String addrString, int port);
+
     @Override
     protected void finalize() { native_finalize(); }
 
diff --git a/media/jni/android_media_MediaPlayer.cpp b/media/jni/android_media_MediaPlayer.cpp
index f3a5668..6ec5d20 100644
--- a/media/jni/android_media_MediaPlayer.cpp
+++ b/media/jni/android_media_MediaPlayer.cpp
@@ -722,6 +722,45 @@
     return service->pullBatteryData(reply);
 }
 
+static jint
+android_media_MediaPlayer_setRetransmitEndpoint(JNIEnv *env, jobject thiz,
+                                                jstring addrString, jint port) {
+    sp<MediaPlayer> mp = getMediaPlayer(env, thiz);
+    if (mp == NULL ) {
+        jniThrowException(env, "java/lang/IllegalStateException", NULL);
+        return INVALID_OPERATION;
+    }
+
+    const char *cAddrString = NULL;
+
+    if (NULL != addrString) {
+        cAddrString = env->GetStringUTFChars(addrString, NULL);
+        if (cAddrString == NULL) {  // Out of memory
+            return NO_MEMORY;
+        }
+    }
+    ALOGV("setRetransmitEndpoint: %s:%d",
+            cAddrString ? cAddrString : "(null)", port);
+
+    status_t ret;
+    if (cAddrString && (port > 0xFFFF)) {
+        ret = BAD_VALUE;
+    } else {
+        ret = mp->setRetransmitEndpoint(cAddrString,
+                static_cast<uint16_t>(port));
+    }
+
+    if (NULL != addrString) {
+        env->ReleaseStringUTFChars(addrString, cAddrString);
+    }
+
+    if (ret == INVALID_OPERATION ) {
+        jniThrowException(env, "java/lang/IllegalStateException", NULL);
+    }
+
+    return ret;
+}
+
 static jboolean
 android_media_MediaPlayer_setParameter(JNIEnv *env, jobject thiz, jint key, jobject java_request)
 {
@@ -799,6 +838,7 @@
     {"native_pullBatteryData", "(Landroid/os/Parcel;)I",        (void *)android_media_MediaPlayer_pullBatteryData},
     {"setParameter",        "(ILandroid/os/Parcel;)Z",          (void *)android_media_MediaPlayer_setParameter},
     {"getParameter",        "(ILandroid/os/Parcel;)V",          (void *)android_media_MediaPlayer_getParameter},
+    {"native_setRetransmitEndpoint", "(Ljava/lang/String;I)I",  (void *)android_media_MediaPlayer_setRetransmitEndpoint},
 };
 
 static const char* const kClassPathName = "android/media/MediaPlayer";
diff --git a/media/libaah_rtp/aah_decoder_pump.cpp b/media/libaah_rtp/aah_decoder_pump.cpp
index 72fe43b..28b8c7b 100644
--- a/media/libaah_rtp/aah_decoder_pump.cpp
+++ b/media/libaah_rtp/aah_decoder_pump.cpp
@@ -159,8 +159,8 @@
 
                 res = renderer_->queueTimedBuffer(pcm_payload, ts);
                 if (res != OK) {
-                    ALOGE("Failed to queue %d byte audio track buffer with media"
-                          " PTS %lld. (res = %d)", decoded_amt, ts, res);
+                    ALOGE("Failed to queue %d byte audio track buffer with"
+                          " media PTS %lld. (res = %d)", decoded_amt, ts, res);
                 } else {
                     last_queued_pts_valid_ = true;
                     last_queued_pts_ = ts;
@@ -291,8 +291,8 @@
     // thread_status_.
     thread_status_ = decoder_->start(format_.get());
     if (OK != thread_status_) {
-        ALOGE("AAH_DecoderPump's work thread failed to start decoder (res = %d)",
-                thread_status_);
+        ALOGE("AAH_DecoderPump's work thread failed to start decoder"
+              " (res = %d)", thread_status_);
         return NULL;
     }
 
diff --git a/media/libaah_rtp/aah_rx_player.h b/media/libaah_rtp/aah_rx_player.h
index 7a1b6e3..ba5617e 100644
--- a/media/libaah_rtp/aah_rx_player.h
+++ b/media/libaah_rtp/aah_rx_player.h
@@ -217,14 +217,15 @@
         status_t getStatus() const { return status_; }
 
       protected:
-        virtual ~Substream() {
-            shutdown();
-        }
+        virtual ~Substream();
 
       private:
         void                cleanupDecoder();
         bool                shouldAbort(const char* log_tag);
         void                processCompletedBuffer();
+        bool                setupSubstreamMeta();
+        bool                setupMP3SubstreamMeta();
+        bool                setupAACSubstreamMeta();
         bool                setupSubstreamType(uint8_t substream_type,
                                                uint8_t codec_type);
 
@@ -235,12 +236,16 @@
         bool                substream_details_known_;
         uint8_t             substream_type_;
         uint8_t             codec_type_;
+        const char*         codec_mime_type_;
         sp<MetaData>        substream_meta_;
 
         MediaBuffer*        buffer_in_progress_;
         uint32_t            expected_buffer_size_;
         uint32_t            buffer_filled_;
 
+        Vector<uint8_t>     aux_data_in_progress_;
+        uint32_t            aux_data_expected_size_;
+
         sp<AAH_DecoderPump> decoder_;
 
         static int64_t      kAboutToUnderflowThreshold;
diff --git a/media/libaah_rtp/aah_rx_player_core.cpp b/media/libaah_rtp/aah_rx_player_core.cpp
index d2b3386..d6b31fd 100644
--- a/media/libaah_rtp/aah_rx_player_core.cpp
+++ b/media/libaah_rtp/aah_rx_player_core.cpp
@@ -431,8 +431,8 @@
         // Looks like a NAK packet; make sure its long enough.
 
         if (amt < static_cast<ssize_t>(sizeof(RetransRequest))) {
-            ALOGV("Dropping packet, too short to contain NAK payload (%u bytes)",
-                  static_cast<uint32_t>(amt));
+            ALOGV("Dropping packet, too short to contain NAK payload"
+                  " (%u bytes)", static_cast<uint32_t>(amt));
             goto drop_packet;
         }
 
@@ -441,7 +441,8 @@
         gap.start_seq_ = ntohs(rtr->start_seq_);
         gap.end_seq_   = ntohs(rtr->end_seq_);
 
-        ALOGV("Process NAK for gap at [%hu, %hu]", gap.start_seq_, gap.end_seq_);
+        ALOGV("Process NAK for gap at [%hu, %hu]",
+                gap.start_seq_, gap.end_seq_);
         ring_buffer_.processNAK(&gap);
 
         return true;
@@ -770,7 +771,8 @@
             ALOGE("Error when sending retransmit request (%d)", errno);
         } else {
             ALOGV("%s request for range [%hu, %hu] sent",
-                  (kGS_FastStartGap == gap_status) ? "Fast Start" : "Retransmit",
+                  (kGS_FastStartGap == gap_status) ? "Fast Start"
+                                                   : "Retransmit",
                   gap.start_seq_, gap.end_seq_);
         }
 
diff --git a/media/libaah_rtp/aah_rx_player_ring_buffer.cpp b/media/libaah_rtp/aah_rx_player_ring_buffer.cpp
index 0d8b31f..779405e 100644
--- a/media/libaah_rtp/aah_rx_player_ring_buffer.cpp
+++ b/media/libaah_rtp/aah_rx_player_ring_buffer.cpp
@@ -116,8 +116,8 @@
 
     // Check for overflow first.
     if ((!(norm_seq & 0x8000)) && (norm_seq >= (capacity_ - 1))) {
-        ALOGW("Ring buffer overflow; cap = %u, [rd, wr] = [%hu, %hu], seq = %hu",
-              capacity_, rd_seq_, norm_wr_seq + rd_seq_, seq);
+        ALOGW("Ring buffer overflow; cap = %u, [rd, wr] = [%hu, %hu],"
+              " seq = %hu", capacity_, rd_seq_, norm_wr_seq + rd_seq_, seq);
         PacketBuffer::destroy(buf);
         return false;
     }
diff --git a/media/libaah_rtp/aah_rx_player_substream.cpp b/media/libaah_rtp/aah_rx_player_substream.cpp
index 1e4c784..18b0e2b 100644
--- a/media/libaah_rtp/aah_rx_player_substream.cpp
+++ b/media/libaah_rtp/aah_rx_player_substream.cpp
@@ -27,6 +27,11 @@
 #include <media/stagefright/Utils.h>
 
 #include "aah_rx_player.h"
+#include "aah_tx_packet.h"
+
+inline uint32_t min(uint32_t a, uint32_t b) {
+    return (a < b ? a : b);
+}
 
 namespace android {
 
@@ -38,6 +43,7 @@
     substream_details_known_ = false;
     buffer_in_progress_ = NULL;
     status_ = OK;
+    codec_mime_type_ = "";
 
     decoder_ = new AAH_DecoderPump(omx);
     if (decoder_ == NULL) {
@@ -52,6 +58,9 @@
     cleanupBufferInProgress();
 }
 
+AAH_RXPlayer::Substream::~Substream() {
+    shutdown();
+}
 
 void AAH_RXPlayer::Substream::shutdown() {
     substream_meta_ = NULL;
@@ -69,6 +78,9 @@
     expected_buffer_size_ = 0;
     buffer_filled_ = 0;
     waiting_for_rap_ = true;
+
+    aux_data_in_progress_.clear();
+    aux_data_expected_size_ = 0;
 }
 
 void AAH_RXPlayer::Substream::cleanupDecoder() {
@@ -129,16 +141,16 @@
     // one that does not conflict with any previously received substream type.
     uint8_t header_type = (buf[1] >> 4) & 0xF;
     switch (header_type) {
-        case 0x01:
+        case TRTPPacket::kHeaderTypeAudio:
             // Audio, yay!  Just break.  We understand audio payloads.
             break;
-        case 0x02:
+        case TRTPPacket::kHeaderTypeVideo:
             ALOGV("RXed packet with unhandled TRTP header type (Video).");
             return;
-        case 0x03:
+        case TRTPPacket::kHeaderTypeSubpicture:
             ALOGV("RXed packet with unhandled TRTP header type (Subpicture).");
             return;
-        case 0x04:
+        case TRTPPacket::kHeaderTypeControl:
             ALOGV("RXed packet with unhandled TRTP header type (Control).");
             return;
         default:
@@ -148,15 +160,15 @@
     }
 
     if (substream_details_known_ && (header_type != substream_type_)) {
-        ALOGV("RXed TRTP Payload for SSRC=0x%08x where header type (%u) does not"
-              " match previously received header type (%u)",
+        ALOGV("RXed TRTP Payload for SSRC=0x%08x where header type (%u) does"
+              " not match previously received header type (%u)",
               ssrc_, header_type, substream_type_);
         return;
     }
 
     // Check the flags to see if there is another 32 bits of timestamp present.
     uint32_t trtp_header_len = 6;
-    bool ts_valid = buf[1] & 0x1;
+    bool ts_valid = buf[1] & TRTPPacket::kFlag_TSValid;
     if (ts_valid) {
         min_length += 4;
         trtp_header_len += 4;
@@ -168,11 +180,7 @@
     }
 
     // Extract the TRTP length field and sanity check it.
-    uint32_t trtp_len;
-    trtp_len = (static_cast<uint32_t>(buf[2]) << 24) |
-        (static_cast<uint32_t>(buf[3]) << 16) |
-        (static_cast<uint32_t>(buf[4]) <<  8) |
-        static_cast<uint32_t>(buf[5]);
+    uint32_t trtp_len = U32_AT(buf + 2);
     if (trtp_len < min_length) {
         ALOGV("TRTP length (%u) is too short to be valid.  Must be at least %u"
               " bytes.", trtp_len, min_length);
@@ -183,17 +191,14 @@
     int64_t ts = 0;
     uint32_t parse_offset = 6;
     if (ts_valid) {
-        ts = (static_cast<int64_t>(buf[parse_offset    ]) << 56) |
-            (static_cast<int64_t>(buf[parse_offset + 1]) << 48) |
-            (static_cast<int64_t>(buf[parse_offset + 2]) << 40) |
-            (static_cast<int64_t>(buf[parse_offset + 3]) << 32);
-        ts |= ts_lower;
+        uint32_t ts_upper = U32_AT(buf + parse_offset);
         parse_offset += 4;
+        ts = (static_cast<int64_t>(ts_upper) << 32) | ts_lower;
     }
 
     // Check the flags to see if there is another 24 bytes of timestamp
     // transformation present.
-    if (buf[1] & 0x2) {
+    if (buf[1] & TRTPPacket::kFlag_TSTransformPresent) {
         min_length += 24;
         parse_offset += 24;
         trtp_header_len += 24;
@@ -219,8 +224,8 @@
 
     if (amt < min_length) {
         ALOGV("TRTP porttion of RTP payload (%u bytes) too small to contain"
-              " entire TRTP header.  TRTP does not currently support fragmenting"
-              " TRTP headers across RTP payloads", amt);
+              " entire TRTP header.  TRTP does not currently support"
+              " fragmenting TRTP headers across RTP payloads", amt);
         return;
     }
 
@@ -238,16 +243,42 @@
         decoder_->setRenderVolume(volume);
     }
 
-    // TODO : move all of the constant flag and offset definitions for TRTP up
-    // into some sort of common header file.
-    if (waiting_for_rap_ && !(flags & 0x08)) {
+    if (waiting_for_rap_ && !(flags & TRTPAudioPacket::kFlag_RandomAccessPoint)) {
         ALOGV("Dropping non-RAP TRTP Audio Payload while waiting for RAP.");
         return;
     }
 
-    if (flags & 0x10) {
-        ALOGV("Dropping TRTP Audio Payload with aux codec data present (only"
-              " handle MP3 right now, and it has no aux data)");
+    // Check for the presence of codec aux data.
+    if (flags & TRTPAudioPacket::kFlag_AuxLengthPresent) {
+        min_length += 4;
+        trtp_header_len += 4;
+
+        if (trtp_len < min_length) {
+            ALOGV("TRTP length (%u) is too short to be a valid audio payload.  "
+                  "Must be at least %u bytes.", trtp_len, min_length);
+            return;
+        }
+
+        if (amt < min_length) {
+            ALOGV("TRTP porttion of RTP payload (%u bytes) too small to contain"
+                  " entire TRTP header.  TRTP does not currently support"
+                  " fragmenting TRTP headers across RTP payloads", amt);
+            return;
+        }
+
+        aux_data_expected_size_ = U32_AT(buf + parse_offset);
+        aux_data_in_progress_.clear();
+        if (aux_data_in_progress_.capacity() < aux_data_expected_size_) {
+            aux_data_in_progress_.setCapacity(aux_data_expected_size_);
+        }
+    } else {
+        aux_data_expected_size_ = 0;
+    }
+
+    if ((aux_data_expected_size_ + trtp_header_len) > trtp_len) {
+        ALOGV("Expected codec aux data length (%u) and TRTP header overhead"
+              " (%u) too large for total TRTP payload length (%u).",
+             aux_data_expected_size_, trtp_header_len, trtp_len);
         return;
     }
 
@@ -255,7 +286,9 @@
     // the buffer in progress and pack as much payload as we can into it.  If
     // the payload is finished once we are done, go ahead and send the payload
     // to the decoder.
-    expected_buffer_size_ = trtp_len - trtp_header_len;
+    expected_buffer_size_ = trtp_len
+                          - trtp_header_len
+                          - aux_data_expected_size_;
     if (!expected_buffer_size_) {
         ALOGV("Dropping TRTP Audio Payload with 0 Access Unit length");
         return;
@@ -263,9 +296,10 @@
 
     CHECK(amt >= trtp_header_len);
     uint32_t todo = amt - trtp_header_len;
-    if (expected_buffer_size_ < todo) {
+    if ((expected_buffer_size_ + aux_data_expected_size_) < todo) {
         ALOGV("Extra data (%u > %u) present in initial TRTP Audio Payload;"
-              " dropping payload.", todo, expected_buffer_size_);
+              " dropping payload.", todo,
+              expected_buffer_size_ + aux_data_expected_size_);
         return;
     }
 
@@ -287,18 +321,32 @@
         return;
     }
 
-    // TODO : set this based on the codec type indicated in the TRTP stream.
-    // Right now, we only support MP3, so the choice is obvious.
-    meta->setCString(kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_MPEG);
+    meta->setCString(kKeyMIMEType, codec_mime_type_);
     if (ts_valid) {
         meta->setInt64(kKeyTime, ts);
     }
 
-    if (amt > 0) {
+    // Skip over the header we have already extracted.
+    amt -= trtp_header_len;
+    buf += trtp_header_len;
+
+    // Extract as much of the expected aux data as we can.
+    todo = min(aux_data_expected_size_, amt);
+    if (todo) {
+        aux_data_in_progress_.appendArray(buf, todo);
+        buf += todo;
+        amt -= todo;
+    }
+
+    // Extract as much of the expected payload as we can.
+    todo = min(expected_buffer_size_, amt);
+    if (todo > 0) {
         uint8_t* tgt =
             reinterpret_cast<uint8_t*>(buffer_in_progress_->data());
-        memcpy(tgt + buffer_filled_, buf + trtp_header_len, todo);
-        buffer_filled_ += amt;
+        memcpy(tgt, buf, todo);
+        buffer_filled_ = amt;
+        buf += todo;
+        amt -= todo;
     }
 
     if (buffer_filled_ >= expected_buffer_size_) {
@@ -318,6 +366,18 @@
         return;
     }
 
+    CHECK(aux_data_in_progress_.size() <= aux_data_expected_size_);
+    uint32_t aux_left = aux_data_expected_size_ - aux_data_in_progress_.size();
+    if (aux_left) {
+        uint32_t todo = min(aux_left, amt);
+        aux_data_in_progress_.appendArray(buf, todo);
+        amt -= todo;
+        buf += todo;
+
+        if (!amt)
+            return;
+    }
+
     CHECK(buffer_filled_ < expected_buffer_size_);
     uint32_t buffer_left = expected_buffer_size_ - buffer_filled_;
     if (amt > buffer_left) {
@@ -340,10 +400,6 @@
 }
 
 void AAH_RXPlayer::Substream::processCompletedBuffer() {
-    const uint8_t* buffer_data = NULL;
-    int sample_rate;
-    int channel_count;
-    size_t frame_size;
     status_t res;
 
     CHECK(NULL != buffer_in_progress_);
@@ -353,56 +409,10 @@
         goto bailout;
     }
 
-    buffer_data = reinterpret_cast<const uint8_t*>(buffer_in_progress_->data());
-    if (buffer_in_progress_->size() < 4) {
-        ALOGV("MP3 payload too short to contain header, dropping payload.");
+    // Make sure our metadata used to initialize the decoder has been properly
+    // set up.
+    if (!setupSubstreamMeta())
         goto bailout;
-    }
-
-    // Extract the channel count and the sample rate from the MP3 header.  The
-    // stagefright MP3 requires that these be delivered before decoing can
-    // begin.
-    if (!GetMPEGAudioFrameSize(U32_AT(buffer_data),
-                               &frame_size,
-                               &sample_rate,
-                               &channel_count,
-                               NULL,
-                               NULL)) {
-        ALOGV("Failed to parse MP3 header in payload, droping payload.");
-        goto bailout;
-    }
-
-
-    // Make sure that our substream metadata is set up properly.  If there has
-    // been a format change, be sure to reset the underlying decoder.  In
-    // stagefright, it seems like the only way to do this is to destroy and
-    // recreate the decoder.
-    if (substream_meta_ == NULL) {
-        substream_meta_ = new MetaData();
-
-        if (substream_meta_ == NULL) {
-            ALOGE("Failed to allocate MetaData structure for substream");
-            goto bailout;
-        }
-
-        substream_meta_->setCString(kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_MPEG);
-        substream_meta_->setInt32  (kKeyChannelCount, channel_count);
-        substream_meta_->setInt32  (kKeySampleRate,   sample_rate);
-    } else {
-        int32_t prev_sample_rate;
-        int32_t prev_channel_count;
-        substream_meta_->findInt32(kKeySampleRate,   &prev_sample_rate);
-        substream_meta_->findInt32(kKeyChannelCount, &prev_channel_count);
-
-        if ((prev_channel_count != channel_count) ||
-            (prev_sample_rate   != sample_rate)) {
-            ALOGW("Format change detected, forcing decoder reset.");
-            cleanupDecoder();
-
-            substream_meta_->setInt32(kKeyChannelCount, channel_count);
-            substream_meta_->setInt32(kKeySampleRate,   sample_rate);
-        }
-    }
 
     // If our decoder has not be set up, do so now.
     res = decoder_->init(substream_meta_);
@@ -418,7 +428,7 @@
 
     if (res != OK) {
         ALOGD("Failed to queue payload for decode, resetting decoder pump!"
-              " (res = %d)", res);
+             " (res = %d)", res);
         status_ = res;
         cleanupDecoder();
         cleanupBufferInProgress();
@@ -454,6 +464,167 @@
     cleanupBufferInProgress();
 }
 
+bool AAH_RXPlayer::Substream::setupSubstreamMeta() {
+    switch (codec_type_) {
+        case TRTPAudioPacket::kCodecMPEG1Audio:
+            codec_mime_type_ = MEDIA_MIMETYPE_AUDIO_MPEG;
+            return setupMP3SubstreamMeta();
+
+        case TRTPAudioPacket::kCodecAACAudio:
+            codec_mime_type_ = MEDIA_MIMETYPE_AUDIO_AAC;
+            return setupAACSubstreamMeta();
+
+        default:
+            ALOGV("Failed to setup substream metadata for unsupported codec"
+                  " type (%u)", codec_type_);
+            break;
+    }
+
+    return false;
+}
+
+bool AAH_RXPlayer::Substream::setupMP3SubstreamMeta() {
+    const uint8_t* buffer_data = NULL;
+    int sample_rate;
+    int channel_count;
+    size_t frame_size;
+    status_t res;
+
+    buffer_data = reinterpret_cast<const uint8_t*>(buffer_in_progress_->data());
+    if (buffer_in_progress_->size() < 4) {
+        ALOGV("MP3 payload too short to contain header, dropping payload.");
+        return false;
+    }
+
+    // Extract the channel count and the sample rate from the MP3 header.  The
+    // stagefright MP3 requires that these be delivered before decoing can
+    // begin.
+    if (!GetMPEGAudioFrameSize(U32_AT(buffer_data),
+                               &frame_size,
+                               &sample_rate,
+                               &channel_count,
+                               NULL,
+                               NULL)) {
+        ALOGV("Failed to parse MP3 header in payload, droping payload.");
+        return false;
+    }
+
+
+    // Make sure that our substream metadata is set up properly.  If there has
+    // been a format change, be sure to reset the underlying decoder.  In
+    // stagefright, it seems like the only way to do this is to destroy and
+    // recreate the decoder.
+    if (substream_meta_ == NULL) {
+        substream_meta_ = new MetaData();
+
+        if (substream_meta_ == NULL) {
+            ALOGE("Failed to allocate MetaData structure for MP3 substream");
+            return false;
+        }
+
+        substream_meta_->setCString(kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_MPEG);
+        substream_meta_->setInt32  (kKeyChannelCount, channel_count);
+        substream_meta_->setInt32  (kKeySampleRate,   sample_rate);
+    } else {
+        int32_t prev_sample_rate;
+        int32_t prev_channel_count;
+        substream_meta_->findInt32(kKeySampleRate,   &prev_sample_rate);
+        substream_meta_->findInt32(kKeyChannelCount, &prev_channel_count);
+
+        if ((prev_channel_count != channel_count) ||
+            (prev_sample_rate   != sample_rate)) {
+            ALOGW("MP3 format change detected, forcing decoder reset.");
+            cleanupDecoder();
+
+            substream_meta_->setInt32(kKeyChannelCount, channel_count);
+            substream_meta_->setInt32(kKeySampleRate,   sample_rate);
+        }
+    }
+
+    return true;
+}
+
+bool AAH_RXPlayer::Substream::setupAACSubstreamMeta() {
+    int32_t sample_rate, channel_cnt;
+    static const size_t overhead = sizeof(sample_rate)
+                                 + sizeof(channel_cnt);
+
+    if (aux_data_in_progress_.size() < overhead) {
+        ALOGE("Not enough aux data (%u) to initialize AAC substream decoder",
+                aux_data_in_progress_.size());
+        return false;
+    }
+
+    const uint8_t* aux_data = aux_data_in_progress_.array();
+    size_t aux_data_size = aux_data_in_progress_.size();
+    sample_rate = U32_AT(aux_data);
+    channel_cnt = U32_AT(aux_data + sizeof(sample_rate));
+
+    const uint8_t* esds_data = NULL;
+    size_t esds_data_size = 0;
+    if (aux_data_size > overhead) {
+        esds_data = aux_data + overhead;
+        esds_data_size = aux_data_size - overhead;
+    }
+
+    // Do we already have metadata?  If so, has it changed at all?  If not, then
+    // there should be nothing else to do.  Otherwise, release our old stream
+    // metadata and make new metadata.
+    if (substream_meta_ != NULL) {
+        uint32_t type;
+        const void* data;
+        size_t size;
+        int32_t prev_sample_rate;
+        int32_t prev_channel_count;
+        bool res;
+
+        res = substream_meta_->findInt32(kKeySampleRate,   &prev_sample_rate);
+        CHECK(res);
+        res = substream_meta_->findInt32(kKeyChannelCount, &prev_channel_count);
+        CHECK(res);
+
+        // If nothing has changed about the codec aux data (esds, sample rate,
+        // channel count), then we can just do nothing and get out.  Otherwise,
+        // we will need to reset the decoder and make a new metadata object to
+        // deal with the format change.
+        bool hasData = (esds_data != NULL);
+        bool hadData = substream_meta_->findData(kKeyESDS, &type, &data, &size);
+        bool esds_change = (hadData != hasData);
+
+        if (!esds_change && hasData)
+            esds_change = ((size != esds_data_size) ||
+                           memcmp(data, esds_data, size));
+
+        if (!esds_change &&
+            (prev_sample_rate   == sample_rate) &&
+            (prev_channel_count == channel_cnt)) {
+            return true;  // no change, just get out.
+        }
+
+        ALOGW("AAC format change detected, forcing decoder reset.");
+        cleanupDecoder();
+        substream_meta_ = NULL;
+    }
+
+    CHECK(substream_meta_ == NULL);
+
+    substream_meta_ = new MetaData();
+    if (substream_meta_ == NULL) {
+        ALOGE("Failed to allocate MetaData structure for AAC substream");
+        return false;
+    }
+
+    substream_meta_->setCString(kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_AAC);
+    substream_meta_->setInt32  (kKeySampleRate,   sample_rate);
+    substream_meta_->setInt32  (kKeyChannelCount, channel_cnt);
+
+    if (esds_data) {
+        substream_meta_->setData(kKeyESDS, kTypeESDS,
+                                 esds_data, esds_data_size);
+    }
+
+    return true;
+}
 
 void AAH_RXPlayer::Substream::processTSTransform(const LinearTransform& trans) {
     if (decoder_ != NULL) {
@@ -471,26 +642,34 @@
 
 bool AAH_RXPlayer::Substream::setupSubstreamType(uint8_t substream_type,
                                                  uint8_t codec_type) {
-    // Sanity check the codec type.  Right now we only support MP3.  Also check
-    // for conflicts with previously delivered codec types.
-    if (substream_details_known_ && (codec_type != codec_type_)) {
-        ALOGV("RXed TRTP Payload for SSRC=0x%08x where codec type (%u) does not"
-              " match previously received codec type (%u)",
-              ssrc_, codec_type, codec_type_);
-        return false;
+    // Sanity check the codec type.  Right now we only support MP3 and AAC.
+    // Also check for conflicts with previously delivered codec types.
+    if (substream_details_known_) {
+        if (codec_type != codec_type_) {
+            ALOGV("RXed TRTP Payload for SSRC=0x%08x where codec type (%u) does"
+                  " not match previously received codec type (%u)",
+                 ssrc_, codec_type, codec_type_);
+            return false;
+        }
+
+        return true;
     }
 
-    if (codec_type != 0x03) {
-        ALOGV("RXed TRTP Audio Payload for SSRC=0x%08x with unsupported codec"
-              " type (%u)", ssrc_, codec_type);
-        return false;
+    switch (codec_type) {
+        // MP3 and AAC are all we support right now.
+        case TRTPAudioPacket::kCodecMPEG1Audio:
+        case TRTPAudioPacket::kCodecAACAudio:
+            break;
+
+        default:
+            ALOGV("RXed TRTP Audio Payload for SSRC=0x%08x with unsupported"
+                  " codec type (%u)", ssrc_, codec_type);
+            return false;
     }
 
-    if (!substream_details_known_) {
-        substream_type_ = substream_type;
-        codec_type_ = codec_type;
-        substream_details_known_ = true;
-    }
+    substream_type_ = substream_type;
+    codec_type_ = codec_type;
+    substream_details_known_ = true;
 
     return true;
 }
diff --git a/media/libaah_rtp/aah_tx_packet.cpp b/media/libaah_rtp/aah_tx_packet.cpp
index 3f6e0e9..4cd6e47 100644
--- a/media/libaah_rtp/aah_tx_packet.cpp
+++ b/media/libaah_rtp/aah_tx_packet.cpp
@@ -142,12 +142,18 @@
     mVolume = val;
 }
 
-void TRTPAudioPacket::setAccessUnitData(void* data, int len) {
+void TRTPAudioPacket::setAccessUnitData(const void* data, size_t len) {
     CHECK(!mIsPacked);
     mAccessUnitData = data;
     mAccessUnitLen = len;
 }
 
+void TRTPAudioPacket::setAuxData(const void* data, size_t len) {
+    CHECK(!mIsPacked);
+    mAuxData = data;
+    mAuxDataLen = len;
+}
+
 /*** TRTP control packet properties ***/
 
 void TRTPControlPacket::setCommandID(TRTPCommandID val) {
@@ -232,6 +238,7 @@
     }
 
     int packetLen = kRTPHeaderLen +
+                    mAuxDataLen +
                     mAccessUnitLen +
                     TRTPHeaderLen();
 
@@ -249,16 +256,24 @@
     mPacketLen = packetLen;
 
     uint8_t* cur = mPacket;
+    bool hasAux = mAuxData && mAuxDataLen;
+    uint8_t flags = (static_cast<int>(hasAux) << 4) |
+                    (static_cast<int>(mRandomAccessPoint) << 3) |
+                    (static_cast<int>(mDropable) << 2) |
+                    (static_cast<int>(mDiscontinuity) << 1) |
+                    (static_cast<int>(mEndOfStream));
 
     writeTRTPHeader(cur, true, packetLen);
     writeU8(cur, mCodecType);
-    writeU8(cur,
-            (static_cast<int>(mRandomAccessPoint) << 3) |
-            (static_cast<int>(mDropable) << 2) |
-            (static_cast<int>(mDiscontinuity) << 1) |
-            (static_cast<int>(mEndOfStream)));
+    writeU8(cur, flags);
     writeU8(cur, mVolume);
 
+    if (hasAux) {
+        writeU32(cur, mAuxDataLen);
+        memcpy(cur, mAuxData, mAuxDataLen);
+        cur += mAuxDataLen;
+    }
+
     memcpy(cur, mAccessUnitData, mAccessUnitLen);
 
     mIsPacked = true;
@@ -293,12 +308,10 @@
     }
 
 
-    // TODO : properly compute aux data length.  Currently, nothing
-    // uses aux data, so its length is always 0.
-    int auxDataLength = 0;
+    int auxDataLenField = (NULL != mAuxData) ? sizeof(uint32_t) : 0;
     return TRTPPacket::TRTPHeaderLen() +
            3 +
-           auxDataLength +
+           auxDataLenField +
            pcmParamLength;
 }
 
diff --git a/media/libaah_rtp/aah_tx_packet.h b/media/libaah_rtp/aah_tx_packet.h
index 833803e..7f78ea0 100644
--- a/media/libaah_rtp/aah_tx_packet.h
+++ b/media/libaah_rtp/aah_tx_packet.h
@@ -25,7 +25,7 @@
 namespace android {
 
 class TRTPPacket : public RefBase {
-  protected:
+  public:
     enum TRTPHeaderType {
         kHeaderTypeAudio = 1,
         kHeaderTypeVideo = 2,
@@ -33,6 +33,12 @@
         kHeaderTypeControl = 4,
     };
 
+    enum TRTPPayloadFlags {
+        kFlag_TSTransformPresent = 0x02,
+        kFlag_TSValid = 0x01,
+    };
+
+  protected:
     TRTPPacket(TRTPHeaderType headerType)
         : mIsPacked(false)
         , mVersion(2)
@@ -121,6 +127,14 @@
 
 class TRTPAudioPacket : public TRTPPacket {
   public:
+    enum AudioPayloadFlags {
+        kFlag_AuxLengthPresent = 0x10,
+        kFlag_RandomAccessPoint = 0x08,
+        kFlag_Dropable = 0x04,
+        kFlag_Discontinuity = 0x02,
+        kFlag_EndOfStream = 0x01,
+    };
+
     TRTPAudioPacket()
         : TRTPPacket(kHeaderTypeAudio)
         , mCodecType(kCodecInvalid)
@@ -129,13 +143,17 @@
         , mDiscontinuity(false)
         , mEndOfStream(false)
         , mVolume(0)
-        , mAccessUnitData(NULL) { }
+        , mAccessUnitData(NULL)
+        , mAccessUnitLen(0)
+        , mAuxData(NULL)
+        , mAuxDataLen(0) { }
 
     enum TRTPAudioCodecType {
         kCodecInvalid = 0,
         kCodecPCMBigEndian = 1,
         kCodecPCMLittleEndian = 2,
         kCodecMPEG1Audio = 3,
+        kCodecAACAudio = 4,
     };
 
     void setCodecType(TRTPAudioCodecType val);
@@ -144,7 +162,8 @@
     void setDiscontinuity(bool val);
     void setEndOfStream(bool val);
     void setVolume(uint8_t val);
-    void setAccessUnitData(void* data, int len);
+    void setAccessUnitData(const void* data, size_t len);
+    void setAuxData(const void* data, size_t len);
 
     virtual bool pack();
 
@@ -158,8 +177,11 @@
     bool mDiscontinuity;
     bool mEndOfStream;
     uint8_t mVolume;
-    void* mAccessUnitData;
-    int mAccessUnitLen;
+
+    const void* mAccessUnitData;
+    size_t mAccessUnitLen;
+    const void* mAuxData;
+    size_t mAuxDataLen;
 
     DISALLOW_EVIL_CONSTRUCTORS(TRTPAudioPacket);
 };
diff --git a/media/libaah_rtp/aah_tx_player.cpp b/media/libaah_rtp/aah_tx_player.cpp
index a79a989..974805b 100644
--- a/media/libaah_rtp/aah_tx_player.cpp
+++ b/media/libaah_rtp/aah_tx_player.cpp
@@ -28,6 +28,7 @@
 #include <media/stagefright/foundation/AMessage.h>
 #include <media/stagefright/FileSource.h>
 #include <media/stagefright/MediaBuffer.h>
+#include <media/stagefright/MediaDefs.h>
 #include <media/stagefright/MetaData.h>
 #include <utils/Timers.h>
 
@@ -98,6 +99,8 @@
     mPumpAudioEvent = new AAH_TXEvent(this, &AAH_TXPlayer::onPumpAudio);
     mPumpAudioEventPending = false;
 
+    mAudioCodecData = NULL;
+
     reset_l();
 }
 
@@ -146,14 +149,7 @@
         const KeyedVector<String8, String8> *headers) {
     reset_l();
 
-    // the URL must consist of "aahTX://" followed by the real URL of
-    // the data source
-    const char *kAAHPrefix = "aahTX://";
-    if (strncasecmp(url, kAAHPrefix, strlen(kAAHPrefix))) {
-        return INVALID_OPERATION;
-    }
-
-    mUri.setTo(url + strlen(kAAHPrefix));
+    mUri.setTo(url);
 
     if (headers) {
         mUriHeaders = *headers;
@@ -398,7 +394,76 @@
         }
     }
 
-    mAudioSource->getFormat()->findInt64(kKeyDuration, &mDurationUs);
+    mAudioFormat = mAudioSource->getFormat();
+    if (!mAudioFormat->findInt64(kKeyDuration, &mDurationUs))
+        mDurationUs = 1;
+
+    const char* mime_type = NULL;
+    if (!mAudioFormat->findCString(kKeyMIMEType, &mime_type)) {
+        ALOGE("Failed to find audio substream MIME type during prepare.");
+        abortPrepare(BAD_VALUE);
+        return;
+    }
+
+    if (!strcmp(mime_type, MEDIA_MIMETYPE_AUDIO_MPEG)) {
+        mAudioCodec = TRTPAudioPacket::kCodecMPEG1Audio;
+    } else
+    if (!strcmp(mime_type, MEDIA_MIMETYPE_AUDIO_AAC)) {
+        mAudioCodec = TRTPAudioPacket::kCodecAACAudio;
+
+        uint32_t type;
+        int32_t  sample_rate;
+        int32_t  channel_count;
+        const void* esds_data;
+        size_t esds_len;
+
+        if (!mAudioFormat->findInt32(kKeySampleRate, &sample_rate)) {
+            ALOGE("Failed to find sample rate for AAC substream.");
+            abortPrepare(BAD_VALUE);
+            return;
+        }
+
+        if (!mAudioFormat->findInt32(kKeyChannelCount, &channel_count)) {
+            ALOGE("Failed to find channel count for AAC substream.");
+            abortPrepare(BAD_VALUE);
+            return;
+        }
+
+        if (!mAudioFormat->findData(kKeyESDS, &type, &esds_data, &esds_len)) {
+            ALOGE("Failed to find codec init data for AAC substream.");
+            abortPrepare(BAD_VALUE);
+            return;
+        }
+
+        CHECK(NULL == mAudioCodecData);
+        mAudioCodecDataSize = esds_len
+                            + sizeof(sample_rate)
+                            + sizeof(channel_count);
+        mAudioCodecData = new uint8_t[mAudioCodecDataSize];
+        if (NULL == mAudioCodecData) {
+            ALOGE("Failed to allocate %u bytes for AAC substream codec aux"
+                  " data.", mAudioCodecDataSize);
+            mAudioCodecDataSize = 0;
+            abortPrepare(BAD_VALUE);
+            return;
+        }
+
+        uint8_t* tmp = mAudioCodecData;
+        tmp[0] = static_cast<uint8_t>((sample_rate   >> 24) & 0xFF);
+        tmp[1] = static_cast<uint8_t>((sample_rate   >> 16) & 0xFF);
+        tmp[2] = static_cast<uint8_t>((sample_rate   >>  8) & 0xFF);
+        tmp[3] = static_cast<uint8_t>((sample_rate        ) & 0xFF);
+        tmp[4] = static_cast<uint8_t>((channel_count >> 24) & 0xFF);
+        tmp[5] = static_cast<uint8_t>((channel_count >> 16) & 0xFF);
+        tmp[6] = static_cast<uint8_t>((channel_count >>  8) & 0xFF);
+        tmp[7] = static_cast<uint8_t>((channel_count      ) & 0xFF);
+
+        memcpy(tmp + 8, esds_data, esds_len);
+    } else {
+        ALOGE("Unsupported MIME type \"%s\" in audio substream", mime_type);
+        abortPrepare(BAD_VALUE);
+        return;
+    }
 
     status_t err = mAudioSource->start();
     if (err != OK) {
@@ -666,6 +731,11 @@
         mAudioSource->stop();
     }
     mAudioSource.clear();
+    mAudioCodec = TRTPAudioPacket::kCodecInvalid;
+    mAudioFormat = NULL;
+    delete[] mAudioCodecData;
+    mAudioCodecData = NULL;
+    mAudioCodecDataSize = 0;
 
     mFlags = 0;
     mExtractorFlags = 0;
@@ -717,67 +787,7 @@
 }
 
 status_t AAH_TXPlayer::invoke(const Parcel& request, Parcel *reply) {
-    if (!reply) {
-        return BAD_VALUE;
-    }
-
-    int32_t methodID;
-    status_t err = request.readInt32(&methodID);
-    if (err != android::OK) {
-        return err;
-    }
-
-    switch (methodID) {
-        case kInvokeSetAAHDstIPPort:
-        case kInvokeSetAAHConfigBlob: {
-            if (mEndpointValid) {
-                return INVALID_OPERATION;
-            }
-
-            String8 addr;
-            uint16_t port;
-
-            if (methodID == kInvokeSetAAHDstIPPort) {
-                addr = String8(request.readString16());
-
-                int32_t port32;
-                err = request.readInt32(&port32);
-                if (err != android::OK) {
-                    return err;
-                }
-                port = static_cast<uint16_t>(port32);
-            } else {
-                String8 blob(request.readString16());
-
-                char addr_buf[101];
-                if (sscanf(blob.string(), "V1:%100s %" SCNu16,
-                           addr_buf, &port) != 2) {
-                    return BAD_VALUE;
-                }
-                if (addr.setTo(addr_buf) != OK) {
-                    return NO_MEMORY;
-                }
-            }
-
-            struct hostent* ent = gethostbyname(addr.string());
-            if (ent == NULL) {
-                return ERROR_UNKNOWN_HOST;
-            }
-            if (!(ent->h_addrtype == AF_INET && ent->h_length == 4)) {
-                return BAD_VALUE;
-            }
-
-            Mutex::Autolock lock(mEndpointLock);
-            mEndpoint = AAH_TXSender::Endpoint(
-                        reinterpret_cast<struct in_addr*>(ent->h_addr)->s_addr,
-                        port);
-            mEndpointValid = true;
-            return OK;
-        };
-
-        default:
-            return INVALID_OPERATION;
-    }
+    return INVALID_OPERATION;
 }
 
 status_t AAH_TXPlayer::getMetadata(const media::Metadata::Filter& ids,
@@ -812,6 +822,24 @@
     return OK;
 }
 
+status_t AAH_TXPlayer::setRetransmitEndpoint(
+        const struct sockaddr_in* endpoint) {
+    Mutex::Autolock lock(mLock);
+
+    if (NULL == endpoint)
+        return BAD_VALUE;
+
+    // Once the endpoint has been registered, it may not be changed.
+    if (mEndpointRegistered)
+        return INVALID_OPERATION;
+
+    mEndpoint.addr = endpoint->sin_addr.s_addr;
+    mEndpoint.port = endpoint->sin_port;
+    mEndpointValid = true;
+
+    return OK;
+}
+
 void AAH_TXPlayer::notifyListener_l(int msg, int ext1, int ext2) {
     sendEvent(msg, ext1, ext2);
 }
@@ -1078,14 +1106,24 @@
         packet->setPTS(mediaTimeUs);
         packet->setSubstreamID(1);
 
-        packet->setCodecType(TRTPAudioPacket::kCodecMPEG1Audio);
+        packet->setCodecType(mAudioCodec);
         packet->setVolume(mTRTPVolume);
         // TODO : introduce a throttle for this so we can control the
         // frequency with which transforms get sent.
         packet->setClockTransform(mCurrentClockTransform);
         packet->setAccessUnitData(data, mediaBuffer->range_length());
+
+        // TODO : while its pretty much universally true that audio ES payloads
+        // are all RAPs across all codecs, it might be a good idea to throttle
+        // the frequency with which we send codec out of band data to the RXers.
+        // If/when we do, we need to flag only those payloads which have
+        // required out of band data attached to them as RAPs.
         packet->setRandomAccessPoint(true);
 
+        if (mAudioCodecData && mAudioCodecDataSize) {
+            packet->setAuxData(mAudioCodecData, mAudioCodecDataSize);
+        }
+
         queuePacketToSender_l(packet);
         mediaBuffer->release();
 
diff --git a/media/libaah_rtp/aah_tx_player.h b/media/libaah_rtp/aah_tx_player.h
index 64cf5dc..2e4b1f7 100644
--- a/media/libaah_rtp/aah_tx_player.h
+++ b/media/libaah_rtp/aah_tx_player.h
@@ -63,16 +63,8 @@
                                     Parcel* records);
     virtual status_t    setVolume(float leftVolume, float rightVolume);
     virtual status_t    setAudioStreamType(audio_stream_type_t streamType);
-
-    // invoke method IDs
-    enum {
-        // set the IP address and port of the A@H receiver
-        kInvokeSetAAHDstIPPort = 1,
-
-        // set the destination IP address and port (and perhaps any additional
-        // parameters added in the future) packaged in one string
-        kInvokeSetAAHConfigBlob,
-    };
+    virtual status_t    setRetransmitEndpoint(
+                            const struct sockaddr_in* endpoint);
 
     static const int64_t kAAHRetryKeepAroundTimeNs;
 
@@ -153,6 +145,11 @@
     sp<NuCachedSource2> mCachedSource;
 
     sp<MediaSource> mAudioSource;
+    TRTPAudioPacket::TRTPAudioCodecType mAudioCodec;
+    sp<MetaData> mAudioFormat;
+    uint8_t* mAudioCodecData;
+    size_t mAudioCodecDataSize;
+
     int64_t mDurationUs;
     int64_t mBitrate;
 
diff --git a/media/libaah_rtp/aah_tx_sender.cpp b/media/libaah_rtp/aah_tx_sender.cpp
index d991ea7..08e32d2 100644
--- a/media/libaah_rtp/aah_tx_sender.cpp
+++ b/media/libaah_rtp/aah_tx_sender.cpp
@@ -243,7 +243,7 @@
     memset(&addr, 0, sizeof(addr));
     addr.sin_family = AF_INET;
     addr.sin_addr.s_addr = endpoint.addr;
-    addr.sin_port = htons(endpoint.port);
+    addr.sin_port = endpoint.port;
 
     ssize_t result = sendto(mSocket,
                             packet->getPacket(),
@@ -283,7 +283,8 @@
     // remove the state for any endpoints that are no longer in use
     for (size_t i = 0; i < endpointsToRemove.size(); i++) {
         Endpoint& e = endpointsToRemove.editItemAt(i);
-        ALOGD("*** %s removing endpoint addr=%08x", __PRETTY_FUNCTION__, e.addr);
+        ALOGD("*** %s removing endpoint addr=%08x",
+                __PRETTY_FUNCTION__, e.addr);
         size_t index = mEndpointMap.indexOfKey(e);
         delete mEndpointMap.valueAt(index);
         mEndpointMap.removeItemsAt(index);
@@ -411,7 +412,7 @@
         return;
     }
 
-    Endpoint endpoint(request.endpointIP, ntohs(request.endpointPort));
+    Endpoint endpoint(request.endpointIP, request.endpointPort);
 
     Mutex::Autolock lock(mSender->mEndpointLock);
 
diff --git a/media/libeffects/data/audio_effects.conf b/media/libeffects/data/audio_effects.conf
index b8fa487..ce25bc8 100644
--- a/media/libeffects/data/audio_effects.conf
+++ b/media/libeffects/data/audio_effects.conf
@@ -50,11 +50,11 @@
   }
   volume {
     library bundle
-    uuid 119341a0-8469-11df-81f9- 0002a5d5c51b
+    uuid 119341a0-8469-11df-81f9-0002a5d5c51b
   }
   reverb_env_aux {
     library reverb
-    uuid 4a387fc0-8ab3-11df-8bad- 0002a5d5c51b
+    uuid 4a387fc0-8ab3-11df-8bad-0002a5d5c51b
   }
   reverb_env_ins {
     library reverb
diff --git a/media/libmedia/IMediaPlayer.cpp b/media/libmedia/IMediaPlayer.cpp
index 86d65db..c47fa41 100644
--- a/media/libmedia/IMediaPlayer.cpp
+++ b/media/libmedia/IMediaPlayer.cpp
@@ -15,6 +15,7 @@
 ** limitations under the License.
 */
 
+#include <arpa/inet.h>
 #include <stdint.h>
 #include <sys/types.h>
 
@@ -53,6 +54,7 @@
     SET_VIDEO_SURFACETEXTURE,
     SET_PARAMETER,
     GET_PARAMETER,
+    SET_RETRANSMIT_ENDPOINT,
 };
 
 class BpMediaPlayer: public BpInterface<IMediaPlayer>
@@ -289,6 +291,25 @@
         return remote()->transact(GET_PARAMETER, data, reply);
     }
 
+    status_t setRetransmitEndpoint(const struct sockaddr_in* endpoint) {
+        Parcel data, reply;
+        status_t err;
+
+        data.writeInterfaceToken(IMediaPlayer::getInterfaceDescriptor());
+        if (NULL != endpoint) {
+            data.writeInt32(sizeof(*endpoint));
+            data.write(endpoint, sizeof(*endpoint));
+        } else {
+            data.writeInt32(0);
+        }
+
+        err = remote()->transact(SET_RETRANSMIT_ENDPOINT, data, &reply);
+        if (OK != err) {
+            return err;
+        }
+
+        return reply.readInt32();
+    }
 };
 
 IMPLEMENT_META_INTERFACE(MediaPlayer, "android.media.IMediaPlayer");
@@ -457,6 +478,20 @@
             CHECK_INTERFACE(IMediaPlayer, data, reply);
             return getParameter(data.readInt32(), reply);
         } break;
+        case SET_RETRANSMIT_ENDPOINT: {
+            CHECK_INTERFACE(IMediaPlayer, data, reply);
+
+            struct sockaddr_in endpoint;
+            int amt = data.readInt32();
+            if (amt == sizeof(endpoint)) {
+                data.read(&endpoint, sizeof(struct sockaddr_in));
+                reply->writeInt32(setRetransmitEndpoint(&endpoint));
+            } else {
+                reply->writeInt32(setRetransmitEndpoint(NULL));
+            }
+
+            return NO_ERROR;
+        } break;
         default:
             return BBinder::onTransact(code, data, reply, flags);
     }
diff --git a/media/libmedia/mediaplayer.cpp b/media/libmedia/mediaplayer.cpp
index 9d45907..4ff1862 100644
--- a/media/libmedia/mediaplayer.cpp
+++ b/media/libmedia/mediaplayer.cpp
@@ -61,6 +61,7 @@
     mAudioSessionId = AudioSystem::newAudioSessionId();
     AudioSystem::acquireAudioSessionId(mAudioSessionId);
     mSendLevel = 0;
+    mRetransmitEndpointValid = false;
 }
 
 MediaPlayer::~MediaPlayer()
@@ -93,6 +94,7 @@
     mCurrentPosition = -1;
     mSeekPosition = -1;
     mVideoWidth = mVideoHeight = 0;
+    mRetransmitEndpointValid = false;
 }
 
 status_t MediaPlayer::setListener(const sp<MediaPlayerListener>& listener)
@@ -144,7 +146,8 @@
         const sp<IMediaPlayerService>& service(getMediaPlayerService());
         if (service != 0) {
             sp<IMediaPlayer> player(service->create(getpid(), this, mAudioSessionId));
-            if (NO_ERROR != player->setDataSource(url, headers)) {
+            if ((NO_ERROR != doSetRetransmitEndpoint(player)) ||
+                (NO_ERROR != player->setDataSource(url, headers))) {
                 player.clear();
             }
             err = attachNewPlayer(player);
@@ -160,7 +163,8 @@
     const sp<IMediaPlayerService>& service(getMediaPlayerService());
     if (service != 0) {
         sp<IMediaPlayer> player(service->create(getpid(), this, mAudioSessionId));
-        if (NO_ERROR != player->setDataSource(fd, offset, length)) {
+        if ((NO_ERROR != doSetRetransmitEndpoint(player)) ||
+            (NO_ERROR != player->setDataSource(fd, offset, length))) {
             player.clear();
         }
         err = attachNewPlayer(player);
@@ -175,7 +179,8 @@
     const sp<IMediaPlayerService>& service(getMediaPlayerService());
     if (service != 0) {
         sp<IMediaPlayer> player(service->create(getpid(), this, mAudioSessionId));
-        if (NO_ERROR != player->setDataSource(source)) {
+        if ((NO_ERROR != doSetRetransmitEndpoint(player)) ||
+            (NO_ERROR != player->setDataSource(source))) {
             player.clear();
         }
         err = attachNewPlayer(player);
@@ -469,6 +474,20 @@
     return NO_ERROR;
 }
 
+status_t MediaPlayer::doSetRetransmitEndpoint(const sp<IMediaPlayer>& player) {
+    Mutex::Autolock _l(mLock);
+
+    if (player == NULL) {
+        return UNKNOWN_ERROR;
+    }
+
+    if (mRetransmitEndpointValid) {
+        return player->setRetransmitEndpoint(&mRetransmitEndpoint);
+    }
+
+    return OK;
+}
+
 status_t MediaPlayer::reset()
 {
     ALOGV("reset");
@@ -597,6 +616,34 @@
     return INVALID_OPERATION;
 }
 
+status_t MediaPlayer::setRetransmitEndpoint(const char* addrString,
+                                            uint16_t port) {
+    ALOGV("MediaPlayer::setRetransmitEndpoint(%s:%hu)",
+            addrString ? addrString : "(null)", port);
+
+    Mutex::Autolock _l(mLock);
+    if ((mPlayer != NULL) || (mCurrentState != MEDIA_PLAYER_IDLE))
+        return INVALID_OPERATION;
+
+    if (NULL == addrString) {
+        mRetransmitEndpointValid = false;
+        return OK;
+    }
+
+    struct in_addr saddr;
+    if(!inet_aton(addrString, &saddr)) {
+        return BAD_VALUE;
+    }
+
+    memset(&mRetransmitEndpoint, 0, sizeof(&mRetransmitEndpoint));
+    mRetransmitEndpoint.sin_family = AF_INET;
+    mRetransmitEndpoint.sin_addr   = saddr;
+    mRetransmitEndpoint.sin_port   = htons(port);
+    mRetransmitEndpointValid       = true;
+
+    return OK;
+}
+
 void MediaPlayer::notify(int msg, int ext1, int ext2, const Parcel *obj)
 {
     ALOGV("message received msg=%d, ext1=%d, ext2=%d", msg, ext1, ext2);
diff --git a/media/libmediaplayerservice/MediaPlayerService.cpp b/media/libmediaplayerservice/MediaPlayerService.cpp
index 764eddc..1e2abf0 100644
--- a/media/libmediaplayerservice/MediaPlayerService.cpp
+++ b/media/libmediaplayerservice/MediaPlayerService.cpp
@@ -492,6 +492,7 @@
     mStatus = NO_INIT;
     mAudioSessionId = audioSessionId;
     mUID = uid;
+    mRetransmitEndpointValid = false;
 
 #if CALLBACK_ANTAGONIZER
     ALOGD("create Antagonizer");
@@ -602,10 +603,6 @@
         return AAH_RX_PLAYER;
     }
 
-    if (!strncasecmp("aahTX://", url, 8)) {
-        return AAH_TX_PLAYER;
-    }
-
     // use MidiFile for MIDI extensions
     int lenURL = strlen(url);
     for (int i = 0; i < NELEM(FILE_EXTS); ++i) {
@@ -621,6 +618,44 @@
     return getDefaultPlayerType();
 }
 
+player_type MediaPlayerService::Client::getPlayerType(int fd,
+                                                      int64_t offset,
+                                                      int64_t length)
+{
+    // Until re-transmit functionality is added to the existing core android
+    // players, we use the special AAH TX player whenever we were configured
+    // for retransmission.
+    if (mRetransmitEndpointValid) {
+        return AAH_TX_PLAYER;
+    }
+
+    return android::getPlayerType(fd, offset, length);
+}
+
+player_type MediaPlayerService::Client::getPlayerType(const char* url)
+{
+    // Until re-transmit functionality is added to the existing core android
+    // players, we use the special AAH TX player whenever we were configured
+    // for retransmission.
+    if (mRetransmitEndpointValid) {
+        return AAH_TX_PLAYER;
+    }
+
+    return android::getPlayerType(url);
+}
+
+player_type MediaPlayerService::Client::getPlayerType(
+        const sp<IStreamSource> &source) {
+    // Until re-transmit functionality is added to the existing core android
+    // players, we use the special AAH TX player whenever we were configured
+    // for retransmission.
+    if (mRetransmitEndpointValid) {
+        return AAH_TX_PLAYER;
+    }
+
+    return NU_PLAYER;
+}
+
 static sp<MediaPlayerBase> createPlayer(player_type playerType, void* cookie,
         notify_callback_f notifyFunc)
 {
@@ -686,6 +721,49 @@
     return p;
 }
 
+sp<MediaPlayerBase> MediaPlayerService::Client::setDataSource_pre(
+        player_type playerType)
+{
+    ALOGV("player type = %d", playerType);
+
+    // create the right type of player
+    sp<MediaPlayerBase> p = createPlayer(playerType);
+    if (p == NULL) {
+        return p;
+    }
+
+    if (!p->hardwareOutput()) {
+        mAudioOutput = new AudioOutput(mAudioSessionId);
+        static_cast<MediaPlayerInterface*>(p.get())->setAudioSink(mAudioOutput);
+    }
+
+    return p;
+}
+
+void MediaPlayerService::Client::setDataSource_post(
+        const sp<MediaPlayerBase>& p,
+        status_t status)
+{
+    ALOGV(" setDataSource");
+    mStatus = status;
+    if (mStatus != OK) {
+        ALOGE("  error: %d", mStatus);
+        return;
+    }
+
+    // Set the re-transmission endpoint if one was chosen.
+    if (mRetransmitEndpointValid) {
+        mStatus = p->setRetransmitEndpoint(&mRetransmitEndpoint);
+        if (mStatus != NO_ERROR) {
+            ALOGE("setRetransmitEndpoint error: %d", mStatus);
+        }
+    }
+
+    if (mStatus == OK) {
+        mPlayer = p;
+    }
+}
+
 status_t MediaPlayerService::Client::setDataSource(
         const char *url, const KeyedVector<String8, String8> *headers)
 {
@@ -717,25 +795,12 @@
         return mStatus;
     } else {
         player_type playerType = getPlayerType(url);
-        ALOGV("player type = %d", playerType);
-
-        // create the right type of player
-        sp<MediaPlayerBase> p = createPlayer(playerType);
-        if (p == NULL) return NO_INIT;
-
-        if (!p->hardwareOutput()) {
-            mAudioOutput = new AudioOutput(mAudioSessionId);
-            static_cast<MediaPlayerInterface*>(p.get())->setAudioSink(mAudioOutput);
+        sp<MediaPlayerBase> p = setDataSource_pre(playerType);
+        if (p == NULL) {
+            return NO_INIT;
         }
 
-        // now set data source
-        ALOGV(" setDataSource");
-        mStatus = p->setDataSource(url, headers);
-        if (mStatus == NO_ERROR) {
-            mPlayer = p;
-        } else {
-            ALOGE("  error: %d", mStatus);
-        }
+        setDataSource_post(p, p->setDataSource(url, headers));
         return mStatus;
     }
 }
@@ -766,46 +831,34 @@
         ALOGV("calculated length = %lld", length);
     }
 
+    // Until re-transmit functionality is added to the existing core android
+    // players, we use the special AAH TX player whenever we were configured for
+    // retransmission.
     player_type playerType = getPlayerType(fd, offset, length);
-    ALOGV("player type = %d", playerType);
-
-    // create the right type of player
-    sp<MediaPlayerBase> p = createPlayer(playerType);
-    if (p == NULL) return NO_INIT;
-
-    if (!p->hardwareOutput()) {
-        mAudioOutput = new AudioOutput(mAudioSessionId);
-        static_cast<MediaPlayerInterface*>(p.get())->setAudioSink(mAudioOutput);
+    sp<MediaPlayerBase> p = setDataSource_pre(playerType);
+    if (p == NULL) {
+        return NO_INIT;
     }
 
     // now set data source
-    mStatus = p->setDataSource(fd, offset, length);
-    if (mStatus == NO_ERROR) mPlayer = p;
-
+    setDataSource_post(p, p->setDataSource(fd, offset, length));
     return mStatus;
 }
 
 status_t MediaPlayerService::Client::setDataSource(
         const sp<IStreamSource> &source) {
     // create the right type of player
-    sp<MediaPlayerBase> p = createPlayer(NU_PLAYER);
-
+    // Until re-transmit functionality is added to the existing core android
+    // players, we use the special AAH TX player whenever we were configured for
+    // retransmission.
+    player_type playerType = getPlayerType(source);
+    sp<MediaPlayerBase> p = setDataSource_pre(playerType);
     if (p == NULL) {
         return NO_INIT;
     }
 
-    if (!p->hardwareOutput()) {
-        mAudioOutput = new AudioOutput(mAudioSessionId);
-        static_cast<MediaPlayerInterface*>(p.get())->setAudioSink(mAudioOutput);
-    }
-
     // now set data source
-    mStatus = p->setDataSource(source);
-
-    if (mStatus == OK) {
-        mPlayer = p;
-    }
-
+    setDataSource_post(p, p->setDataSource(source));
     return mStatus;
 }
 
@@ -1026,6 +1079,7 @@
 status_t MediaPlayerService::Client::reset()
 {
     ALOGV("[%d] reset", mConnId);
+    mRetransmitEndpointValid = false;
     sp<MediaPlayerBase> p = getPlayer();
     if (p == 0) return UNKNOWN_ERROR;
     return p->reset();
@@ -1100,6 +1154,36 @@
     return p->getParameter(key, reply);
 }
 
+status_t MediaPlayerService::Client::setRetransmitEndpoint(
+        const struct sockaddr_in* endpoint) {
+
+    if (NULL != endpoint) {
+        uint32_t a = ntohl(endpoint->sin_addr.s_addr);
+        uint16_t p = ntohs(endpoint->sin_port);
+        ALOGV("[%d] setRetransmitEndpoint(%u.%u.%u.%u:%hu)", mConnId,
+                (a >> 24), (a >> 16) & 0xFF, (a >> 8) & 0xFF, (a & 0xFF), p);
+    } else {
+        ALOGV("[%d] setRetransmitEndpoint = <none>", mConnId);
+    }
+
+    sp<MediaPlayerBase> p = getPlayer();
+
+    // Right now, the only valid time to set a retransmit endpoint is before
+    // player selection has been made (since the presence or absence of a
+    // retransmit endpoint is going to determine which player is selected during
+    // setDataSource).
+    if (p != 0) return INVALID_OPERATION;
+
+    if (NULL != endpoint) {
+        mRetransmitEndpoint = *endpoint;
+        mRetransmitEndpointValid = true;
+    } else {
+        mRetransmitEndpointValid = false;
+    }
+
+    return NO_ERROR;
+}
+
 void MediaPlayerService::Client::notify(
         void* cookie, int msg, int ext1, int ext2, const Parcel *obj)
 {
diff --git a/media/libmediaplayerservice/MediaPlayerService.h b/media/libmediaplayerservice/MediaPlayerService.h
index 52af64d..53847ed 100644
--- a/media/libmediaplayerservice/MediaPlayerService.h
+++ b/media/libmediaplayerservice/MediaPlayerService.h
@@ -18,6 +18,8 @@
 #ifndef ANDROID_MEDIAPLAYERSERVICE_H
 #define ANDROID_MEDIAPLAYERSERVICE_H
 
+#include <arpa/inet.h>
+
 #include <utils/Log.h>
 #include <utils/threads.h>
 #include <utils/List.h>
@@ -276,6 +278,7 @@
         virtual status_t        attachAuxEffect(int effectId);
         virtual status_t        setParameter(int key, const Parcel &request);
         virtual status_t        getParameter(int key, Parcel *reply);
+        virtual status_t        setRetransmitEndpoint(const struct sockaddr_in* endpoint);
 
         sp<MediaPlayerBase>     createPlayer(player_type playerType);
 
@@ -287,6 +290,14 @@
 
         virtual status_t        setDataSource(const sp<IStreamSource> &source);
 
+        sp<MediaPlayerBase>     setDataSource_pre(player_type playerType);
+        void                    setDataSource_post(const sp<MediaPlayerBase>& p,
+                                                   status_t status);
+
+        player_type             getPlayerType(int fd, int64_t offset, int64_t length);
+        player_type             getPlayerType(const char* url);
+        player_type             getPlayerType(const sp<IStreamSource> &source);
+
         static  void            notify(void* cookie, int msg,
                                        int ext1, int ext2, const Parcel *obj);
 
@@ -338,6 +349,8 @@
                     uid_t                       mUID;
                     sp<ANativeWindow>           mConnectedWindow;
                     sp<IBinder>                 mConnectedWindowBinder;
+                    struct sockaddr_in          mRetransmitEndpoint;
+                    bool                        mRetransmitEndpointValid;
 
         // Metadata filters.
         media::Metadata::Filter mMetadataAllow;  // protected by mLock
diff --git a/media/libstagefright/ACodec.cpp b/media/libstagefright/ACodec.cpp
index 9a9d094..09e4e45 100644
--- a/media/libstagefright/ACodec.cpp
+++ b/media/libstagefright/ACodec.cpp
@@ -26,6 +26,7 @@
 #include <media/stagefright/foundation/ADebug.h>
 #include <media/stagefright/foundation/AMessage.h>
 
+#include <media/stagefright/MediaCodecList.h>
 #include <media/stagefright/MediaDefs.h>
 #include <media/stagefright/NativeWindowWrapper.h>
 #include <media/stagefright/OMXClient.h>
@@ -328,7 +329,8 @@
 ////////////////////////////////////////////////////////////////////////////////
 
 ACodec::ACodec()
-    : mNode(NULL),
+    : mQuirks(0),
+      mNode(NULL),
       mSentFormat(false),
       mIsEncoder(false),
       mShutdownInProgress(false) {
@@ -427,16 +429,12 @@
 
                 IOMX::buffer_id buffer;
 
-                if (!strncasecmp(
-                            mComponentName.c_str(), "OMX.TI.DUCATI1.VIDEO.", 21)) {
-                    if (portIndex == kPortIndexInput && i == 0) {
-                        // Only log this warning once per allocation round.
+                uint32_t requiresAllocateBufferBit =
+                    (portIndex == kPortIndexInput)
+                        ? OMXCodec::kRequiresAllocateBufferOnInputPorts
+                        : OMXCodec::kRequiresAllocateBufferOnOutputPorts;
 
-                        ALOGW("OMX.TI.DUCATI1.VIDEO.* require the use of "
-                             "OMX_AllocateBuffer instead of the preferred "
-                             "OMX_UseBuffer. Vendor must fix this.");
-                    }
-
+                if (mQuirks & requiresAllocateBufferBit) {
                     err = mOMX->allocateBufferWithBackup(
                             mNode, portIndex, mem, &buffer);
                 } else {
@@ -2588,12 +2586,19 @@
     sp<IOMX> omx = client.interface();
 
     Vector<String8> matchingCodecs;
+    Vector<uint32_t> matchingCodecQuirks;
 
     AString mime;
 
     AString componentName;
+    uint32_t quirks;
     if (msg->findString("componentName", &componentName)) {
         matchingCodecs.push_back(String8(componentName.c_str()));
+
+        if (!OMXCodec::findCodecQuirks(componentName.c_str(), &quirks)) {
+            quirks = 0;
+        }
+        matchingCodecQuirks.push_back(quirks);
     } else {
         CHECK(msg->findString("mime", &mime));
 
@@ -2607,7 +2612,8 @@
                 encoder, // createEncoder
                 NULL,  // matchComponentName
                 0,     // flags
-                &matchingCodecs);
+                &matchingCodecs,
+                &matchingCodecQuirks);
     }
 
     sp<CodecObserver> observer = new CodecObserver;
@@ -2616,6 +2622,7 @@
     for (size_t matchIndex = 0; matchIndex < matchingCodecs.size();
             ++matchIndex) {
         componentName = matchingCodecs.itemAt(matchIndex).string();
+        quirks = matchingCodecQuirks.itemAt(matchIndex);
 
         pid_t tid = androidGetTid();
         int prevPriority = androidGetThreadPriority(tid);
@@ -2646,6 +2653,7 @@
     observer->setNotificationMessage(notify);
 
     mCodec->mComponentName = componentName;
+    mCodec->mQuirks = quirks;
     mCodec->mOMX = omx;
     mCodec->mNode = node;
 
@@ -2692,6 +2700,7 @@
         mCodec->mNativeWindow.clear();
         mCodec->mNode = NULL;
         mCodec->mOMX.clear();
+        mCodec->mQuirks = 0;
         mCodec->mComponentName.clear();
 
         mCodec->changeState(mCodec->mUninitializedState);
diff --git a/media/libstagefright/Android.mk b/media/libstagefright/Android.mk
index 95bcada..21d6866 100644
--- a/media/libstagefright/Android.mk
+++ b/media/libstagefright/Android.mk
@@ -30,6 +30,7 @@
         MediaBuffer.cpp                   \
         MediaBufferGroup.cpp              \
         MediaCodec.cpp                    \
+        MediaCodecList.cpp                \
         MediaDefs.cpp                     \
         MediaExtractor.cpp                \
         MediaSource.cpp                   \
@@ -59,31 +60,33 @@
 	$(JNI_H_INCLUDE) \
         $(TOP)/frameworks/base/include/media/stagefright/openmax \
         $(TOP)/frameworks/base/include/media/stagefright/timedtext \
+        $(TOP)/external/expat/lib \
         $(TOP)/external/flac/include \
         $(TOP)/external/tremolo \
         $(TOP)/external/openssl/include \
 
 LOCAL_SHARED_LIBRARIES := \
         libbinder \
-        libmedia \
-        libutils \
-        libcutils \
-        libui \
-        libsonivox \
-        libvorbisidec \
-        libstagefright_yuv \
         libcamera_client \
-        libdrmframework \
-        libcrypto \
-        libssl \
-        libgui \
-        libstagefright_omx \
-        liblog \
-        libicuuc \
-        libicui18n \
-        libz \
-        libdl \
         libchromium_net \
+        libcrypto \
+        libcutils \
+        libdl \
+        libdrmframework \
+        libexpat \
+        libgui \
+        libicui18n \
+        libicuuc \
+        liblog \
+        libmedia \
+        libsonivox \
+        libssl \
+        libstagefright_omx \
+        libstagefright_yuv \
+        libui \
+        libutils \
+        libvorbisidec \
+        libz \
 
 LOCAL_STATIC_LIBRARIES := \
         libstagefright_color_conversion \
diff --git a/media/libstagefright/MediaCodecList.cpp b/media/libstagefright/MediaCodecList.cpp
new file mode 100644
index 0000000..6b64e21
--- /dev/null
+++ b/media/libstagefright/MediaCodecList.cpp
@@ -0,0 +1,475 @@
+/*
+ * Copyright 2012, 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.
+ */
+
+//#define LOG_NDEBUG 0
+#define LOG_TAG "MediaCodecList"
+#include <utils/Log.h>
+
+#include <media/stagefright/MediaCodecList.h>
+
+#include <media/stagefright/foundation/ADebug.h>
+#include <media/stagefright/MediaErrors.h>
+#include <utils/threads.h>
+
+#include <expat.h>
+
+namespace android {
+
+static Mutex sInitMutex;
+
+// static
+MediaCodecList *MediaCodecList::sCodecList;
+
+// static
+const MediaCodecList *MediaCodecList::getInstance() {
+    Mutex::Autolock autoLock(sInitMutex);
+
+    if (sCodecList == NULL) {
+        sCodecList = new MediaCodecList;
+    }
+
+    return sCodecList->initCheck() == OK ? sCodecList : NULL;
+}
+
+MediaCodecList::MediaCodecList()
+    : mInitCheck(NO_INIT) {
+    FILE *file = fopen("/etc/media_codecs.xml", "r");
+
+    if (file == NULL) {
+        ALOGW("unable to open media codecs configuration xml file.");
+        return;
+    }
+
+    parseXMLFile(file);
+
+    if (mInitCheck == OK) {
+        // These are currently still used by the video editing suite.
+
+        addMediaCodec(true /* encoder */, "AACEncoder", "audio/mp4a-latm");
+        addMediaCodec(true /* encoder */, "AVCEncoder", "video/avc");
+
+        addMediaCodec(true /* encoder */, "M4vH263Encoder");
+        addType("video/3gpp");
+        addType("video/mp4v-es");
+    }
+
+#if 0
+    for (size_t i = 0; i < mCodecInfos.size(); ++i) {
+        const CodecInfo &info = mCodecInfos.itemAt(i);
+
+        AString line = info.mName;
+        line.append(" supports ");
+        for (size_t j = 0; j < mTypes.size(); ++j) {
+            uint32_t value = mTypes.valueAt(j);
+
+            if (info.mTypes & (1ul << value)) {
+                line.append(mTypes.keyAt(j));
+                line.append(" ");
+            }
+        }
+
+        ALOGI("%s", line.c_str());
+    }
+#endif
+
+    fclose(file);
+    file = NULL;
+}
+
+MediaCodecList::~MediaCodecList() {
+}
+
+status_t MediaCodecList::initCheck() const {
+    return mInitCheck;
+}
+
+void MediaCodecList::parseXMLFile(FILE *file) {
+    mInitCheck = OK;
+    mCurrentSection = SECTION_TOPLEVEL;
+    mDepth = 0;
+
+    XML_Parser parser = ::XML_ParserCreate(NULL);
+    CHECK(parser != NULL);
+
+    ::XML_SetUserData(parser, this);
+    ::XML_SetElementHandler(
+            parser, StartElementHandlerWrapper, EndElementHandlerWrapper);
+
+    const int BUFF_SIZE = 512;
+    while (mInitCheck == OK) {
+        void *buff = ::XML_GetBuffer(parser, BUFF_SIZE);
+        if (buff == NULL) {
+            ALOGE("failed to in call to XML_GetBuffer()");
+            mInitCheck = UNKNOWN_ERROR;
+            break;
+        }
+
+        int bytes_read = ::fread(buff, 1, BUFF_SIZE, file);
+        if (bytes_read < 0) {
+            ALOGE("failed in call to read");
+            mInitCheck = ERROR_IO;
+            break;
+        }
+
+        if (::XML_ParseBuffer(parser, bytes_read, bytes_read == 0)
+                != XML_STATUS_OK) {
+            mInitCheck = ERROR_MALFORMED;
+            break;
+        }
+
+        if (bytes_read == 0) {
+            break;
+        }
+    }
+
+    ::XML_ParserFree(parser);
+
+    if (mInitCheck == OK) {
+        for (size_t i = mCodecInfos.size(); i-- > 0;) {
+            CodecInfo *info = &mCodecInfos.editItemAt(i);
+
+            if (info->mTypes == 0) {
+                // No types supported by this component???
+
+                ALOGW("Component %s does not support any type of media?",
+                      info->mName.c_str());
+
+                mCodecInfos.removeAt(i);
+            }
+        }
+    }
+
+    if (mInitCheck != OK) {
+        mCodecInfos.clear();
+        mCodecQuirks.clear();
+    }
+}
+
+// static
+void MediaCodecList::StartElementHandlerWrapper(
+        void *me, const char *name, const char **attrs) {
+    static_cast<MediaCodecList *>(me)->startElementHandler(name, attrs);
+}
+
+// static
+void MediaCodecList::EndElementHandlerWrapper(void *me, const char *name) {
+    static_cast<MediaCodecList *>(me)->endElementHandler(name);
+}
+
+void MediaCodecList::startElementHandler(
+        const char *name, const char **attrs) {
+    if (mInitCheck != OK) {
+        return;
+    }
+
+    switch (mCurrentSection) {
+        case SECTION_TOPLEVEL:
+        {
+            if (!strcmp(name, "Decoders")) {
+                mCurrentSection = SECTION_DECODERS;
+            } else if (!strcmp(name, "Encoders")) {
+                mCurrentSection = SECTION_ENCODERS;
+            }
+            break;
+        }
+
+        case SECTION_DECODERS:
+        {
+            if (!strcmp(name, "MediaCodec")) {
+                mInitCheck =
+                    addMediaCodecFromAttributes(false /* encoder */, attrs);
+
+                mCurrentSection = SECTION_DECODER;
+            }
+            break;
+        }
+
+        case SECTION_ENCODERS:
+        {
+            if (!strcmp(name, "MediaCodec")) {
+                mInitCheck =
+                    addMediaCodecFromAttributes(true /* encoder */, attrs);
+
+                mCurrentSection = SECTION_ENCODER;
+            }
+            break;
+        }
+
+        case SECTION_DECODER:
+        case SECTION_ENCODER:
+        {
+            if (!strcmp(name, "Quirk")) {
+                mInitCheck = addQuirk(attrs);
+            } else if (!strcmp(name, "Type")) {
+                mInitCheck = addTypeFromAttributes(attrs);
+            }
+            break;
+        }
+
+        default:
+            break;
+    }
+
+    ++mDepth;
+}
+
+void MediaCodecList::endElementHandler(const char *name) {
+    if (mInitCheck != OK) {
+        return;
+    }
+
+    switch (mCurrentSection) {
+        case SECTION_DECODERS:
+        {
+            if (!strcmp(name, "Decoders")) {
+                mCurrentSection = SECTION_TOPLEVEL;
+            }
+            break;
+        }
+
+        case SECTION_ENCODERS:
+        {
+            if (!strcmp(name, "Encoders")) {
+                mCurrentSection = SECTION_TOPLEVEL;
+            }
+            break;
+        }
+
+        case SECTION_DECODER:
+        {
+            if (!strcmp(name, "MediaCodec")) {
+                mCurrentSection = SECTION_DECODERS;
+            }
+            break;
+        }
+
+        case SECTION_ENCODER:
+        {
+            if (!strcmp(name, "MediaCodec")) {
+                mCurrentSection = SECTION_ENCODERS;
+            }
+            break;
+        }
+
+        default:
+            break;
+    }
+
+    --mDepth;
+}
+
+status_t MediaCodecList::addMediaCodecFromAttributes(
+        bool encoder, const char **attrs) {
+    const char *name = NULL;
+    const char *type = NULL;
+
+    size_t i = 0;
+    while (attrs[i] != NULL) {
+        if (!strcmp(attrs[i], "name")) {
+            if (attrs[i + 1] == NULL) {
+                return -EINVAL;
+            }
+            name = attrs[i + 1];
+            ++i;
+        } else if (!strcmp(attrs[i], "type")) {
+            if (attrs[i + 1] == NULL) {
+                return -EINVAL;
+            }
+            type = attrs[i + 1];
+            ++i;
+        } else {
+            return -EINVAL;
+        }
+
+        ++i;
+    }
+
+    if (name == NULL) {
+        return -EINVAL;
+    }
+
+    addMediaCodec(encoder, name, type);
+
+    return OK;
+}
+
+void MediaCodecList::addMediaCodec(
+        bool encoder, const char *name, const char *type) {
+    mCodecInfos.push();
+    CodecInfo *info = &mCodecInfos.editItemAt(mCodecInfos.size() - 1);
+    info->mName = name;
+    info->mIsEncoder = encoder;
+    info->mTypes = 0;
+    info->mQuirks = 0;
+
+    if (type != NULL) {
+        addType(type);
+    }
+}
+
+status_t MediaCodecList::addQuirk(const char **attrs) {
+    const char *name = NULL;
+
+    size_t i = 0;
+    while (attrs[i] != NULL) {
+        if (!strcmp(attrs[i], "name")) {
+            if (attrs[i + 1] == NULL) {
+                return -EINVAL;
+            }
+            name = attrs[i + 1];
+            ++i;
+        } else {
+            return -EINVAL;
+        }
+
+        ++i;
+    }
+
+    if (name == NULL) {
+        return -EINVAL;
+    }
+
+    uint32_t bit;
+    ssize_t index = mCodecQuirks.indexOfKey(name);
+    if (index < 0) {
+        bit = mCodecQuirks.size();
+
+        if (bit == 32) {
+            ALOGW("Too many distinct quirk names in configuration.");
+            return OK;
+        }
+
+        mCodecQuirks.add(name, bit);
+    } else {
+        bit = mCodecQuirks.valueAt(index);
+    }
+
+    CodecInfo *info = &mCodecInfos.editItemAt(mCodecInfos.size() - 1);
+    info->mQuirks |= 1ul << bit;
+
+    return OK;
+}
+
+status_t MediaCodecList::addTypeFromAttributes(const char **attrs) {
+    const char *name = NULL;
+
+    size_t i = 0;
+    while (attrs[i] != NULL) {
+        if (!strcmp(attrs[i], "name")) {
+            if (attrs[i + 1] == NULL) {
+                return -EINVAL;
+            }
+            name = attrs[i + 1];
+            ++i;
+        } else {
+            return -EINVAL;
+        }
+
+        ++i;
+    }
+
+    if (name == NULL) {
+        return -EINVAL;
+    }
+
+    addType(name);
+
+    return OK;
+}
+
+void MediaCodecList::addType(const char *name) {
+    uint32_t bit;
+    ssize_t index = mTypes.indexOfKey(name);
+    if (index < 0) {
+        bit = mTypes.size();
+
+        if (bit == 32) {
+            ALOGW("Too many distinct type names in configuration.");
+            return;
+        }
+
+        mTypes.add(name, bit);
+    } else {
+        bit = mTypes.valueAt(index);
+    }
+
+    CodecInfo *info = &mCodecInfos.editItemAt(mCodecInfos.size() - 1);
+    info->mTypes |= 1ul << bit;
+}
+
+ssize_t MediaCodecList::findCodecByType(
+        const char *type, bool encoder, size_t startIndex) const {
+    ssize_t typeIndex = mTypes.indexOfKey(type);
+
+    if (typeIndex < 0) {
+        return -ENOENT;
+    }
+
+    uint32_t typeMask = 1ul << mTypes.valueAt(typeIndex);
+
+    while (startIndex < mCodecInfos.size()) {
+        const CodecInfo &info = mCodecInfos.itemAt(startIndex);
+
+        if (info.mIsEncoder == encoder && (info.mTypes & typeMask)) {
+            return startIndex;
+        }
+
+        ++startIndex;
+    }
+
+    return -ENOENT;
+}
+
+ssize_t MediaCodecList::findCodecByName(const char *name) const {
+    for (size_t i = 0; i < mCodecInfos.size(); ++i) {
+        const CodecInfo &info = mCodecInfos.itemAt(i);
+
+        if (info.mName == name) {
+            return i;
+        }
+    }
+
+    return -ENOENT;
+}
+
+const char *MediaCodecList::getCodecName(size_t index) const {
+    if (index >= mCodecInfos.size()) {
+        return NULL;
+    }
+
+    const CodecInfo &info = mCodecInfos.itemAt(index);
+    return info.mName.c_str();
+}
+
+bool MediaCodecList::codecHasQuirk(
+        size_t index, const char *quirkName) const {
+    if (index >= mCodecInfos.size()) {
+        return NULL;
+    }
+
+    const CodecInfo &info = mCodecInfos.itemAt(index);
+
+    if (info.mQuirks != 0) {
+        ssize_t index = mCodecQuirks.indexOfKey(quirkName);
+        if (index >= 0 && info.mQuirks & (1ul << mCodecQuirks.valueAt(index))) {
+            return true;
+        }
+    }
+
+    return false;
+}
+
+}  // namespace android
diff --git a/media/libstagefright/OMXCodec.cpp b/media/libstagefright/OMXCodec.cpp
index 1325462..966416e 100755
--- a/media/libstagefright/OMXCodec.cpp
+++ b/media/libstagefright/OMXCodec.cpp
@@ -33,6 +33,7 @@
 #include <media/stagefright/MediaBuffer.h>
 #include <media/stagefright/MediaBufferGroup.h>
 #include <media/stagefright/MediaDefs.h>
+#include <media/stagefright/MediaCodecList.h>
 #include <media/stagefright/MediaExtractor.h>
 #include <media/stagefright/MetaData.h>
 #include <media/stagefright/OMXCodec.h>
@@ -57,11 +58,6 @@
 // component in question is buggy or not.
 const static uint32_t kMaxColorFormatSupported = 1000;
 
-struct CodecInfo {
-    const char *mime;
-    const char *codec;
-};
-
 #define FACTORY_CREATE_ENCODER(name) \
 static sp<MediaSource> Make##name(const sp<MediaSource> &source, const sp<MetaData> &meta) { \
     return new name(source, meta); \
@@ -96,83 +92,8 @@
     return NULL;
 }
 
+#undef FACTORY_CREATE_ENCODER
 #undef FACTORY_REF
-#undef FACTORY_CREATE
-
-static const CodecInfo kDecoderInfo[] = {
-    { MEDIA_MIMETYPE_IMAGE_JPEG, "OMX.TI.JPEG.decode" },
-//    { MEDIA_MIMETYPE_AUDIO_MPEG, "OMX.TI.MP3.decode" },
-    { MEDIA_MIMETYPE_AUDIO_MPEG, "OMX.google.mp3.decoder" },
-    { MEDIA_MIMETYPE_AUDIO_MPEG_LAYER_II, "OMX.Nvidia.mp2.decoder" },
-//    { MEDIA_MIMETYPE_AUDIO_AMR_NB, "OMX.TI.AMR.decode" },
-//    { MEDIA_MIMETYPE_AUDIO_AMR_NB, "OMX.Nvidia.amr.decoder" },
-    { MEDIA_MIMETYPE_AUDIO_AMR_NB, "OMX.google.amrnb.decoder" },
-//    { MEDIA_MIMETYPE_AUDIO_AMR_NB, "OMX.Nvidia.amrwb.decoder" },
-    { MEDIA_MIMETYPE_AUDIO_AMR_WB, "OMX.TI.WBAMR.decode" },
-    { MEDIA_MIMETYPE_AUDIO_AMR_WB, "OMX.google.amrwb.decoder" },
-//    { MEDIA_MIMETYPE_AUDIO_AAC, "OMX.Nvidia.aac.decoder" },
-    { MEDIA_MIMETYPE_AUDIO_AAC, "OMX.TI.AAC.decode" },
-    { MEDIA_MIMETYPE_AUDIO_AAC, "OMX.google.aac.decoder" },
-    { MEDIA_MIMETYPE_AUDIO_G711_ALAW, "OMX.google.g711.alaw.decoder" },
-    { MEDIA_MIMETYPE_AUDIO_G711_MLAW, "OMX.google.g711.mlaw.decoder" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.TI.DUCATI1.VIDEO.DECODER" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.Nvidia.mp4.decode" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.qcom.7x30.video.decoder.mpeg4" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.qcom.video.decoder.mpeg4" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.TI.Video.Decoder" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.SEC.MPEG4.Decoder" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.google.mpeg4.decoder" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.TI.DUCATI1.VIDEO.DECODER" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.Nvidia.h263.decode" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.qcom.7x30.video.decoder.h263" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.qcom.video.decoder.h263" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.SEC.H263.Decoder" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.google.h263.decoder" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.TI.DUCATI1.VIDEO.DECODER" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.Nvidia.h264.decode" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.qcom.7x30.video.decoder.avc" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.qcom.video.decoder.avc" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.TI.Video.Decoder" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.SEC.AVC.Decoder" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.google.h264.decoder" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.google.avc.decoder" },
-    { MEDIA_MIMETYPE_AUDIO_VORBIS, "OMX.google.vorbis.decoder" },
-    { MEDIA_MIMETYPE_VIDEO_VPX, "OMX.google.vpx.decoder" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG2, "OMX.Nvidia.mpeg2v.decode" },
-};
-
-static const CodecInfo kEncoderInfo[] = {
-    { MEDIA_MIMETYPE_AUDIO_AMR_NB, "OMX.TI.AMR.encode" },
-    { MEDIA_MIMETYPE_AUDIO_AMR_NB, "OMX.google.amrnb.encoder" },
-    { MEDIA_MIMETYPE_AUDIO_AMR_WB, "OMX.TI.WBAMR.encode" },
-    { MEDIA_MIMETYPE_AUDIO_AMR_WB, "OMX.google.amrwb.encoder" },
-    { MEDIA_MIMETYPE_AUDIO_AAC, "OMX.TI.AAC.encode" },
-    { MEDIA_MIMETYPE_AUDIO_AAC, "OMX.google.aac.encoder" },
-    { MEDIA_MIMETYPE_AUDIO_AAC, "AACEncoder" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.TI.DUCATI1.VIDEO.MPEG4E" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.qcom.7x30.video.encoder.mpeg4" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.qcom.video.encoder.mpeg4" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.TI.Video.encoder" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.Nvidia.mp4.encoder" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "OMX.SEC.MPEG4.Encoder" },
-    { MEDIA_MIMETYPE_VIDEO_MPEG4, "M4vH263Encoder" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.TI.DUCATI1.VIDEO.MPEG4E" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.qcom.7x30.video.encoder.h263" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.qcom.video.encoder.h263" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.TI.Video.encoder" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.Nvidia.h263.encoder" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "OMX.SEC.H263.Encoder" },
-    { MEDIA_MIMETYPE_VIDEO_H263, "M4vH263Encoder" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.TI.DUCATI1.VIDEO.H264E" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.qcom.7x30.video.encoder.avc" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.qcom.video.encoder.avc" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.TI.Video.encoder" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.Nvidia.h264.encoder" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "OMX.SEC.AVC.Encoder" },
-    { MEDIA_MIMETYPE_VIDEO_AVC, "AVCEncoder" },
-};
-
-#undef OPTIONAL
 
 #define CODEC_LOGI(x, ...) ALOGI("[%s] "x, mComponentName, ##__VA_ARGS__)
 #define CODEC_LOGV(x, ...) ALOGV("[%s] "x, mComponentName, ##__VA_ARGS__)
@@ -207,22 +128,6 @@
     OMXCodecObserver &operator=(const OMXCodecObserver &);
 };
 
-static const char *GetCodec(const CodecInfo *info, size_t numInfos,
-                            const char *mime, int index) {
-    CHECK(index >= 0);
-    for(size_t i = 0; i < numInfos; ++i) {
-        if (!strcasecmp(mime, info[i].mime)) {
-            if (index == 0) {
-                return info[i].codec;
-            }
-
-            --index;
-        }
-    }
-
-    return NULL;
-}
-
 template<class T>
 static void InitOMXParams(T *params) {
     params->nSize = sizeof(T);
@@ -278,119 +183,36 @@
 }
 
 // static
-uint32_t OMXCodec::getComponentQuirks(
-        const char *componentName, bool isEncoder) {
-    uint32_t quirks = 0;
-
-    if (!strcmp(componentName, "OMX.Nvidia.amr.decoder") ||
-         !strcmp(componentName, "OMX.Nvidia.amrwb.decoder") ||
-         !strcmp(componentName, "OMX.Nvidia.aac.decoder") ||
-         !strcmp(componentName, "OMX.Nvidia.mp3.decoder")) {
-        quirks |= kDecoderLiesAboutNumberOfChannels;
-    }
-
-    if (!strcmp(componentName, "OMX.TI.MP3.decode")) {
-        quirks |= kNeedsFlushBeforeDisable;
-        quirks |= kDecoderLiesAboutNumberOfChannels;
-    }
-    if (!strcmp(componentName, "OMX.TI.AAC.decode")) {
-        quirks |= kNeedsFlushBeforeDisable;
-        quirks |= kRequiresFlushCompleteEmulation;
-        quirks |= kSupportsMultipleFramesPerInputBuffer;
-    }
-    if (!strncmp(componentName, "OMX.qcom.video.encoder.", 23)) {
-        quirks |= kRequiresLoadedToIdleAfterAllocation;
-        quirks |= kRequiresAllocateBufferOnInputPorts;
-        quirks |= kRequiresAllocateBufferOnOutputPorts;
-        if (!strncmp(componentName, "OMX.qcom.video.encoder.avc", 26)) {
-
-            // The AVC encoder advertises the size of output buffers
-            // based on the input video resolution and assumes
-            // the worst/least compression ratio is 0.5. It is found that
-            // sometimes, the output buffer size is larger than
-            // size advertised by the encoder.
-            quirks |= kRequiresLargerEncoderOutputBuffer;
-        }
-    }
-    if (!strncmp(componentName, "OMX.qcom.7x30.video.encoder.", 28)) {
-    }
-    if (!strncmp(componentName, "OMX.qcom.video.decoder.", 23)) {
-        quirks |= kRequiresAllocateBufferOnOutputPorts;
-        quirks |= kDefersOutputBufferAllocation;
-    }
-    if (!strncmp(componentName, "OMX.qcom.7x30.video.decoder.", 28)) {
-        quirks |= kRequiresAllocateBufferOnInputPorts;
-        quirks |= kRequiresAllocateBufferOnOutputPorts;
-        quirks |= kDefersOutputBufferAllocation;
-    }
-
-    if (!strcmp(componentName, "OMX.TI.DUCATI1.VIDEO.DECODER")) {
-        quirks |= kRequiresAllocateBufferOnInputPorts;
-        quirks |= kRequiresAllocateBufferOnOutputPorts;
-    }
-
-    // FIXME:
-    // Remove the quirks after the work is done.
-    else if (!strcmp(componentName, "OMX.TI.DUCATI1.VIDEO.MPEG4E") ||
-             !strcmp(componentName, "OMX.TI.DUCATI1.VIDEO.H264E")) {
-
-        quirks |= kRequiresAllocateBufferOnInputPorts;
-        quirks |= kRequiresAllocateBufferOnOutputPorts;
-    }
-    else if (!strncmp(componentName, "OMX.TI.", 7)) {
-        // Apparently I must not use OMX_UseBuffer on either input or
-        // output ports on any of the TI components or quote:
-        // "(I) may have unexpected problem (sic) which can be timing related
-        //  and hard to reproduce."
-
-        quirks |= kRequiresAllocateBufferOnInputPorts;
-        quirks |= kRequiresAllocateBufferOnOutputPorts;
-        if (!strncmp(componentName, "OMX.TI.Video.encoder", 20)) {
-            quirks |= kAvoidMemcopyInputRecordingFrames;
-        }
-    }
-
-    if (!strcmp(componentName, "OMX.TI.Video.Decoder")) {
-        quirks |= kInputBufferSizesAreBogus;
-    }
-
-    if (!strncmp(componentName, "OMX.SEC.", 8) && !isEncoder) {
-        // These output buffers contain no video data, just some
-        // opaque information that allows the overlay to display their
-        // contents.
-        quirks |= kOutputBuffersAreUnreadable;
-    }
-
-    return quirks;
-}
-
-// static
 void OMXCodec::findMatchingCodecs(
         const char *mime,
         bool createEncoder, const char *matchComponentName,
         uint32_t flags,
-        Vector<String8> *matchingCodecs) {
+        Vector<String8> *matchingCodecs,
+        Vector<uint32_t> *matchingCodecQuirks) {
     matchingCodecs->clear();
 
-    for (int index = 0;; ++index) {
-        const char *componentName;
+    if (matchingCodecQuirks) {
+        matchingCodecQuirks->clear();
+    }
 
-        if (createEncoder) {
-            componentName = GetCodec(
-                    kEncoderInfo,
-                    sizeof(kEncoderInfo) / sizeof(kEncoderInfo[0]),
-                    mime, index);
-        } else {
-            componentName = GetCodec(
-                    kDecoderInfo,
-                    sizeof(kDecoderInfo) / sizeof(kDecoderInfo[0]),
-                    mime, index);
-        }
+    const MediaCodecList *list = MediaCodecList::getInstance();
+    if (list == NULL) {
+        return;
+    }
 
-        if (!componentName) {
+    size_t index = 0;
+    for (;;) {
+        ssize_t matchIndex =
+            list->findCodecByType(mime, createEncoder, index);
+
+        if (matchIndex < 0) {
             break;
         }
 
+        index = matchIndex + 1;
+
+        const char *componentName = list->getCodecName(matchIndex);
+
         // If a specific codec is requested, skip the non-matching ones.
         if (matchComponentName && strcmp(componentName, matchComponentName)) {
             continue;
@@ -405,6 +227,10 @@
             (!(flags & (kSoftwareCodecsOnly | kHardwareCodecsOnly)))) {
 
             matchingCodecs->push(String8(componentName));
+
+            if (matchingCodecQuirks) {
+                matchingCodecQuirks->push(getComponentQuirks(list, matchIndex));
+            }
         }
     }
 
@@ -414,6 +240,45 @@
 }
 
 // static
+uint32_t OMXCodec::getComponentQuirks(
+        const MediaCodecList *list, size_t index) {
+    uint32_t quirks = 0;
+    if (list->codecHasQuirk(
+                index, "requires-allocate-on-input-ports")) {
+        quirks |= kRequiresAllocateBufferOnInputPorts;
+    }
+    if (list->codecHasQuirk(
+                index, "requires-allocate-on-output-ports")) {
+        quirks |= kRequiresAllocateBufferOnOutputPorts;
+    }
+    if (list->codecHasQuirk(
+                index, "output-buffers-are-unreadable")) {
+        quirks |= kOutputBuffersAreUnreadable;
+    }
+
+    return quirks;
+}
+
+// static
+bool OMXCodec::findCodecQuirks(const char *componentName, uint32_t *quirks) {
+    const MediaCodecList *list = MediaCodecList::getInstance();
+
+    if (list == NULL) {
+        return false;
+    }
+
+    ssize_t index = list->findCodecByName(componentName);
+
+    if (index < 0) {
+        return false;
+    }
+
+    *quirks = getComponentQuirks(list, index);
+
+    return true;
+}
+
+// static
 sp<MediaSource> OMXCodec::Create(
         const sp<IOMX> &omx,
         const sp<MetaData> &meta, bool createEncoder,
@@ -435,8 +300,10 @@
     CHECK(success);
 
     Vector<String8> matchingCodecs;
+    Vector<uint32_t> matchingCodecQuirks;
     findMatchingCodecs(
-            mime, createEncoder, matchComponentName, flags, &matchingCodecs);
+            mime, createEncoder, matchComponentName, flags,
+            &matchingCodecs, &matchingCodecQuirks);
 
     if (matchingCodecs.isEmpty()) {
         return NULL;
@@ -447,6 +314,7 @@
 
     for (size_t i = 0; i < matchingCodecs.size(); ++i) {
         const char *componentNameBase = matchingCodecs[i].string();
+        uint32_t quirks = matchingCodecQuirks[i];
         const char *componentName = componentNameBase;
 
         AString tmp;
@@ -470,8 +338,6 @@
 
         ALOGV("Attempting to allocate OMX node '%s'", componentName);
 
-        uint32_t quirks = getComponentQuirks(componentNameBase, createEncoder);
-
         if (!createEncoder
                 && (quirks & kOutputBuffersAreUnreadable)
                 && (flags & kClientNeedsFramebuffer)) {
@@ -627,16 +493,6 @@
             CODEC_LOGI(
                     "AVC profile = %u (%s), level = %u",
                     profile, AVCProfileToString(profile), level);
-
-            if (!strcmp(mComponentName, "OMX.TI.Video.Decoder")
-                && (profile != kAVCProfileBaseline || level > 30)) {
-                // This stream exceeds the decoder's capabilities. The decoder
-                // does not handle this gracefully and would clobber the heap
-                // and wreak havoc instead...
-
-                ALOGE("Profile and/or level exceed the decoder's capabilities.");
-                return ERROR_UNSUPPORTED;
-            }
         } else if (meta->findData(kKeyVorbisInfo, &type, &data, &size)) {
             addCodecSpecificData(data, size);
 
@@ -692,40 +548,11 @@
         }
     }
 
-    if (!strcasecmp(mMIME, MEDIA_MIMETYPE_IMAGE_JPEG)
-        && !strcmp(mComponentName, "OMX.TI.JPEG.decode")) {
-        OMX_COLOR_FORMATTYPE format =
-            OMX_COLOR_Format32bitARGB8888;
-            // OMX_COLOR_FormatYUV420PackedPlanar;
-            // OMX_COLOR_FormatCbYCrY;
-            // OMX_COLOR_FormatYUV411Planar;
-
-        int32_t width, height;
-        bool success = meta->findInt32(kKeyWidth, &width);
-        success = success && meta->findInt32(kKeyHeight, &height);
-
-        int32_t compressedSize;
-        success = success && meta->findInt32(
-                kKeyMaxInputSize, &compressedSize);
-
-        CHECK(success);
-        CHECK(compressedSize > 0);
-
-        setImageOutputFormat(format, width, height);
-        setJPEGInputFormat(width, height, (OMX_U32)compressedSize);
-    }
-
     int32_t maxInputSize;
     if (meta->findInt32(kKeyMaxInputSize, &maxInputSize)) {
         setMinBufferSize(kPortIndexInput, (OMX_U32)maxInputSize);
     }
 
-    if (!strcmp(mComponentName, "OMX.TI.AMR.encode")
-        || !strcmp(mComponentName, "OMX.TI.WBAMR.encode")
-        || !strcmp(mComponentName, "OMX.TI.AAC.encode")) {
-        setMinBufferSize(kPortIndexOutput, 8192);  // XXX
-    }
-
     initOutputFormat(meta);
 
     if ((mFlags & kClientNeedsFramebuffer)
@@ -829,21 +656,6 @@
              index, format.eCompressionFormat, format.eColorFormat);
 #endif
 
-        if (!strcmp("OMX.TI.Video.encoder", mComponentName)) {
-            if (portIndex == kPortIndexInput
-                    && colorFormat == format.eColorFormat) {
-                // eCompressionFormat does not seem right.
-                found = true;
-                break;
-            }
-            if (portIndex == kPortIndexOutput
-                    && compressionFormat == format.eCompressionFormat) {
-                // eColorFormat does not seem right.
-                found = true;
-                break;
-            }
-        }
-
         if (format.eCompressionFormat == compressionFormat
                 && format.eColorFormat == colorFormat) {
             found = true;
@@ -906,13 +718,8 @@
     int32_t targetColorFormat;
     if (meta->findInt32(kKeyColorFormat, &targetColorFormat)) {
         *colorFormat = (OMX_COLOR_FORMATTYPE) targetColorFormat;
-    } else {
-        if (!strcasecmp("OMX.TI.Video.encoder", mComponentName)) {
-            *colorFormat = OMX_COLOR_FormatYCbYCr;
-        }
     }
 
-
     // Check whether the target color format is supported.
     return isColorFormatSupported(*colorFormat, kPortIndexInput);
 }
@@ -3326,13 +3133,6 @@
 
     info->mStatus = OWNED_BY_COMPONENT;
 
-    // This component does not ever signal the EOS flag on output buffers,
-    // Thanks for nothing.
-    if (mSignalledEOS && !strcmp(mComponentName, "OMX.TI.Video.encoder")) {
-        mNoMoreOutputData = true;
-        mBufferFilled.signal();
-    }
-
     return true;
 }
 
diff --git a/media/libstagefright/codecs/aacenc/Android.mk b/media/libstagefright/codecs/aacenc/Android.mk
index 34a2796..509193c 100644
--- a/media/libstagefright/codecs/aacenc/Android.mk
+++ b/media/libstagefright/codecs/aacenc/Android.mk
@@ -79,7 +79,7 @@
 endif
 
 ifeq ($(VOTT), v7)
-LOCAL_CFLAGS += -DARMV5E -DARMV7Neon -DARM_INASM -DARMV5_INASM
+LOCAL_CFLAGS += -DARMV5E -DARMV7Neon -DARM_INASM -DARMV5_INASM -DARMV6_INASM
 LOCAL_C_INCLUDES += $(LOCAL_PATH)/src/asm/ARMV5E
 LOCAL_C_INCLUDES += $(LOCAL_PATH)/src/asm/ARMV7
 endif
diff --git a/media/libstagefright/codecs/aacenc/basic_op/basic_op.h b/media/libstagefright/codecs/aacenc/basic_op/basic_op.h
index e878bba..5cd7e5f 100644
--- a/media/libstagefright/codecs/aacenc/basic_op/basic_op.h
+++ b/media/libstagefright/codecs/aacenc/basic_op/basic_op.h
@@ -227,13 +227,7 @@
 #if ARMV4_INASM
 __inline Word32 ASM_L_shr(Word32 L_var1, Word16 var2)
 {
-	Word32 result;
-	asm (
-		"MOV %[result], %[L_var1], ASR %[var2] \n"
-		:[result]"=r"(result)
-		:[L_var1]"r"(L_var1), [var2]"r"(var2)
-		);
-	return result;
+	return L_var1 >> var2;
 }
 
 __inline Word32 ASM_L_shl(Word32 L_var1, Word16 var2)
@@ -264,6 +258,18 @@
 
 __inline Word32 ASM_shl(Word32 L_var1, Word16 var2)
 {
+#if ARMV6_SAT
+	Word32 result;
+	asm (
+		"CMP	%[var2], #16\n"
+		"MOVLT  %[result], %[L_var1], ASL %[var2]\n"
+		"MOVGE  %[result], %[L_var1], ASL #16\n"
+		"SSAT   %[result], #16, %[result]\n"
+		:[result]"=r"(result)
+		:[L_var1]"r"(L_var1), [var2]"r"(var2)
+		);
+	return result;
+#else
 	Word32 result;
 	Word32 tmp;
 	asm (
@@ -277,6 +283,7 @@
 		:[L_var1]"r"(L_var1), [var2]"r"(var2), [mask]"r"(0x7fff)
 		);
 	return result;
+#endif
 }
 #endif
 
@@ -288,7 +295,15 @@
 #if (SATRUATE_IS_INLINE)
 __inline Word16 saturate(Word32 L_var1)
 {
-#if ARMV5TE_SAT
+#if ARMV6_SAT
+    Word16 result;
+	asm (
+		"SSAT %[result], #16, %[L_var1]"
+		: [result]"=r"(result)
+		: [L_var1]"r"(L_var1)
+		);
+	return result;
+#elif ARMV5TE_SAT
 	Word16 result;
 	Word32 tmp;
 	asm volatile (
@@ -445,8 +460,7 @@
 	Word32 result;
 	asm (
 		"SMULBB %[result], %[var1], %[var2] \n"
-		"QADD %[result], %[result], %[result] \n"
-		"QSUB %[result], %[L_var3], %[result]\n"
+		"QDSUB %[result], %[L_var3], %[result]\n"
 		:[result]"=&r"(result)
 		:[L_var3]"r"(L_var3), [var1]"r"(var1), [var2]"r"(var2)
 		);
@@ -671,7 +685,16 @@
 #if (MULT_IS_INLINE)
 __inline Word16 mult (Word16 var1, Word16 var2)
 {
-#if ARMV5TE_MULT
+#if ARMV5TE_MULT && ARMV6_SAT
+	Word32 result;
+	asm (
+		"SMULBB %[result], %[var1], %[var2] \n"
+		"SSAT   %[result], #16, %[result], ASR #15 \n"
+		:[result]"=r"(result)
+		:[var1]"r"(var1), [var2]"r"(var2)
+		);
+	return result;
+#elif ARMV5TE_MULT
 	Word32 result, tmp;
 	asm (
 		"SMULBB %[tmp], %[var1], %[var2] \n"
@@ -990,8 +1013,7 @@
 	Word32 result;
 	asm (
 		"SMULBB %[result], %[var1], %[var2]\n"
-		"QADD	%[result], %[result], %[result]\n"
-		"QADD   %[result], %[result], %[L_var3]\n"
+		"QDADD  %[result], %[L_var3], %[result]\n"
 		:[result]"=&r"(result)
 		: [L_var3]"r"(L_var3), [var1]"r"(var1), [var2]"r"(var2)
 		);
diff --git a/media/libstagefright/codecs/aacenc/basic_op/typedefs.h b/media/libstagefright/codecs/aacenc/basic_op/typedefs.h
index 8ef43e2..6059237 100644
--- a/media/libstagefright/codecs/aacenc/basic_op/typedefs.h
+++ b/media/libstagefright/codecs/aacenc/basic_op/typedefs.h
@@ -128,6 +128,13 @@
     #define ARMV5TE_NORM_L        1
 	#define ARMV5TE_L_MPY_LS	  1
 #endif
+#if ARMV6_INASM
+    #undef  ARMV5TE_ADD
+    #define ARMV5TE_ADD           0
+    #undef  ARMV5TE_SUB
+    #define ARMV5TE_SUB           0
+    #define ARMV6_SAT             1
+#endif
 
 //basic operation functions optimization flags
 #define SATRUATE_IS_INLINE              1   //define saturate as inline function
diff --git a/media/libstagefright/codecs/aacenc/src/bitbuffer.c b/media/libstagefright/codecs/aacenc/src/bitbuffer.c
index a706893..0ce93d3 100644
--- a/media/libstagefright/codecs/aacenc/src/bitbuffer.c
+++ b/media/libstagefright/codecs/aacenc/src/bitbuffer.c
@@ -152,6 +152,7 @@
 
   wBitPos = hBitBuf->wBitPos;
   wBitPos += noBitsToWrite;
+  writeValue &= ~(0xffffffff << noBitsToWrite); // Mask out everything except the lowest noBitsToWrite bits
   writeValue <<= 32 - wBitPos;
   writeValue |= hBitBuf->cache;
 
diff --git a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/stress/MediaRecorderStressTest.java b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/stress/MediaRecorderStressTest.java
index 73ee4dd..5e649e0 100644
--- a/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/stress/MediaRecorderStressTest.java
+++ b/media/tests/MediaFrameworkTest/src/com/android/mediaframeworktest/stress/MediaRecorderStressTest.java
@@ -365,6 +365,7 @@
                 mRecorder.setVideoSize(video_width, video_height);
                 mRecorder.setVideoEncoder(video_encoder);
                 mRecorder.setAudioEncoder(audio_encoder);
+                mRecorder.setVideoEncodingBitRate(bit_rate);
                 Log.v(TAG, "mediaRecorder setPreview");
                 mRecorder.setPreviewDisplay(mSurfaceHolder.getSurface());
                 mRecorder.prepare();
diff --git a/packages/FakeOemFeatures/AndroidManifest.xml b/packages/FakeOemFeatures/AndroidManifest.xml
index 57938ac..93b8b47 100644
--- a/packages/FakeOemFeatures/AndroidManifest.xml
+++ b/packages/FakeOemFeatures/AndroidManifest.xml
@@ -15,9 +15,9 @@
 
         <service android:name=".FakeCoreService" android:process=":core"
                 android:label="Fake OEM Core Service" />
-        <service android:name=".FakeCoreService2" android:process=":core"
+        <service android:name=".FakeCoreService2" android:process=":core2"
                 android:label="Fake OEM Core Service Also" />
-        <service android:name=".FakeCoreService3" android:process=":core"
+        <service android:name=".FakeCoreService3" android:process=":core3"
                 android:label="Fake OEM Core Service Me Too" />
         <service android:name=".FakeBackgroundService" android:process=":background"
                 android:label="Fake OEM Bg Service" />
diff --git a/policy/src/com/android/internal/policy/impl/KeyguardViewBase.java b/policy/src/com/android/internal/policy/impl/KeyguardViewBase.java
index f204070..39fdf92 100644
--- a/policy/src/com/android/internal/policy/impl/KeyguardViewBase.java
+++ b/policy/src/com/android/internal/policy/impl/KeyguardViewBase.java
@@ -72,8 +72,9 @@
         }
     };
 
-    public KeyguardViewBase(Context context) {
+    public KeyguardViewBase(Context context, KeyguardViewCallback callback) {
         super(context);
+        mCallback = callback;
         resetBackground();
     }
 
@@ -81,11 +82,6 @@
         setBackgroundDrawable(mBackgroundDrawable);
     }
 
-    // used to inject callback
-    void setCallback(KeyguardViewCallback callback) {
-        mCallback = callback;
-    }
-
     public KeyguardViewCallback getCallback() {
         return mCallback;
     }
diff --git a/policy/src/com/android/internal/policy/impl/KeyguardViewManager.java b/policy/src/com/android/internal/policy/impl/KeyguardViewManager.java
index 4bba71b..7100e89 100644
--- a/policy/src/com/android/internal/policy/impl/KeyguardViewManager.java
+++ b/policy/src/com/android/internal/policy/impl/KeyguardViewManager.java
@@ -158,9 +158,9 @@
 
         if (mKeyguardView == null) {
             if (DEBUG) Log.d(TAG, "keyguard view is null, creating it...");
-            mKeyguardView = mKeyguardViewProperties.createKeyguardView(mContext, mUpdateMonitor, this);
+            mKeyguardView = mKeyguardViewProperties.createKeyguardView(mContext, mCallback,
+                    mUpdateMonitor, this);
             mKeyguardView.setId(R.id.lock_screen);
-            mKeyguardView.setCallback(mCallback);
 
             final ViewGroup.LayoutParams lp = new FrameLayout.LayoutParams(
                     ViewGroup.LayoutParams.MATCH_PARENT,
diff --git a/policy/src/com/android/internal/policy/impl/KeyguardViewProperties.java b/policy/src/com/android/internal/policy/impl/KeyguardViewProperties.java
index bda08eb..51b7f1e 100644
--- a/policy/src/com/android/internal/policy/impl/KeyguardViewProperties.java
+++ b/policy/src/com/android/internal/policy/impl/KeyguardViewProperties.java
@@ -24,16 +24,17 @@
  * of whether the keyguard instance is around or not.
  */
 public interface KeyguardViewProperties {
-    
+
     /**
      * Create a keyguard view.
      * @param context the context to use when creating the view.
+     * @param callback keyguard callback object for pokewakelock(), etc.
      * @param updateMonitor configuration may be based on this.
      * @param controller for talking back with the containing window.
      * @return the view.
      */
     KeyguardViewBase createKeyguardView(Context context,
-            KeyguardUpdateMonitor updateMonitor,
+            KeyguardViewCallback mCallback, KeyguardUpdateMonitor updateMonitor,
             KeyguardWindowController controller);
 
     /**
diff --git a/policy/src/com/android/internal/policy/impl/LockPatternKeyguardView.java b/policy/src/com/android/internal/policy/impl/LockPatternKeyguardView.java
index 1e9784c..3ca57c6 100644
--- a/policy/src/com/android/internal/policy/impl/LockPatternKeyguardView.java
+++ b/policy/src/com/android/internal/policy/impl/LockPatternKeyguardView.java
@@ -291,17 +291,16 @@
 
     /**
      * @param context Used to inflate, and create views.
+     * @param callback Keyguard callback object for pokewakelock(), etc.
      * @param updateMonitor Knows the state of the world, and passed along to each
      *   screen so they can use the knowledge, and also register for callbacks
      *   on dynamic information.
      * @param lockPatternUtils Used to look up state of lock pattern.
      */
     public LockPatternKeyguardView(
-            Context context,
-            KeyguardUpdateMonitor updateMonitor,
-            LockPatternUtils lockPatternUtils,
-            KeyguardWindowController controller) {
-        super(context);
+            Context context, KeyguardViewCallback callback, KeyguardUpdateMonitor updateMonitor,
+            LockPatternUtils lockPatternUtils, KeyguardWindowController controller) {
+        super(context, callback);
 
         mHandler = new Handler(this);
         mConfiguration = context.getResources().getConfiguration();
diff --git a/policy/src/com/android/internal/policy/impl/LockPatternKeyguardViewProperties.java b/policy/src/com/android/internal/policy/impl/LockPatternKeyguardViewProperties.java
index 19adb3e..d7fb19a 100644
--- a/policy/src/com/android/internal/policy/impl/LockPatternKeyguardViewProperties.java
+++ b/policy/src/com/android/internal/policy/impl/LockPatternKeyguardViewProperties.java
@@ -43,9 +43,10 @@
     }
 
     public KeyguardViewBase createKeyguardView(Context context,
+            KeyguardViewCallback callback,
             KeyguardUpdateMonitor updateMonitor,
             KeyguardWindowController controller) {
-        return new LockPatternKeyguardView(context, updateMonitor,
+        return new LockPatternKeyguardView(context, callback, updateMonitor,
                 mLockPatternUtils, controller);
     }
 
diff --git a/policy/tests/src/com/android/internal/policy/impl/LockPatternKeyguardViewTest.java b/policy/tests/src/com/android/internal/policy/impl/LockPatternKeyguardViewTest.java
index bdfe652..db71e2b 100644
--- a/policy/tests/src/com/android/internal/policy/impl/LockPatternKeyguardViewTest.java
+++ b/policy/tests/src/com/android/internal/policy/impl/LockPatternKeyguardViewTest.java
@@ -17,6 +17,7 @@
 package com.android.internal.policy.impl;
 
 import android.content.Context;
+import com.android.internal.policy.impl.KeyguardViewCallback;
 import com.android.internal.telephony.IccCard;
 import android.content.res.Configuration;
 import android.test.AndroidTestCase;
@@ -133,9 +134,10 @@
 
 
 
-        private TestableLockPatternKeyguardView(Context context, KeyguardUpdateMonitor updateMonitor,
+        private TestableLockPatternKeyguardView(Context context, KeyguardViewCallback callback,
+                KeyguardUpdateMonitor updateMonitor,
                 LockPatternUtils lockPatternUtils, KeyguardWindowController controller) {
-            super(context, updateMonitor, lockPatternUtils, controller);
+            super(context, callback, updateMonitor, lockPatternUtils, controller);
         }
 
         @Override
@@ -198,14 +200,13 @@
         super.setUp();
         mUpdateMonitor = new MockUpdateMonitor(getContext());
         mLockPatternUtils = new MockLockPatternUtils(getContext());
+        mKeyguardViewCallback = new MockKeyguardCallback();
 
-        mLPKV = new TestableLockPatternKeyguardView(getContext(), mUpdateMonitor,
-                mLockPatternUtils, new KeyguardWindowController() {
+        mLPKV = new TestableLockPatternKeyguardView(getContext(), mKeyguardViewCallback,
+                mUpdateMonitor, mLockPatternUtils, new KeyguardWindowController() {
             public void setNeedsInput(boolean needsInput) {
             }
         });
-        mKeyguardViewCallback = new MockKeyguardCallback();
-        mLPKV.setCallback(mKeyguardViewCallback);
     }
 
     public void testStateAfterCreatedWhileScreenOff() {
diff --git a/services/audioflinger/AudioFlinger.cpp b/services/audioflinger/AudioFlinger.cpp
index 8f7b35c..b972548 100644
--- a/services/audioflinger/AudioFlinger.cpp
+++ b/services/audioflinger/AudioFlinger.cpp
@@ -1919,10 +1919,10 @@
 
 AudioFlinger::MixerThread::MixerThread(const sp<AudioFlinger>& audioFlinger, AudioStreamOut* output,
         audio_io_handle_t id, uint32_t device, type_t type)
-    :   PlaybackThread(audioFlinger, output, id, device, type),
-        mAudioMixer(new AudioMixer(mFrameCount, mSampleRate)),
-        mPrevMixerStatus(MIXER_IDLE)
+    :   PlaybackThread(audioFlinger, output, id, device, type)
 {
+    mAudioMixer = new AudioMixer(mFrameCount, mSampleRate);
+    mPrevMixerStatus = MIXER_IDLE;
     // FIXME - Current mixer implementation only supports stereo output
     if (mChannelCount == 1) {
         ALOGE("Invalid audio hardware channel count");
@@ -1991,44 +1991,67 @@
     }
 }
 
-bool AudioFlinger::MixerThread::threadLoop()
+bool AudioFlinger::PlaybackThread::threadLoop()
 {
-    // DirectOutputThread has single trackToRemove instead of Vector
+    // MIXER || DUPLICATING
     Vector< sp<Track> > tracksToRemove;
-    // DirectOutputThread has activeTrack here
-    nsecs_t standbyTime = systemTime();
-    size_t mixBufferSize = mFrameCount * mFrameSize;
 
+    // DIRECT
+    sp<Track> trackToRemove;
+
+    standbyTime = systemTime();
+    mixBufferSize = mFrameCount * mFrameSize;
+
+    // MIXER
     // FIXME: Relaxed timing because of a certain device that can't meet latency
     // Should be reduced to 2x after the vendor fixes the driver issue
     // increase threshold again due to low power audio mode. The way this warning threshold is
     // calculated and its usefulness should be reconsidered anyway.
     nsecs_t maxPeriod = seconds(mFrameCount) / mSampleRate * 15;
     nsecs_t lastWarning = 0;
-    bool longStandbyExit = false;
+if (mType == MIXER) {
+    longStandbyExit = false;
+}
 
-    uint32_t activeSleepTime = activeSleepTimeUs();
-    uint32_t idleSleepTime = idleSleepTimeUs();
-    uint32_t sleepTime = idleSleepTime;
+    // DUPLICATING
+    // FIXME could this be made local to while loop?
+    writeFrames = 0;
 
-    uint32_t sleepTimeShift = 0;
+    activeSleepTime = activeSleepTimeUs();
+    idleSleepTime = idleSleepTimeUs();
+    sleepTime = idleSleepTime;
+
+if (mType == MIXER) {
+    sleepTimeShift = 0;
+}
+
+    // MIXER
     CpuStats cpuStats;
 
-    // DirectOutputThread has shorter standbyDelay
+    // DIRECT
+if (mType == DIRECT) {
+    // use shorter standby delay as on normal output to release
+    // hardware resources as soon as possible
+    standbyDelay = microseconds(activeSleepTime*2);
+}
 
     acquireWakeLock();
 
     while (!exitPending())
     {
+if (mType == MIXER) {
         cpuStats.sample();
-
-        // DirectOutputThread has rampVolume, leftVol, rightVol
+}
 
         Vector< sp<EffectChain> > effectChains;
 
         processConfigEvents();
 
-        mixer_state mixerStatus = MIXER_IDLE;
+if (mType == DIRECT) {
+        activeTrack.clear();
+}
+
+        mixerStatus = MIXER_IDLE;
         { // scope for mLock
 
             Mutex::Autolock _l(mLock);
@@ -2036,23 +2059,46 @@
             if (checkForNewParameters_l()) {
                 mixBufferSize = mFrameCount * mFrameSize;
 
+if (mType == MIXER) {
                 // FIXME: Relaxed timing because of a certain device that can't meet latency
                 // Should be reduced to 2x after the vendor fixes the driver issue
                 // increase threshold again due to low power audio mode. The way this warning
                 // threshold is calculated and its usefulness should be reconsidered anyway.
                 maxPeriod = seconds(mFrameCount) / mSampleRate * 15;
+}
+
+if (mType == DUPLICATING) {
+                updateWaitTime();
+}
 
                 activeSleepTime = activeSleepTimeUs();
                 idleSleepTime = idleSleepTimeUs();
-                // DirectOutputThread updates standbyDelay also
+
+if (mType == DIRECT) {
+                standbyDelay = microseconds(activeSleepTime*2);
+}
+
             }
 
+if (mType == DUPLICATING) {
+#if 0   // see earlier FIXME
+            // Now that this is a field instead of local variable,
+            // clear it so it is empty the first time through the loop,
+            // and later an assignment could combine the clear with the loop below
+            outputTracks.clear();
+#endif
+            for (size_t i = 0; i < mOutputTracks.size(); i++) {
+                outputTracks.add(mOutputTracks[i]);
+            }
+}
+
             // put audio hardware into standby after short delay
             if (CC_UNLIKELY((!mActiveTracks.size() && systemTime() > standbyTime) ||
                         mSuspended > 0)) {
                 if (!mStandby) {
-                    ALOGV("Audio hardware entering standby, mixer %p, suspend count %u", this, mSuspended);
-                    mOutput->stream->common.standby(&mOutput->stream->common);
+
+                    threadLoop_standby();
+
                     mStandby = true;
                     mBytesWritten = 0;
                 }
@@ -2061,6 +2107,10 @@
                     // we're about to wait, flush the binder command buffer
                     IPCThreadState::self()->flushCommands();
 
+if (mType == DUPLICATING) {
+                    outputTracks.clear();
+}
+
                     if (exitPending()) break;
 
                     releaseWakeLock_l();
@@ -2070,17 +2120,41 @@
                     ALOGV("Thread %p type %d TID %d waking up", this, mType, gettid());
                     acquireWakeLock_l();
 
+if (mType == MIXER || mType == DUPLICATING) {
                     mPrevMixerStatus = MIXER_IDLE;
+}
+
                     checkSilentMode_l();
 
+if (mType == MIXER || mType == DUPLICATING) {
                     standbyTime = systemTime() + mStandbyTimeInNsecs;
+}
+
+if (mType == DIRECT) {
+                    standbyTime = systemTime() + standbyDelay;
+}
+
                     sleepTime = idleSleepTime;
+
+if (mType == MIXER) {
                     sleepTimeShift = 0;
+}
+
                     continue;
                 }
             }
 
+// FIXME merge these
+if (mType == MIXER || mType == DUPLICATING) {
             mixerStatus = prepareTracks_l(&tracksToRemove);
+}
+if (mType == DIRECT) {
+            mixerStatus = threadLoop_prepareTracks_l(trackToRemove);
+            // see FIXME in AudioFlinger.h
+            if (mixerStatus == MIXER_CONTINUE) {
+                continue;
+            }
+}
 
             // prevent any changes in effect chain list and in each effect chain
             // during mixing and effect process as the audio buffers could be deleted
@@ -2088,7 +2162,130 @@
             lockEffectChains_l(effectChains);
         }
 
+if (mType == DIRECT) {
+        // For DirectOutputThread, this test is equivalent to "activeTrack != 0"
+}
+
         if (CC_LIKELY(mixerStatus == MIXER_TRACKS_READY)) {
+            threadLoop_mix();
+        } else {
+            threadLoop_sleepTime();
+        }
+
+        if (mSuspended > 0) {
+            sleepTime = suspendSleepTimeUs();
+        }
+
+        // only process effects if we're going to write
+        if (sleepTime == 0) {
+
+            if (mixerStatus == MIXER_TRACKS_READY) {
+
+                // Non-trivial for DIRECT only
+                applyVolume();
+
+            }
+
+            for (size_t i = 0; i < effectChains.size(); i ++) {
+                effectChains[i]->process_l();
+            }
+        }
+
+        // enable changes in effect chain
+        unlockEffectChains(effectChains);
+
+        // sleepTime == 0 means we must write to audio hardware
+        if (sleepTime == 0) {
+
+            threadLoop_write();
+
+if (mType == MIXER) {
+            // write blocked detection
+            nsecs_t now = systemTime();
+            nsecs_t delta = now - mLastWriteTime;
+            if (!mStandby && delta > maxPeriod) {
+                mNumDelayedWrites++;
+                if ((now - lastWarning) > kWarningThrottleNs) {
+                    ALOGW("write blocked for %llu msecs, %d delayed writes, thread %p",
+                            ns2ms(delta), mNumDelayedWrites, this);
+                    lastWarning = now;
+                }
+                // FIXME this is broken: longStandbyExit should be handled out of the if() and with
+                // a different threshold. Or completely removed for what it is worth anyway...
+                if (mStandby) {
+                    longStandbyExit = true;
+                }
+            }
+}
+
+            mStandby = false;
+        } else {
+            usleep(sleepTime);
+        }
+
+        // finally let go of removed track(s), without the lock held
+        // since we can't guarantee the destructors won't acquire that
+        // same lock.
+
+// FIXME merge these
+if (mType == MIXER) {
+        tracksToRemove.clear();
+}
+if (mType == DIRECT) {
+        trackToRemove.clear();
+        activeTrack.clear();
+}
+if (mType == DUPLICATING) {
+        tracksToRemove.clear();
+        outputTracks.clear();
+}
+
+        // Effect chains will be actually deleted here if they were removed from
+        // mEffectChains list during mixing or effects processing
+        effectChains.clear();
+
+        // FIXME Note that the above .clear() is no longer necessary since effectChains
+        // is now local to this block, but will keep it for now (at least until merge done).
+    }
+
+if (mType == MIXER || mType == DIRECT) {
+    // put output stream into standby mode
+    if (!mStandby) {
+        mOutput->stream->common.standby(&mOutput->stream->common);
+    }
+}
+if (mType == DUPLICATING) {
+    // for DuplicatingThread, standby mode is handled by the outputTracks
+}
+
+    releaseWakeLock();
+
+    ALOGV("Thread %p type %d exiting", this, mType);
+    return false;
+}
+
+// shared by MIXER and DIRECT, overridden by DUPLICATING
+void AudioFlinger::PlaybackThread::threadLoop_write()
+{
+            // FIXME rewrite to reduce number of system calls
+            mLastWriteTime = systemTime();
+            mInWrite = true;
+            mBytesWritten += mixBufferSize;
+            int bytesWritten = (int)mOutput->stream->write(mOutput->stream, mMixBuffer, mixBufferSize);
+            if (bytesWritten < 0) mBytesWritten -= mixBufferSize;
+            mNumWrites++;
+            mInWrite = false;
+}
+
+// shared by MIXER and DIRECT, overridden by DUPLICATING
+void AudioFlinger::PlaybackThread::threadLoop_standby()
+{
+                    ALOGV("Audio hardware entering standby, mixer %p, suspend count %u", this, mSuspended);
+                    mOutput->stream->common.standby(&mOutput->stream->common);
+}
+
+void AudioFlinger::MixerThread::threadLoop_mix()
+{
             // obtain the presentation timestamp of the next output buffer
             int64_t pts;
             status_t status = INVALID_OPERATION;
@@ -2114,7 +2311,10 @@
             sleepTime = 0;
             standbyTime = systemTime() + mStandbyTimeInNsecs;
             //TODO: delay standby when effects have a tail
-        } else {
+}
+
+void AudioFlinger::MixerThread::threadLoop_sleepTime()
+{
             // If no tracks are ready, sleep once for the duration of an output
             // buffer size, then write 0s to the output
             if (sleepTime == 0) {
@@ -2140,79 +2340,6 @@
                 ALOGV_IF((mBytesWritten == 0 && (mixerStatus == MIXER_TRACKS_ENABLED && longStandbyExit)), "anticipated start");
             }
             // TODO add standby time extension fct of effect tail
-        }
-
-        if (mSuspended > 0) {
-            sleepTime = suspendSleepTimeUs();
-        }
-
-        // only process effects if we're going to write
-        if (sleepTime == 0) {
-
-            // DirectOutputThread adds applyVolume here
-
-            for (size_t i = 0; i < effectChains.size(); i ++) {
-                effectChains[i]->process_l();
-            }
-        }
-
-        // enable changes in effect chain
-        unlockEffectChains(effectChains);
-
-        // sleepTime == 0 means we must write to audio hardware
-        if (sleepTime == 0) {
-            // FIXME Only in MixerThread, and rewrite to reduce number of system calls
-            mLastWriteTime = systemTime();
-            mInWrite = true;
-            mBytesWritten += mixBufferSize;
-            int bytesWritten = (int)mOutput->stream->write(mOutput->stream, mMixBuffer, mixBufferSize);
-            if (bytesWritten < 0) mBytesWritten -= mixBufferSize;
-            mNumWrites++;
-            mInWrite = false;
-
-            // Only in MixerThread: start of write blocked detection
-            nsecs_t now = systemTime();
-            nsecs_t delta = now - mLastWriteTime;
-            if (!mStandby && delta > maxPeriod) {
-                mNumDelayedWrites++;
-                if ((now - lastWarning) > kWarningThrottleNs) {
-                    ALOGW("write blocked for %llu msecs, %d delayed writes, thread %p",
-                            ns2ms(delta), mNumDelayedWrites, this);
-                    lastWarning = now;
-                }
-                if (mStandby) {
-                    longStandbyExit = true;
-                }
-            }
-            // end of write blocked detection
-
-            mStandby = false;
-        } else {
-            usleep(sleepTime);
-        }
-
-        // finally let go of removed track(s), without the lock held
-        // since we can't guarantee the destructors won't acquire that
-        // same lock.
-        tracksToRemove.clear();
-
-        // Effect chains will be actually deleted here if they were removed from
-        // mEffectChains list during mixing or effects processing
-        effectChains.clear();
-
-        // FIXME Note that the above .clear() is no longer necessary since effectChains
-        // is now local to this block, but will keep it for now (at least until merge done).
-    }
-
-    // put output stream into standby mode
-    if (!mStandby) {
-        mOutput->stream->common.standby(&mOutput->stream->common);
-    }
-
-    releaseWakeLock();
-
-    ALOGV("Thread %p type %d exiting", this, mType);
-    return false;
 }
 
 // prepareTracks_l() must be called with ThreadBase::mLock held
@@ -2653,7 +2780,7 @@
 {
 }
 
-void AudioFlinger::DirectOutputThread::applyVolume(uint16_t leftVol, uint16_t rightVol, bool ramp)
+void AudioFlinger::DirectOutputThread::applyVolume()
 {
     // Do not apply volume on compressed audio
     if (!audio_is_linear_pcm(mFormat)) {
@@ -2672,7 +2799,7 @@
 
     size_t frameCount = mFrameCount;
     int16_t *out = mMixBuffer;
-    if (ramp) {
+    if (rampVolume) {
         if (mChannelCount == 1) {
             int32_t d = ((int32_t)leftVol - (int32_t)mLeftVolShort) << 16;
             int32_t vlInc = d / (int32_t)frameCount;
@@ -2727,103 +2854,19 @@
     mRightVolShort = rightVol;
 }
 
-bool AudioFlinger::DirectOutputThread::threadLoop()
+AudioFlinger::PlaybackThread::mixer_state AudioFlinger::DirectOutputThread::threadLoop_prepareTracks_l(
+    sp<Track>& trackToRemove
+)
 {
-    // MixerThread has Vector instead of single trackToRemove
-    sp<Track> trackToRemove;
-
-    nsecs_t standbyTime = systemTime();
-    size_t mixBufferSize = mFrameCount * mFrameSize;
-
-    // MixerThread has relaxed timing: maxPeriod, lastWarning, longStandbyExit
-
-    uint32_t activeSleepTime = activeSleepTimeUs();
-    uint32_t idleSleepTime = idleSleepTimeUs();
-    uint32_t sleepTime = idleSleepTime;
-
-    // MixerThread has sleepTimeShift and cpuStats
-
-    // use shorter standby delay as on normal output to release
-    // hardware resources as soon as possible
-    nsecs_t standbyDelay = microseconds(activeSleepTime*2);
-
-    acquireWakeLock();
-
-    while (!exitPending())
-    {
-        // MixerThread has cpuStats.sample()
-
-        bool rampVolume;
-        uint16_t leftVol;
-        uint16_t rightVol;
-
-        Vector< sp<EffectChain> > effectChains;
-
-        processConfigEvents();
-
-        // MixerThread does not have activeTrack here
-        sp<Track> activeTrack;
-
-        mixer_state mixerStatus = MIXER_IDLE;
-        { // scope for the mLock
-
-            Mutex::Autolock _l(mLock);
-
-            if (checkForNewParameters_l()) {
-                mixBufferSize = mFrameCount * mFrameSize;
-
-                // different calculations here
-                standbyDelay = microseconds(activeSleepTime*2);
-
-                activeSleepTime = activeSleepTimeUs();
-                idleSleepTime = idleSleepTimeUs();
-                standbyDelay = microseconds(activeSleepTime*2);
-            }
-
-            // put audio hardware into standby after short delay
-            if (CC_UNLIKELY((!mActiveTracks.size() && systemTime() > standbyTime) ||
-                        mSuspended > 0)) {
-                if (!mStandby) {
-                    ALOGV("Audio hardware entering standby, mixer %p, suspend count %u", this, mSuspended);
-                    mOutput->stream->common.standby(&mOutput->stream->common);
-                    mStandby = true;
-                    mBytesWritten = 0;
-                }
-
-                if (!mActiveTracks.size() && mConfigEvents.isEmpty()) {
-                    // we're about to wait, flush the binder command buffer
-                    IPCThreadState::self()->flushCommands();
-
-                    if (exitPending()) break;
-
-                    releaseWakeLock_l();
-                    // wait until we have something to do...
-                    ALOGV("Thread %p type %d TID %d going to sleep", this, mType, gettid());
-                    mWaitWorkCV.wait(mLock);
-                    ALOGV("Thread %p type %d TID %d waking up", this, mType, gettid());
-                    acquireWakeLock_l();
-
-                    // MixerThread has "mPrevMixerStatus = MIXER_IDLE"
-                    checkSilentMode_l();
-
-                    // MixerThread has different standbyDelay
-                    standbyTime = systemTime() + standbyDelay;
-                    sleepTime = idleSleepTime;
-                    // MixerThread has "sleepTimeShift = 0"
-                    continue;
-                }
-            }
-
-            // MixerThread has "mixerStatus = prepareTracks_l(...)"
-
-            // equivalent to MixerThread's lockEffectChains_l, but without the lock
-            // FIXME - is it OK to omit the lock here?
-            effectChains = mEffectChains;
+// FIXME Temporarily renamed to avoid confusion with the member "mixerStatus"
+mixer_state mixerStatus_ = MIXER_IDLE;
 
             // find out which tracks need to be processed
             if (mActiveTracks.size() != 0) {
                 sp<Track> t = mActiveTracks[0].promote();
-                if (t == 0) continue;
+                // see FIXME in AudioFlinger.h, return MIXER_IDLE might also work
+                if (t == 0) return MIXER_CONTINUE;
+                //if (t == 0) continue;
 
                 Track* const track = t.get();
                 audio_track_cblk_t* cblk = track->cblk();
@@ -2886,9 +2929,9 @@
                         // Delegate volume control to effect in track effect chain if needed
                         // only one effect chain can be present on DirectOutputThread, so if
                         // there is one, the track is connected to it
-                        if (!effectChains.isEmpty()) {
+                        if (!mEffectChains.isEmpty()) {
                             // Do not ramp volume if volume is controlled by effect
-                            if(effectChains[0]->setVolume_l(&vl, &vr)) {
+                            if (mEffectChains[0]->setVolume_l(&vl, &vr)) {
                                 rampVolume = false;
                             }
                         }
@@ -2909,7 +2952,7 @@
                     // reset retry count
                     track->mRetryCount = kMaxTrackRetriesDirect;
                     activeTrack = t;
-                    mixerStatus = MIXER_TRACKS_READY;
+                    mixerStatus_ = MIXER_TRACKS_READY;
                 } else {
                     //ALOGV("track %d u=%08x, s=%08x [NOT READY]", track->name(), cblk->user, cblk->server);
                     if (track->isStopped()) {
@@ -2926,7 +2969,7 @@
                             ALOGV("BUFFER TIMEOUT: remove(%d) from active list", track->name());
                             trackToRemove = track;
                         } else {
-                            mixerStatus = MIXER_TRACKS_ENABLED;
+                            mixerStatus_ = MIXER_TRACKS_ENABLED;
                         }
                     }
                 }
@@ -2935,21 +2978,21 @@
             // remove all the tracks that need to be...
             if (CC_UNLIKELY(trackToRemove != 0)) {
                 mActiveTracks.remove(trackToRemove);
-                if (!effectChains.isEmpty()) {
+                if (!mEffectChains.isEmpty()) {
                     ALOGV("stopping track on chain %p for session Id: %d", effectChains[0].get(),
                             trackToRemove->sessionId());
-                    effectChains[0]->decActiveTrackCnt();
+                    mEffectChains[0]->decActiveTrackCnt();
                 }
                 if (trackToRemove->isTerminated()) {
                     removeTrack_l(trackToRemove);
                 }
             }
 
-            lockEffectChains_l(effectChains);
-       }
+return mixerStatus_;
+}
 
-        // For DirectOutputThread, this test is equivalent to "activeTrack != 0"
-        if (CC_LIKELY(mixerStatus == MIXER_TRACKS_READY)) {
+void AudioFlinger::DirectOutputThread::threadLoop_mix()
+{
             AudioBufferProvider::Buffer buffer;
             size_t frameCount = mFrameCount;
             int8_t *curBuf = (int8_t *)mMixBuffer;
@@ -2968,7 +3011,10 @@
             }
             sleepTime = 0;
             standbyTime = systemTime() + standbyDelay;
-        } else {
+}
+
+void AudioFlinger::DirectOutputThread::threadLoop_sleepTime()
+{
             if (sleepTime == 0) {
                 if (mixerStatus == MIXER_TRACKS_ENABLED) {
                     sleepTime = activeSleepTime;
@@ -2979,68 +3025,6 @@
                 memset (mMixBuffer, 0, mFrameCount * mFrameSize);
                 sleepTime = 0;
             }
-        }
-
-        if (mSuspended > 0) {
-            sleepTime = suspendSleepTimeUs();
-        }
-
-        // only process effects if we're going to write
-        if (sleepTime == 0) {
-
-            // MixerThread does not have applyVolume
-            if (mixerStatus == MIXER_TRACKS_READY) {
-                applyVolume(leftVol, rightVol, rampVolume);
-            }
-
-            for (size_t i = 0; i < effectChains.size(); i ++) {
-                effectChains[i]->process_l();
-            }
-        }
-
-        // enable changes in effect chain
-        unlockEffectChains(effectChains);
-
-        // sleepTime == 0 means we must write to audio hardware
-        if (sleepTime == 0) {
-            mLastWriteTime = systemTime();
-            mInWrite = true;
-            mBytesWritten += mixBufferSize;
-            int bytesWritten = (int)mOutput->stream->write(mOutput->stream, mMixBuffer, mixBufferSize);
-            if (bytesWritten < 0) mBytesWritten -= mixBufferSize;
-            mNumWrites++;
-            mInWrite = false;
-
-            // MixerThread has write blocked detection here
-
-            mStandby = false;
-        } else {
-            usleep(sleepTime);
-        }
-
-        // finally let go of removed track(s), without the lock held
-        // since we can't guarantee the destructors won't acquire that
-        // same lock.
-        trackToRemove.clear();
-        activeTrack.clear();
-
-        // Effect chains will be actually deleted here if they were removed from
-        // mEffectChains list during mixing or effects processing
-        effectChains.clear();
-
-        // FIXME Note that the above .clear() is no longer necessary since effectChains
-        // is now local to this block, but will keep it for now (at least until merge done).
-    }
-
-    // put output stream into standby mode
-    if (!mStandby) {
-        mOutput->stream->common.standby(&mOutput->stream->common);
-    }
-
-    releaseWakeLock();
-
-    ALOGV("Thread %p type %d exiting", this, mType);
-    return false;
 }
 
 // getTrackName_l() must be called with ThreadBase::mLock held
@@ -3153,96 +3137,8 @@
     }
 }
 
-bool AudioFlinger::DuplicatingThread::threadLoop()
+void AudioFlinger::DuplicatingThread::threadLoop_mix()
 {
-    Vector< sp<Track> > tracksToRemove;
-    nsecs_t standbyTime = systemTime();
-    size_t mixBufferSize = mFrameCount * mFrameSize;
-
-    // Only in DuplicatingThread
-    SortedVector< sp<OutputTrack> > outputTracks;
-    uint32_t writeFrames = 0;
-
-    uint32_t activeSleepTime = activeSleepTimeUs();
-    uint32_t idleSleepTime = idleSleepTimeUs();
-    uint32_t sleepTime = idleSleepTime;
-
-    acquireWakeLock();
-
-    while (!exitPending())
-    {
-        // MixerThread has cpuStats.sample
-
-        Vector< sp<EffectChain> > effectChains;
-
-        processConfigEvents();
-
-        mixer_state mixerStatus = MIXER_IDLE;
-        { // scope for the mLock
-
-            Mutex::Autolock _l(mLock);
-
-            if (checkForNewParameters_l()) {
-                mixBufferSize = mFrameCount * mFrameSize;
-
-                // Only in DuplicatingThread
-                updateWaitTime();
-
-                activeSleepTime = activeSleepTimeUs();
-                idleSleepTime = idleSleepTimeUs();
-            }
-
-            // Only in DuplicatingThread
-            for (size_t i = 0; i < mOutputTracks.size(); i++) {
-                outputTracks.add(mOutputTracks[i]);
-            }
-
-            // put audio hardware into standby after short delay
-            if (CC_UNLIKELY((!mActiveTracks.size() && systemTime() > standbyTime) ||
-                         mSuspended > 0)) {
-                if (!mStandby) {
-                    // DuplicatingThread implements standby by stopping all tracks
-                    for (size_t i = 0; i < outputTracks.size(); i++) {
-                        outputTracks[i]->stop();
-                    }
-                    mStandby = true;
-                    mBytesWritten = 0;
-                }
-
-                if (!mActiveTracks.size() && mConfigEvents.isEmpty()) {
-                    // we're about to wait, flush the binder command buffer
-                    IPCThreadState::self()->flushCommands();
-                    outputTracks.clear();
-
-                    if (exitPending()) break;
-
-                    releaseWakeLock_l();
-                    // wait until we have something to do...
-                    ALOGV("Thread %p type %d TID %d going to sleep", this, mType, gettid());
-                    mWaitWorkCV.wait(mLock);
-                    ALOGV("Thread %p type %d TID %d waking up", this, mType, gettid());
-                    acquireWakeLock_l();
-
-                    // MixerThread has "mPrevMixerStatus = MIXER_IDLE"
-                    checkSilentMode_l();
-
-                    standbyTime = systemTime() + mStandbyTimeInNsecs;
-                    sleepTime = idleSleepTime;
-                    // MixerThread has sleepTimeShift
-                    continue;
-                }
-            }
-
-            mixerStatus = prepareTracks_l(&tracksToRemove);
-
-            // prevent any changes in effect chain list and in each effect chain
-            // during mixing and effect process as the audio buffers could be deleted
-            // or modified if an effect is created or deleted
-            lockEffectChains_l(effectChains);
-        }
-
-        // Duplicating Thread is completely different here
-        if (CC_LIKELY(mixerStatus == MIXER_TRACKS_READY)) {
             // mix buffers...
             if (outputsReady(outputTracks)) {
                 mAudioMixer->process(AudioBufferProvider::kInvalidPTS);
@@ -3251,7 +3147,10 @@
             }
             sleepTime = 0;
             writeFrames = mFrameCount;
-        } else {
+}
+
+void AudioFlinger::DuplicatingThread::threadLoop_sleepTime()
+{
             if (sleepTime == 0) {
                 if (mixerStatus == MIXER_TRACKS_ENABLED) {
                     sleepTime = activeSleepTime;
@@ -3269,58 +3168,23 @@
                     }
                 }
             }
-        }
+}
 
-        if (mSuspended > 0) {
-            sleepTime = suspendSleepTimeUs();
-        }
-
-        // only process effects if we're going to write
-        if (sleepTime == 0) {
-            for (size_t i = 0; i < effectChains.size(); i ++) {
-                effectChains[i]->process_l();
-            }
-        }
-
-        // enable changes in effect chain
-        unlockEffectChains(effectChains);
-
-        // sleepTime == 0 means we must write to audio hardware
-        if (sleepTime == 0) {
+void AudioFlinger::DuplicatingThread::threadLoop_write()
+{
             standbyTime = systemTime() + mStandbyTimeInNsecs;
             for (size_t i = 0; i < outputTracks.size(); i++) {
                 outputTracks[i]->write(mMixBuffer, writeFrames);
             }
-            mStandby = false;
             mBytesWritten += mixBufferSize;
+}
 
-            // MixerThread has write blocked detection here
-
-        } else {
-            usleep(sleepTime);
-        }
-
-        // finally let go of removed track(s), without the lock held
-        // since we can't guarantee the destructors won't acquire that
-        // same lock.
-        tracksToRemove.clear();
-        outputTracks.clear();
-
-        // Effect chains will be actually deleted here if they were removed from
-        // mEffectChains list during mixing or effects processing
-        effectChains.clear();
-
-        // FIXME Note that the above .clear() is no longer necessary since effectChains
-        // is now local to this block, but will keep it for now (at least until merge done).
-    }
-
-    // MixerThread and DirectOutpuThread have standby here,
-    // but for DuplicatingThread this is handled by the outputTracks
-
-    releaseWakeLock();
-
-    ALOGV("Thread %p type %d exiting", this, mType);
-    return false;
+void AudioFlinger::DuplicatingThread::threadLoop_standby()
+{
+                    // DuplicatingThread implements standby by stopping all tracks
+                    for (size_t i = 0; i < outputTracks.size(); i++) {
+                        outputTracks[i]->stop();
+                    }
 }
 
 void AudioFlinger::DuplicatingThread::addOutputTrack(MixerThread *thread)
diff --git a/services/audioflinger/AudioFlinger.h b/services/audioflinger/AudioFlinger.h
index bdaf97c..c7ac0a8 100644
--- a/services/audioflinger/AudioFlinger.h
+++ b/services/audioflinger/AudioFlinger.h
@@ -207,7 +207,9 @@
     // call in any IAudioFlinger method that accesses mPrimaryHardwareDev
     status_t                initCheck() const { return mPrimaryHardwareDev == NULL ? NO_INIT : NO_ERROR; }
 
+    // RefBase
     virtual     void        onFirstRef();
+
     audio_hw_device_t*      findSuitableHwDev_l(uint32_t devices);
     void                    purgeStaleEffects_l();
 
@@ -581,6 +583,10 @@
             MIXER_TRACKS_READY      // at least one active track, and at least one track has data
             // standby mode does not have an enum value
             // suspend by audio policy manager is orthogonal to mixer state
+#if 1
+            // FIXME remove these hacks for threadLoop_prepareTracks_l
+            , MIXER_CONTINUE        // "continue;"
+#endif
         };
 
         // playback track
@@ -793,8 +799,33 @@
 
         // Thread virtuals
         virtual     status_t    readyToRun();
+        virtual     bool        threadLoop();
+
+        // RefBase
         virtual     void        onFirstRef();
 
+protected:
+        // Code snippets that were lifted up out of threadLoop()
+        virtual     void        threadLoop_mix() = 0;
+        virtual     void        threadLoop_sleepTime() = 0;
+        virtual     void        threadLoop_write();
+        virtual     void        threadLoop_standby();
+
+        // Non-trivial for DUPLICATING only
+        virtual     void        updateWaitTime() { }
+
+        // Non-trivial for DIRECT only
+        virtual     void        applyVolume() { }
+
+        // FIXME merge these
+        // Non-trivial for MIXER and DUPLICATING only
+        virtual     mixer_state prepareTracks_l(Vector< sp<Track> > *tracksToRemove) { return MIXER_IDLE; }
+        // Non-trivial for DIRECT only
+        virtual     mixer_state threadLoop_prepareTracks_l(sp<Track>& trackToRemove)
+                                                                { return MIXER_IDLE; }
+
+public:
+
         virtual     status_t    initCheck() const { return (mOutput == NULL) ? NO_INIT : NO_ERROR; }
 
         virtual     uint32_t    latency() const;
@@ -897,6 +928,30 @@
         int                             mNumWrites;
         int                             mNumDelayedWrites;
         bool                            mInWrite;
+
+        // FIXME rename these former local variables of threadLoop to standard "m" names
+        nsecs_t                         standbyTime;
+        size_t                          mixBufferSize;
+        uint32_t                        activeSleepTime;
+        uint32_t                        idleSleepTime;
+        uint32_t                        sleepTime;
+        // mixerStatus was local to the while !exitingPending loop
+        mixer_state                     mixerStatus;
+
+        // FIXME move these declarations into the specific sub-class that needs them
+        // MIXER only
+        bool                            longStandbyExit;
+        uint32_t                        sleepTimeShift;
+        // MIXER and DUPLICATING only
+        mixer_state mPrevMixerStatus; // previous status returned by prepareTracks_l()
+        // DIRECT only
+        nsecs_t                         standbyDelay;
+        // activeTrack was local to the while !exitingPending loop
+        sp<Track>                       activeTrack;
+        // DUPLICATING only
+        SortedVector < sp<OutputTrack> >  outputTracks;
+        uint32_t                        writeFrames;
+        SortedVector < sp<OutputTrack> >  mOutputTracks;
     };
 
     class MixerThread : public PlaybackThread {
@@ -909,7 +964,6 @@
         virtual             ~MixerThread();
 
         // Thread virtuals
-        virtual     bool        threadLoop();
 
                     void        invalidateTracks(audio_stream_type_t streamType);
         virtual     bool        checkForNewParameters_l();
@@ -920,14 +974,17 @@
                     // pending set of tracks to remove via Vector 'tracksToRemove'.  The caller is
                     // responsible for clearing or destroying this Vector later on, when it
                     // is safe to do so. That will drop the final ref count and destroy the tracks.
-                    mixer_state prepareTracks_l(Vector< sp<Track> > *tracksToRemove);
+        virtual     mixer_state prepareTracks_l(Vector< sp<Track> > *tracksToRemove);
         virtual     int         getTrackName_l();
         virtual     void        deleteTrackName_l(int name);
         virtual     uint32_t    idleSleepTimeUs();
         virtual     uint32_t    suspendSleepTimeUs();
 
+        // threadLoop snippets
+        virtual     void        threadLoop_mix();
+        virtual     void        threadLoop_sleepTime();
+
                     AudioMixer* mAudioMixer;
-                    mixer_state mPrevMixerStatus; // previous status returned by prepareTracks_l()
     };
 
     class DirectOutputThread : public PlaybackThread {
@@ -938,7 +995,6 @@
         virtual                 ~DirectOutputThread();
 
         // Thread virtuals
-        virtual     bool        threadLoop();
 
         virtual     bool        checkForNewParameters_l();
 
@@ -949,8 +1005,11 @@
         virtual     uint32_t    idleSleepTimeUs();
         virtual     uint32_t    suspendSleepTimeUs();
 
-    private:
-        void applyVolume(uint16_t leftVol, uint16_t rightVol, bool ramp);
+        // threadLoop snippets
+        virtual     mixer_state threadLoop_prepareTracks_l(sp<Track>& trackToRemove);
+        virtual     void        threadLoop_mix();
+        virtual     void        threadLoop_sleepTime();
+        virtual     void        applyVolume();
 
         // volumes last sent to audio HAL with stream->set_volume()
         // FIXME use standard representation and names
@@ -958,6 +1017,12 @@
         float mRightVolFloat;
         uint16_t mLeftVolShort;
         uint16_t mRightVolShort;
+
+        // FIXME rename these former local variables of threadLoop to standard names
+        // next 3 were local to the while !exitingPending loop
+        bool rampVolume;
+        uint16_t leftVol;
+        uint16_t rightVol;
     };
 
     class DuplicatingThread : public MixerThread {
@@ -967,7 +1032,6 @@
         virtual                 ~DuplicatingThread();
 
         // Thread virtuals
-        virtual     bool        threadLoop();
                     void        addOutputTrack(MixerThread* thread);
                     void        removeOutputTrack(MixerThread* thread);
                     uint32_t    waitTimeMs() { return mWaitTimeMs; }
@@ -976,9 +1040,15 @@
 
     private:
                     bool        outputsReady(const SortedVector<sp<OutputTrack> > &outputTracks);
-                    void        updateWaitTime();
+    protected:
+        // threadLoop snippets
+        virtual     void        threadLoop_mix();
+        virtual     void        threadLoop_sleepTime();
+        virtual     void        threadLoop_write();
+        virtual     void        threadLoop_standby();
+        virtual     void        updateWaitTime();
+    private:
 
-        SortedVector < sp<OutputTrack> >  mOutputTracks;
                     uint32_t    mWaitTimeMs;
     };
 
@@ -1086,8 +1156,11 @@
                         uint32_t device);
                 virtual     ~RecordThread();
 
+        // Thread
         virtual bool        threadLoop();
         virtual status_t    readyToRun();
+
+        // RefBase
         virtual void        onFirstRef();
 
         virtual status_t    initCheck() const { return (mInput == NULL) ? NO_INIT : NO_ERROR; }
diff --git a/services/java/com/android/server/ConnectivityService.java b/services/java/com/android/server/ConnectivityService.java
index eab60a7..352decf 100644
--- a/services/java/com/android/server/ConnectivityService.java
+++ b/services/java/com/android/server/ConnectivityService.java
@@ -2179,8 +2179,9 @@
             String dnsString = dns.getHostAddress();
             if (changed || !dnsString.equals(SystemProperties.get("net.dns" + j + "." + pid))) {
                 changed = true;
-                SystemProperties.set("net.dns" + j++ + "." + pid, dns.getHostAddress());
+                SystemProperties.set("net.dns" + j + "." + pid, dns.getHostAddress());
             }
+            j++;
         }
         return changed;
     }
diff --git a/services/java/com/android/server/PowerManagerService.java b/services/java/com/android/server/PowerManagerService.java
index 7b4372f..d9d3f4e 100644
--- a/services/java/com/android/server/PowerManagerService.java
+++ b/services/java/com/android/server/PowerManagerService.java
@@ -45,6 +45,7 @@
 import android.os.IBinder;
 import android.os.IPowerManager;
 import android.os.LocalPowerManager;
+import android.os.Message;
 import android.os.Power;
 import android.os.PowerManager;
 import android.os.Process;
@@ -57,6 +58,7 @@
 import android.util.Log;
 import android.util.Slog;
 import android.view.WindowManagerPolicy;
+import static android.view.WindowManagerPolicy.OFF_BECAUSE_OF_PROX_SENSOR;
 import static android.provider.Settings.System.DIM_SCREEN;
 import static android.provider.Settings.System.SCREEN_BRIGHTNESS;
 import static android.provider.Settings.System.SCREEN_BRIGHTNESS_MODE;
@@ -76,6 +78,7 @@
 
 public class PowerManagerService extends IPowerManager.Stub
         implements LocalPowerManager, Watchdog.Monitor {
+    private static final int NOMINAL_FRAME_TIME_MS = 1000/60;
 
     private static final String TAG = "PowerManagerService";
     static final String PARTIAL_NAME = "PowerManagerService";
@@ -131,6 +134,7 @@
     private static final int DEFAULT_SCREEN_BRIGHTNESS = 192;
 
     // flags for setPowerState
+    private static final int ALL_LIGHTS_OFF         = 0x00000000;
     private static final int SCREEN_ON_BIT          = 0x00000001;
     private static final int SCREEN_BRIGHT_BIT      = 0x00000002;
     private static final int BUTTON_BRIGHT_BIT      = 0x00000004;
@@ -157,11 +161,12 @@
     // used for noChangeLights in setPowerState()
     private static final int LIGHTS_MASK        = SCREEN_BRIGHT_BIT | BUTTON_BRIGHT_BIT | KEYBOARD_BRIGHT_BIT;
 
+    // animate screen lights in PowerManager (as opposed to SurfaceFlinger)
     boolean mAnimateScreenLights = true;
 
-    static final int ANIM_STEPS = 60/4;
+    static final int ANIM_STEPS = 60; // nominal # of frames at 60Hz
     // Slower animation for autobrightness changes
-    static final int AUTOBRIGHTNESS_ANIM_STEPS = 60;
+    static final int AUTOBRIGHTNESS_ANIM_STEPS = 2 * ANIM_STEPS;
     // Number of steps when performing a more immediate brightness change.
     static final int IMMEDIATE_ANIM_STEPS = 4;
 
@@ -221,12 +226,11 @@
     private UnsynchronizedWakeLock mPreventScreenOnPartialLock;
     private UnsynchronizedWakeLock mProximityPartialLock;
     private HandlerThread mHandlerThread;
-    private HandlerThread mScreenOffThread;
     private Handler mScreenOffHandler;
+    private Handler mScreenBrightnessHandler;
     private Handler mHandler;
     private final TimeoutTask mTimeoutTask = new TimeoutTask();
-    private final BrightnessState mScreenBrightness
-            = new BrightnessState(SCREEN_BRIGHT_BIT);
+    private ScreenBrightnessAnimator mScreenBrightnessAnimator;
     private boolean mStillNeedSleepNotification;
     private boolean mIsPowered = false;
     private IActivityManager mActivityService;
@@ -271,6 +275,7 @@
     private int mWarningSpewThrottleCount;
     private long mWarningSpewThrottleTime;
     private int mAnimationSetting = ANIM_SETTING_OFF;
+    private float mWindowScaleAnimation;
 
     // Must match with the ISurfaceComposer constants in C++.
     private static final int ANIM_SETTING_ON = 0x01;
@@ -285,7 +290,8 @@
     private static final boolean mSpew = false;
     private static final boolean mDebugProximitySensor = (false || mSpew);
     private static final boolean mDebugLightSensor = (false || mSpew);
-    
+    private static final boolean mDebugLightAnimation = (false || mSpew);
+
     private native void nativeInit();
     private native void nativeSetPowerState(boolean screenOn, boolean screenBright);
     private native void nativeStartSurfaceFlingerAnimation(int mode);
@@ -487,10 +493,10 @@
                 // recalculate everything
                 setScreenOffTimeoutsLocked();
 
-                final float windowScale = getFloat(WINDOW_ANIMATION_SCALE, 1.0f);
+                mWindowScaleAnimation = getFloat(WINDOW_ANIMATION_SCALE, 1.0f);
                 final float transitionScale = getFloat(TRANSITION_ANIMATION_SCALE, 1.0f);
                 mAnimationSetting = 0;
-                if (windowScale > 0.5f) {
+                if (mWindowScaleAnimation > 0.5f) {
                     mAnimationSetting |= ANIM_SETTING_OFF;
                 }
                 if (transitionScale > 0.5f) {
@@ -540,28 +546,20 @@
         }
 
         mInitComplete = false;
-        mScreenOffThread = new HandlerThread("PowerManagerService.mScreenOffThread") {
-            @Override
-            protected void onLooperPrepared() {
-                mScreenOffHandler = new Handler();
-                synchronized (mScreenOffThread) {
-                    mInitComplete = true;
-                    mScreenOffThread.notifyAll();
-                }
-            }
-        };
-        mScreenOffThread.start();
+        mScreenBrightnessAnimator = new ScreenBrightnessAnimator("mScreenBrightnessUpdaterThread",
+                Process.THREAD_PRIORITY_DISPLAY);
+        mScreenBrightnessAnimator.start();
 
-        synchronized (mScreenOffThread) {
+        synchronized (mScreenBrightnessAnimator) {
             while (!mInitComplete) {
                 try {
-                    mScreenOffThread.wait();
+                    mScreenBrightnessAnimator.wait();
                 } catch (InterruptedException e) {
                     // Ignore
                 }
             }
         }
-        
+
         mInitComplete = false;
         mHandlerThread = new HandlerThread("PowerManagerService") {
             @Override
@@ -581,7 +579,7 @@
                 }
             }
         }
-        
+
         nativeInit();
         Power.powerInitNative();
         synchronized (mLocks) {
@@ -1079,7 +1077,6 @@
 
             int oldPokey = mPokey;
             int cumulative = 0;
-            boolean oldAwakeOnSet = mPokeAwakeOnSet;
             boolean awakeOnSet = false;
             for (PokeLock p: mPokeLocks.values()) {
                 cumulative |= p.pokey;
@@ -1199,7 +1196,7 @@
                     + " mLightSensorKeyboardBrightness=" + mLightSensorKeyboardBrightness);
             pw.println("  mUseSoftwareAutoBrightness=" + mUseSoftwareAutoBrightness);
             pw.println("  mAutoBrightessEnabled=" + mAutoBrightessEnabled);
-            mScreenBrightness.dump(pw, "  mScreenBrightness: ");
+            mScreenBrightnessAnimator.dump(pw, "  mScreenBrightnessAnimator: ");
 
             int N = mLocks.size();
             pw.println();
@@ -1431,7 +1428,7 @@
 
     private WindowManagerPolicy.ScreenOnListener mScreenOnListener =
             new WindowManagerPolicy.ScreenOnListener() {
-                @Override public void onScreenOn() {
+                public void onScreenOn() {
                     synchronized (mLocks) {
                         if (mPreparingForScreenOn) {
                             mPreparingForScreenOn = false;
@@ -1720,7 +1717,8 @@
                             + Integer.toHexString(mPowerState)
                             + " mSkippedScreenOn=" + mSkippedScreenOn);
                 }
-                mScreenBrightness.forceValueLocked(Power.BRIGHTNESS_OFF);
+                mScreenBrightnessHandler.removeMessages(ScreenBrightnessAnimator.ANIMATE_LIGHTS);
+                mScreenBrightnessAnimator.animateTo(Power.BRIGHTNESS_OFF, SCREEN_BRIGHT_BIT, 0);
             }
         }
         int err = Power.setScreenState(on);
@@ -1879,7 +1877,7 @@
                     }
                     mPowerState &= ~SCREEN_ON_BIT;
                     mScreenOffReason = reason;
-                    if (!mScreenBrightness.animating) {
+                    if (!mScreenBrightnessAnimator.isAnimating()) {
                         err = screenOffFinishedAnimatingLocked(reason);
                     } else {
                         err = 0;
@@ -1953,11 +1951,11 @@
 
         // If the screen is not currently on, we will want to delay actually
         // turning the lights on if we are still getting the UI put up.
-        if ((oldState&SCREEN_ON_BIT) == 0 || mSkippedScreenOn) {
+        if ((oldState & SCREEN_ON_BIT) == 0 || mSkippedScreenOn) {
             // Don't turn screen on until we know we are really ready to.
             // This is to avoid letting the screen go on before things like the
             // lock screen have been displayed.
-            if ((mSkippedScreenOn=shouldDeferScreenOnLocked())) {
+            if ((mSkippedScreenOn = shouldDeferScreenOnLocked())) {
                 newState &= ~(SCREEN_ON_BIT|SCREEN_BRIGHT_BIT);
             }
         }
@@ -2017,7 +2015,7 @@
                     case SCREEN_BRIGHT_BIT:
                     default:
                         // not possible
-                        nominalCurrentValue = (int)mScreenBrightness.curValue;
+                        nominalCurrentValue = (int)mScreenBrightnessAnimator.getCurrentBrightness();
                         break;
                 }
             }
@@ -2067,8 +2065,8 @@
                 Binder.restoreCallingIdentity(identity);
             }
             if (!mSkippedScreenOn) {
-                mScreenBrightness.setTargetLocked(brightness, steps,
-                        INITIAL_SCREEN_BRIGHTNESS, nominalCurrentValue);
+                int dt = steps * NOMINAL_FRAME_TIME_MS;
+                mScreenBrightnessAnimator.animateTo(brightness, SCREEN_BRIGHT_BIT, dt);
                 if (DEBUG_SCREEN_ON) {
                     RuntimeException e = new RuntimeException("here");
                     e.fillInStackTrace();
@@ -2111,152 +2109,162 @@
         }
     }
 
-    private void setLightBrightness(int mask, int value) {
-        int brightnessMode = (mAutoBrightessEnabled
+    /**
+     * Note: by design this class does not hold mLocks while calling native methods.
+     * Nor should it. Ever.
+     */
+    class ScreenBrightnessAnimator extends HandlerThread {
+        static final int ANIMATE_LIGHTS = 10;
+        static final int ANIMATE_POWER_OFF = 11;
+        volatile int startValue;
+        volatile int endValue;
+        volatile int currentValue;
+        private int currentMask;
+        private int duration;
+        private long startTimeMillis;
+        private final String prefix;
+
+        public ScreenBrightnessAnimator(String name, int priority) {
+            super(name, priority);
+            prefix = name;
+        }
+
+        @Override
+        protected void onLooperPrepared() {
+            mScreenBrightnessHandler = new Handler() {
+                public void handleMessage(Message msg) {
+                    int brightnessMode = (mAutoBrightessEnabled && !mInitialAnimation
                             ? LightsService.BRIGHTNESS_MODE_SENSOR
                             : LightsService.BRIGHTNESS_MODE_USER);
-        if ((mask & SCREEN_BRIGHT_BIT) != 0) {
-            if (DEBUG_SCREEN_ON) {
-                RuntimeException e = new RuntimeException("here");
-                e.fillInStackTrace();
-                Slog.i(TAG, "Set LCD brightness: " + value, e);
+                    if (msg.what == ANIMATE_LIGHTS) {
+                        final int mask = msg.arg1;
+                        int value = msg.arg2;
+                        long tStart = SystemClock.uptimeMillis();
+                        if ((mask & SCREEN_BRIGHT_BIT) != 0) {
+                            if (mDebugLightAnimation) Log.v(TAG, "Set brightness: " + value);
+                            mLcdLight.setBrightness(value, brightnessMode);
+                        }
+                        long elapsed = SystemClock.uptimeMillis() - tStart;
+                        if ((mask & BUTTON_BRIGHT_BIT) != 0) {
+                            mButtonLight.setBrightness(value);
+                        }
+                        if ((mask & KEYBOARD_BRIGHT_BIT) != 0) {
+                            mKeyboardLight.setBrightness(value);
+                        }
+
+                        if (elapsed > 100) {
+                            Log.e(TAG, "Excessive delay setting brightness: " + elapsed
+                                    + "ms, mask=" + mask);
+                        }
+
+                        // Throttle brightness updates to frame refresh rate
+                        int delay = elapsed < NOMINAL_FRAME_TIME_MS ? NOMINAL_FRAME_TIME_MS : 0;
+                        synchronized(this) {
+                            currentValue = value;
+                        }
+                        animateInternal(mask, false, delay);
+                    } else if (msg.what == ANIMATE_POWER_OFF) {
+                        int mode = msg.arg1;
+                        nativeStartSurfaceFlingerAnimation(mode);
+                    }
+                }
+            };
+            synchronized (this) {
+                mInitComplete = true;
+                notifyAll();
             }
-            mLcdLight.setBrightness(value, brightnessMode);
         }
-        if ((mask & BUTTON_BRIGHT_BIT) != 0) {
-            mButtonLight.setBrightness(value);
+
+        private void animateInternal(int mask, boolean turningOff, int delay) {
+            synchronized (this) {
+                if (currentValue != endValue) {
+                    final long now = SystemClock.elapsedRealtime();
+                    final int elapsed = (int) (now - startTimeMillis);
+                    int newValue;
+                    if (elapsed < duration) {
+                        int delta = endValue - startValue;
+                        newValue = startValue + delta * elapsed / duration;
+                        newValue = Math.max(Power.BRIGHTNESS_OFF, newValue);
+                        newValue = Math.min(Power.BRIGHTNESS_ON, newValue);
+                    } else {
+                        newValue = endValue;
+                        mInitialAnimation = false;
+                    }
+
+                    if (mDebugLightAnimation) {
+                        Log.v(TAG, "Animating light: " + "start:" + startValue
+                                + ", end:" + endValue + ", elapsed:" + elapsed
+                                + ", duration:" + duration + ", current:" + currentValue
+                                + ", delay:" + delay);
+                    }
+
+                    if (turningOff && !mHeadless && !mAnimateScreenLights) {
+                        int mode = mScreenOffReason == OFF_BECAUSE_OF_PROX_SENSOR
+                                ? 0 : mAnimationSetting;
+                        if (mDebugLightAnimation) Log.v(TAG, "Doing power-off anim, mode=" + mode);
+                        mScreenBrightnessHandler.obtainMessage(ANIMATE_POWER_OFF, mode, 0)
+                                .sendToTarget();
+                    }
+                    Message msg = mScreenBrightnessHandler
+                            .obtainMessage(ANIMATE_LIGHTS, mask, newValue);
+                    mScreenBrightnessHandler.sendMessageDelayed(msg, delay);
+                }
+            }
         }
-        if ((mask & KEYBOARD_BRIGHT_BIT) != 0) {
-            mKeyboardLight.setBrightness(value);
+
+        public void dump(PrintWriter pw, String string) {
+            pw.println(prefix + "animating: " + "start:" + startValue + ", end:" + endValue
+                    + ", duration:" + duration + ", current:" + currentValue);
+        }
+
+        public void animateTo(int target, int mask, int animationDuration) {
+            synchronized(this) {
+                startValue = currentValue;
+                endValue = target;
+                currentMask = mask;
+                duration = (int) (mWindowScaleAnimation * animationDuration);
+                startTimeMillis = SystemClock.elapsedRealtime();
+                mInitialAnimation = currentValue == 0 && target > 0;
+
+                if (mDebugLightAnimation) {
+                    Log.v(TAG, "animateTo(target=" + target + ", mask=" + mask
+                            + ", duration=" + animationDuration +")"
+                            + ", currentValue=" + currentValue
+                            + ", startTime=" + startTimeMillis);
+                }
+
+                if (target != currentValue) {
+                    final boolean turningOff = endValue == Power.BRIGHTNESS_OFF;
+                    if (turningOff && ((mask & (SCREEN_ON_BIT | SCREEN_BRIGHT_BIT)) != 0)) {
+                        // Cancel all pending animations since we're turning off
+                        mScreenBrightnessHandler.removeCallbacksAndMessages(null);
+                        screenOffFinishedAnimatingLocked(mScreenOffReason);
+                        duration = 200; // TODO: how long should this be?
+                    }
+                    animateInternal(mask, turningOff, 0);
+                }
+            }
+        }
+
+        public int getCurrentBrightness() {
+            synchronized (this) {
+                return currentValue;
+            }
+        }
+
+        public boolean isAnimating() {
+            synchronized (this) {
+                return currentValue != endValue;
+            }
+        }
+
+        public void cancelAnimation() {
+            animateTo(endValue, currentMask, 0);
         }
     }
 
-    class BrightnessState implements Runnable {
-        final int mask;
-
-        boolean initialized;
-        int targetValue;
-        float curValue;
-        float delta;
-        boolean animating;
-
-        BrightnessState(int m) {
-            mask = m;
-        }
-
-        public void dump(PrintWriter pw, String prefix) {
-            pw.println(prefix + "animating=" + animating
-                    + " targetValue=" + targetValue
-                    + " curValue=" + curValue
-                    + " delta=" + delta);
-        }
-
-        void forceValueLocked(int value) {
-            targetValue = -1;
-            curValue = value;
-            setLightBrightness(mask, value);
-            if (animating) {
-                finishAnimationLocked(false, value);
-            }
-        }
-
-        void setTargetLocked(int target, int stepsToTarget, int initialValue,
-                int nominalCurrentValue) {
-            if (!initialized) {
-                initialized = true;
-                curValue = (float)initialValue;
-            } else if (targetValue == target) {
-                return;
-            }
-            targetValue = target;
-            delta = (targetValue -
-                    (nominalCurrentValue >= 0 ? nominalCurrentValue : curValue))
-                    / stepsToTarget;
-            if (mSpew || DEBUG_SCREEN_ON) {
-                String noticeMe = nominalCurrentValue == curValue ? "" : "  ******************";
-                Slog.i(TAG, "setTargetLocked mask=" + mask + " curValue=" + curValue
-                        + " target=" + target + " targetValue=" + targetValue + " delta=" + delta
-                        + " nominalCurrentValue=" + nominalCurrentValue
-                        + noticeMe);
-            }
-            animating = true;
-
-            if (mSpew) {
-                Slog.i(TAG, "scheduling light animator");
-            }
-            mScreenOffHandler.removeCallbacks(this);
-            mScreenOffHandler.post(this);
-        }
-
-        boolean stepLocked() {
-            if (!animating) return false;
-            if (false && mSpew) {
-                Slog.i(TAG, "Step target " + mask + ": cur=" + curValue
-                        + " target=" + targetValue + " delta=" + delta);
-            }
-            curValue += delta;
-            int curIntValue = (int)curValue;
-            boolean more = true;
-            if (delta == 0) {
-                curValue = curIntValue = targetValue;
-                more = false;
-            } else if (delta > 0) {
-                if (curIntValue >= targetValue) {
-                    curValue = curIntValue = targetValue;
-                    more = false;
-                }
-            } else {
-                if (curIntValue <= targetValue) {
-                    curValue = curIntValue = targetValue;
-                    more = false;
-                }
-            }
-            if (mSpew) Slog.d(TAG, "Animating curIntValue=" + curIntValue + ": " + mask);
-            setLightBrightness(mask, curIntValue);
-            finishAnimationLocked(more, curIntValue);
-            return more;
-        }
-
-        void jumpToTargetLocked() {
-            if (mSpew) Slog.d(TAG, "jumpToTargetLocked targetValue=" + targetValue + ": " + mask);
-            setLightBrightness(mask, targetValue);
-            final int tv = targetValue;
-            curValue = tv;
-            targetValue = -1;
-            finishAnimationLocked(false, tv);
-        }
-
-        private void finishAnimationLocked(boolean more, int curIntValue) {
-            animating = more;
-            if (!more) {
-                if (mask == SCREEN_BRIGHT_BIT && curIntValue == Power.BRIGHTNESS_OFF) {
-                    screenOffFinishedAnimatingLocked(mScreenOffReason);
-                }
-            }
-        }
-
-        public void run() {
-            synchronized (mLocks) {
-                // we're turning off
-                final boolean turningOff = animating && targetValue == Power.BRIGHTNESS_OFF;
-                if (mAnimateScreenLights || !turningOff) {
-                    long now = SystemClock.uptimeMillis();
-                    boolean more = mScreenBrightness.stepLocked();
-                    if (more) {
-                        mScreenOffHandler.postAtTime(this, now+(1000/60));
-                    }
-                } else {
-                    if (!mHeadless) {
-                        // It's pretty scary to hold mLocks for this long, and we should
-                        // redesign this, but it works for now.
-                        nativeStartSurfaceFlingerAnimation(
-                                mScreenOffReason == WindowManagerPolicy.OFF_BECAUSE_OF_PROX_SENSOR
-                                ? 0 : mAnimationSetting);
-                    }
-                    mScreenBrightness.jumpToTargetLocked();
-                }
-            }
-        }
+    private void setLightBrightness(int mask, int value) {
+        mScreenBrightnessAnimator.animateTo(value, mask, 0);
     }
 
     private int getPreferredBrightness() {
@@ -2326,7 +2334,8 @@
     }
 
     private boolean isScreenTurningOffLocked() {
-        return (mScreenBrightness.animating && mScreenBrightness.targetValue == 0);
+        return (mScreenBrightnessAnimator.isAnimating()
+                && mScreenBrightnessAnimator.endValue == Power.BRIGHTNESS_OFF);
     }
 
     private boolean shouldLog(long time) {
@@ -2347,7 +2356,7 @@
     private void forceUserActivityLocked() {
         if (isScreenTurningOffLocked()) {
             // cancel animation so userActivity will succeed
-            mScreenBrightness.animating = false;
+            mScreenBrightnessAnimator.cancelAnimation();
         }
         boolean savedActivityAllowed = mUserActivityAllowed;
         mUserActivityAllowed = true;
@@ -2526,6 +2535,8 @@
         }
     };
 
+    private boolean mInitialAnimation; // used to prevent lightsensor changes while turning on
+
     private void dockStateChanged(int state) {
         synchronized (mLocks) {
             mIsDocked = (state != Intent.EXTRA_DOCK_STATE_UNDOCKED);
@@ -2587,10 +2598,11 @@
                 }
 
                 if (mAutoBrightessEnabled && mScreenBrightnessOverride < 0) {
-                    if (!mSkippedScreenOn) {
-                        mScreenBrightness.setTargetLocked(lcdValue,
-                                immediate ? IMMEDIATE_ANIM_STEPS : AUTOBRIGHTNESS_ANIM_STEPS,
-                                INITIAL_SCREEN_BRIGHTNESS, (int)mScreenBrightness.curValue);
+                    if (!mSkippedScreenOn && !mInitialAnimation) {
+                        int steps = immediate ? IMMEDIATE_ANIM_STEPS : AUTOBRIGHTNESS_ANIM_STEPS;
+                        mScreenBrightnessAnimator.cancelAnimation();
+                        mScreenBrightnessAnimator.animateTo(lcdValue,
+                                SCREEN_BRIGHT_BIT, steps * NOMINAL_FRAME_TIME_MS);
                     }
                 }
                 if (mButtonBrightnessOverride < 0) {
@@ -2642,7 +2654,7 @@
                 synchronized (this) {
                     ShutdownThread.reboot(mContext, finalReason, false);
                 }
-                
+
             }
         };
         // ShutdownThread must run on a looper capable of displaying the UI.
@@ -2996,9 +3008,7 @@
             } finally {
                 Binder.restoreCallingIdentity(identity);
             }
-
-            mScreenBrightness.targetValue = brightness;
-            mScreenBrightness.jumpToTargetLocked();
+            mScreenBrightnessAnimator.animateTo(brightness, SCREEN_BRIGHT_BIT, 0);
         }
     }
 
diff --git a/services/java/com/android/server/UpdateLockService.java b/services/java/com/android/server/UpdateLockService.java
index 5df1928..1ffd196 100644
--- a/services/java/com/android/server/UpdateLockService.java
+++ b/services/java/com/android/server/UpdateLockService.java
@@ -77,7 +77,7 @@
             Intent intent = new Intent(UpdateLock.UPDATE_LOCK_CHANGED)
                     .putExtra(UpdateLock.NOW_IS_CONVENIENT, state)
                     .putExtra(UpdateLock.TIMESTAMP, System.currentTimeMillis())
-                    .addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);
+                    .addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
             mContext.sendStickyBroadcast(intent);
         } finally {
             Binder.restoreCallingIdentity(oldIdent);
diff --git a/services/java/com/android/server/WifiService.java b/services/java/com/android/server/WifiService.java
index f09c43f..8363e6e 100644
--- a/services/java/com/android/server/WifiService.java
+++ b/services/java/com/android/server/WifiService.java
@@ -263,47 +263,46 @@
                     ac.connect(mContext, this, msg.replyTo);
                     break;
                 }
-                case WifiManager.CMD_ENABLE_TRAFFIC_STATS_POLL: {
+                case WifiManager.ENABLE_TRAFFIC_STATS_POLL: {
                     mEnableTrafficStatsPoll = (msg.arg1 == 1);
                     mTrafficStatsPollToken++;
                     if (mEnableTrafficStatsPoll) {
                         notifyOnDataActivity();
-                        sendMessageDelayed(Message.obtain(this, WifiManager.CMD_TRAFFIC_STATS_POLL,
+                        sendMessageDelayed(Message.obtain(this, WifiManager.TRAFFIC_STATS_POLL,
                                 mTrafficStatsPollToken, 0), POLL_TRAFFIC_STATS_INTERVAL_MSECS);
                     }
                     break;
                 }
-                case WifiManager.CMD_TRAFFIC_STATS_POLL: {
+                case WifiManager.TRAFFIC_STATS_POLL: {
                     if (msg.arg1 == mTrafficStatsPollToken) {
                         notifyOnDataActivity();
-                        sendMessageDelayed(Message.obtain(this, WifiManager.CMD_TRAFFIC_STATS_POLL,
+                        sendMessageDelayed(Message.obtain(this, WifiManager.TRAFFIC_STATS_POLL,
                                 mTrafficStatsPollToken, 0), POLL_TRAFFIC_STATS_INTERVAL_MSECS);
                     }
                     break;
                 }
-                case WifiManager.CMD_CONNECT_NETWORK: {
-                    if (msg.obj != null) {
-                        mWifiStateMachine.connectNetwork((WifiConfiguration)msg.obj);
-                    } else {
-                        mWifiStateMachine.connectNetwork(msg.arg1);
-                    }
+                case WifiManager.CONNECT_NETWORK: {
+                    mWifiStateMachine.sendMessage(Message.obtain(msg));
                     break;
                 }
-                case WifiManager.CMD_SAVE_NETWORK: {
-                    mWifiStateMachine.saveNetwork((WifiConfiguration)msg.obj);
+                case WifiManager.SAVE_NETWORK: {
+                    mWifiStateMachine.sendMessage(Message.obtain(msg));
                     break;
                 }
-                case WifiManager.CMD_FORGET_NETWORK: {
-                    mWifiStateMachine.forgetNetwork(msg.arg1);
+                case WifiManager.FORGET_NETWORK: {
+                    mWifiStateMachine.sendMessage(Message.obtain(msg));
                     break;
                 }
-                case WifiManager.CMD_START_WPS: {
-                    //replyTo has the original source
-                    mWifiStateMachine.startWps(msg.replyTo, (WpsInfo)msg.obj);
+                case WifiManager.START_WPS: {
+                    mWifiStateMachine.sendMessage(Message.obtain(msg));
                     break;
                 }
-                case WifiManager.CMD_DISABLE_NETWORK: {
-                    mWifiStateMachine.disableNetwork(msg.replyTo, msg.arg1, msg.arg2);
+                case WifiManager.CANCEL_WPS: {
+                    mWifiStateMachine.sendMessage(Message.obtain(msg));
+                    break;
+                }
+                case WifiManager.DISABLE_NETWORK: {
+                    mWifiStateMachine.sendMessage(Message.obtain(msg));
                     break;
                 }
                 default: {
@@ -1594,10 +1593,10 @@
         Message msg;
         if (mNetworkInfo.getDetailedState() == DetailedState.CONNECTED && !mScreenOff) {
             msg = Message.obtain(mAsyncServiceHandler,
-                    WifiManager.CMD_ENABLE_TRAFFIC_STATS_POLL, 1, 0);
+                    WifiManager.ENABLE_TRAFFIC_STATS_POLL, 1, 0);
         } else {
             msg = Message.obtain(mAsyncServiceHandler,
-                    WifiManager.CMD_ENABLE_TRAFFIC_STATS_POLL, 0, 0);
+                    WifiManager.ENABLE_TRAFFIC_STATS_POLL, 0, 0);
         }
         msg.sendToTarget();
     }
diff --git a/services/java/com/android/server/pm/PackageManagerService.java b/services/java/com/android/server/pm/PackageManagerService.java
index e471a3f..4b4c8ab 100644
--- a/services/java/com/android/server/pm/PackageManagerService.java
+++ b/services/java/com/android/server/pm/PackageManagerService.java
@@ -1132,6 +1132,27 @@
                             ? (UPDATE_PERMISSIONS_REPLACE_PKG|UPDATE_PERMISSIONS_REPLACE_ALL)
                             : 0));
 
+            // Verify that all of the preferred activity components actually
+            // exist.  It is possible for applications to be updated and at
+            // that point remove a previously declared activity component that
+            // had been set as a preferred activity.  We try to clean this up
+            // the next time we encounter that preferred activity, but it is
+            // possible for the user flow to never be able to return to that
+            // situation so here we do a sanity check to make sure we haven't
+            // left any junk around.
+            ArrayList<PreferredActivity> removed = new ArrayList<PreferredActivity>();
+            for (PreferredActivity pa : mSettings.mPreferredActivities.filterSet()) {
+                if (mActivities.mActivities.get(pa.mPref.mComponent) == null) {
+                    removed.add(pa);
+                }
+            }
+            for (int i=0; i<removed.size(); i++) {
+                PreferredActivity pa = removed.get(i);
+                Slog.w(TAG, "Removing dangling preferred activity: "
+                        + pa.mPref.mComponent);
+                mSettings.mPreferredActivities.removeFilter(pa);
+            }
+
             // can downgrade to reader
             mSettings.writeLPr();
 
@@ -2295,31 +2316,40 @@
                             Log.v(TAG, "  null");
                         }
                     }
-                    if (ai != null) {
-                        for (int j=0; j<N; j++) {
-                            final ResolveInfo ri = query.get(j);
-                            if (!ri.activityInfo.applicationInfo.packageName
-                                    .equals(ai.applicationInfo.packageName)) {
-                                continue;
-                            }
-                            if (!ri.activityInfo.name.equals(ai.name)) {
-                                continue;
-                            }
-
-                            // Okay we found a previously set preferred app.
-                            // If the result set is different from when this
-                            // was created, we need to clear it and re-ask the
-                            // user their preference.
-                            if (!pa.mPref.sameSet(query, priority)) {
-                                Slog.i(TAG, "Result set changed, dropping preferred activity for "
-                                        + intent + " type " + resolvedType);
-                                mSettings.mPreferredActivities.removeFilter(pa);
-                                return null;
-                            }
-
-                            // Yay!
-                            return ri;
+                    if (ai == null) {
+                        // This previously registered preferred activity
+                        // component is no longer known.  Most likely an update
+                        // to the app was installed and in the new version this
+                        // component no longer exists.  Clean it up by removing
+                        // it from the preferred activities list, and skip it.
+                        Slog.w(TAG, "Removing dangling preferred activity: "
+                                + pa.mPref.mComponent);
+                        mSettings.mPreferredActivities.removeFilter(pa);
+                        continue;
+                    }
+                    for (int j=0; j<N; j++) {
+                        final ResolveInfo ri = query.get(j);
+                        if (!ri.activityInfo.applicationInfo.packageName
+                                .equals(ai.applicationInfo.packageName)) {
+                            continue;
                         }
+                        if (!ri.activityInfo.name.equals(ai.name)) {
+                            continue;
+                        }
+
+                        // Okay we found a previously set preferred app.
+                        // If the result set is different from when this
+                        // was created, we need to clear it and re-ask the
+                        // user their preference.
+                        if (!pa.mPref.sameSet(query, priority)) {
+                            Slog.i(TAG, "Result set changed, dropping preferred activity for "
+                                    + intent + " type " + resolvedType);
+                            mSettings.mPreferredActivities.removeFilter(pa);
+                            return null;
+                        }
+
+                        // Yay!
+                        return ri;
                     }
                 }
             }
@@ -4036,8 +4066,6 @@
 
         // writer
         synchronized (mPackages) {
-            clearPackagePreferredActivitiesLPw(pkg.packageName);
-
             mPackages.remove(pkg.applicationInfo.packageName);
             if (pkg.mPath != null) {
                 mAppDirs.remove(pkg.mPath);
@@ -7118,16 +7146,7 @@
                             mSettings.updateSharedUserPermsLPw(deletedPs, mGlobalGids);
                         }
                     }
-                }
-                // remove from preferred activities.
-                ArrayList<PreferredActivity> removed = new ArrayList<PreferredActivity>();
-                for (PreferredActivity pa : mSettings.mPreferredActivities.filterSet()) {
-                    if (pa.mPref.mComponent.getPackageName().equals(deletedPs.name)) {
-                        removed.add(pa);
-                    }
-                }
-                for (PreferredActivity pa : removed) {
-                    mSettings.mPreferredActivities.removeFilter(pa);
+                    clearPackagePreferredActivitiesLPw(deletedPs.name);
                 }
             }
             // can downgrade to reader
@@ -7569,17 +7588,27 @@
                         android.Manifest.permission.SET_PREFERRED_APPLICATIONS, null);
             }
             
+            ArrayList<PreferredActivity> removed = null;
             Iterator<PreferredActivity> it = mSettings.mPreferredActivities.filterIterator();
             String action = filter.getAction(0);
             String category = filter.getCategory(0);
             while (it.hasNext()) {
                 PreferredActivity pa = it.next();
                 if (pa.getAction(0).equals(action) && pa.getCategory(0).equals(category)) {
-                    it.remove();
-                    Log.i(TAG, "Removed preferred activity " + pa.mPref.mComponent + ":");
+                    if (removed == null) {
+                        removed = new ArrayList<PreferredActivity>();
+                    }
+                    removed.add(pa);
+                    Log.i(TAG, "Removing preferred activity " + pa.mPref.mComponent + ":");
                     filter.dump(new LogPrinter(Log.INFO, TAG), "  ");
                 }
             }
+            if (removed != null) {
+                for (int i=0; i<removed.size(); i++) {
+                    PreferredActivity pa = removed.get(i);
+                    mSettings.mPreferredActivities.removeFilter(pa);
+                }
+            }
             addPreferredActivity(filter, match, set, activity);
         }
     }
@@ -7611,16 +7640,25 @@
     }
 
     boolean clearPackagePreferredActivitiesLPw(String packageName) {
-        boolean changed = false;
+        ArrayList<PreferredActivity> removed = null;
         Iterator<PreferredActivity> it = mSettings.mPreferredActivities.filterIterator();
         while (it.hasNext()) {
             PreferredActivity pa = it.next();
             if (pa.mPref.mComponent.getPackageName().equals(packageName)) {
-                it.remove();
-                changed = true;
+                if (removed == null) {
+                    removed = new ArrayList<PreferredActivity>();
+                }
+                removed.add(pa);
             }
         }
-        return changed;
+        if (removed != null) {
+            for (int i=0; i<removed.size(); i++) {
+                PreferredActivity pa = removed.get(i);
+                mSettings.mPreferredActivities.removeFilter(pa);
+            }
+            return true;
+        }
+        return false;
     }
 
     public int getPreferredActivities(List<IntentFilter> outFilters,
diff --git a/services/java/com/android/server/wm/AppWindowToken.java b/services/java/com/android/server/wm/AppWindowToken.java
index 0e3d20a..b84fbdb 100644
--- a/services/java/com/android/server/wm/AppWindowToken.java
+++ b/services/java/com/android/server/wm/AppWindowToken.java
@@ -37,7 +37,7 @@
  * Version of WindowToken that is specifically for a particular application (or
  * really activity) that is displaying windows.
  */
-class AppWindowToken extends WindowToken {
+class AppWindowToken extends WindowToken implements WindowManagerService.StepAnimator {
     // Non-null only for application tokens.
     final IApplicationToken appToken;
 
@@ -195,8 +195,28 @@
         }
     }
 
+    @Override
+    public boolean stepAnimation(long currentTime) {
+        if (animation == null) {
+            return false;
+        }
+        transformation.clear();
+        final boolean more = animation.getTransformation(currentTime, transformation);
+        if (WindowManagerService.DEBUG_ANIM) Slog.v(
+            WindowManagerService.TAG, "Stepped animation in " + this +
+            ": more=" + more + ", xform=" + transformation);
+        if (!more) {
+            animation = null;
+            if (WindowManagerService.DEBUG_ANIM) Slog.v(
+                WindowManagerService.TAG, "Finished animation in " + this +
+                " @ " + currentTime);
+        }
+        hasTransformation = more;
+        return more;
+    }
+
     // This must be called while inside a transaction.
-    boolean stepAnimationLocked(long currentTime, int dw, int dh) {
+    boolean startAndFinishAnimationLocked(long currentTime, int dw, int dh) {
         if (!service.mDisplayFrozen && service.mPolicy.isScreenOnFully()) {
             // We will run animations as long as the display isn't frozen.
 
@@ -219,21 +239,8 @@
                     animation.setStartTime(currentTime);
                     animating = true;
                 }
-                transformation.clear();
-                final boolean more = animation.getTransformation(
-                    currentTime, transformation);
-                if (WindowManagerService.DEBUG_ANIM) Slog.v(
-                    WindowManagerService.TAG, "Stepped animation in " + this +
-                    ": more=" + more + ", xform=" + transformation);
-                if (more) {
-                    // we're done!
-                    hasTransformation = true;
-                    return true;
-                }
-                if (WindowManagerService.DEBUG_ANIM) Slog.v(
-                    WindowManagerService.TAG, "Finished animation in " + this +
-                    " @ " + currentTime);
-                animation = null;
+                // we're done!
+                return true;
             }
         } else if (animation != null) {
             // If the display is frozen, and there is a pending animation,
@@ -369,6 +376,7 @@
         return null;
     }
 
+    @Override
     void dump(PrintWriter pw, String prefix) {
         super.dump(pw, prefix);
         if (appToken != null) {
diff --git a/services/java/com/android/server/wm/BlackFrame.java b/services/java/com/android/server/wm/BlackFrame.java
index 10e294b..26289c9 100644
--- a/services/java/com/android/server/wm/BlackFrame.java
+++ b/services/java/com/android/server/wm/BlackFrame.java
@@ -16,6 +16,8 @@
 
 package com.android.server.wm;
 
+import java.io.PrintWriter;
+
 import android.graphics.Matrix;
 import android.graphics.PixelFormat;
 import android.graphics.Rect;
@@ -72,14 +74,31 @@
         }
     }
 
+    final Rect mOuterRect;
+    final Rect mInnerRect;
     final Matrix mTmpMatrix = new Matrix();
     final float[] mTmpFloats = new float[9];
     final BlackSurface[] mBlackSurfaces = new BlackSurface[4];
 
+    public void printTo(String prefix, PrintWriter pw) {
+        pw.print(prefix); pw.print("Outer: "); mOuterRect.printShortString(pw);
+                pw.print(" / Inner: "); mInnerRect.printShortString(pw);
+                pw.println();
+        for (int i=0; i<mBlackSurfaces.length; i++) {
+            BlackSurface bs = mBlackSurfaces[i];
+            pw.print(prefix); pw.print("#"); pw.print(i);
+                    pw.print(": "); pw.print(bs.surface);
+                    pw.print(" left="); pw.print(bs.left);
+                    pw.print(" top="); pw.println(bs.top);
+        }
+    }
+
     public BlackFrame(SurfaceSession session, Rect outer, Rect inner,
             int layer) throws Surface.OutOfResourcesException {
         boolean success = false;
 
+        mOuterRect = new Rect(outer);
+        mInnerRect = new Rect(inner);
         try {
             if (outer.top < inner.top) {
                 mBlackSurfaces[0] = new BlackSurface(session, layer,
diff --git a/services/java/com/android/server/wm/ScreenRotationAnimation.java b/services/java/com/android/server/wm/ScreenRotationAnimation.java
index 04a039f..7ac67b6 100644
--- a/services/java/com/android/server/wm/ScreenRotationAnimation.java
+++ b/services/java/com/android/server/wm/ScreenRotationAnimation.java
@@ -29,7 +29,7 @@
 import android.view.animation.AnimationUtils;
 import android.view.animation.Transformation;
 
-class ScreenRotationAnimation {
+class ScreenRotationAnimation implements WindowManagerService.StepAnimator {
     static final String TAG = "ScreenRotationAnimation";
     static final boolean DEBUG_STATE = false;
     static final boolean DEBUG_TRANSFORMS = false;
@@ -59,6 +59,8 @@
     final Transformation mStartExitTransformation = new Transformation();
     Animation mStartEnterAnimation;
     final Transformation mStartEnterTransformation = new Transformation();
+    Animation mStartFrameAnimation;
+    final Transformation mStartFrameTransformation = new Transformation();
 
     // The finishing animation for the exiting and entering elements.  This
     // animation needs to undo the transformation of the starting animation.
@@ -68,6 +70,8 @@
     final Transformation mFinishExitTransformation = new Transformation();
     Animation mFinishEnterAnimation;
     final Transformation mFinishEnterTransformation = new Transformation();
+    Animation mFinishFrameAnimation;
+    final Transformation mFinishFrameTransformation = new Transformation();
 
     // The current active animation to move from the old to the new rotated
     // state.  Which animation is run here will depend on the old and new
@@ -76,6 +80,8 @@
     final Transformation mRotateExitTransformation = new Transformation();
     Animation mRotateEnterAnimation;
     final Transformation mRotateEnterTransformation = new Transformation();
+    Animation mRotateFrameAnimation;
+    final Transformation mRotateFrameTransformation = new Transformation();
 
     // A previously running rotate animation.  This will be used if we need
     // to switch to a new rotation before finishing the previous one.
@@ -83,26 +89,42 @@
     final Transformation mLastRotateExitTransformation = new Transformation();
     Animation mLastRotateEnterAnimation;
     final Transformation mLastRotateEnterTransformation = new Transformation();
+    Animation mLastRotateFrameAnimation;
+    final Transformation mLastRotateFrameTransformation = new Transformation();
 
     // Complete transformations being applied.
     final Transformation mExitTransformation = new Transformation();
     final Transformation mEnterTransformation = new Transformation();
+    final Transformation mFrameTransformation = new Transformation();
 
     boolean mStarted;
     boolean mAnimRunning;
     boolean mFinishAnimReady;
     long mFinishAnimStartTime;
 
+    final Matrix mFrameInitialMatrix = new Matrix();
     final Matrix mSnapshotInitialMatrix = new Matrix();
     final Matrix mSnapshotFinalMatrix = new Matrix();
     final Matrix mTmpMatrix = new Matrix();
     final float[] mTmpFloats = new float[9];
+    private boolean mMoreRotateEnter;
+    private boolean mMoreRotateExit;
+    private boolean mMoreRotateFrame;
+    private boolean mMoreFinishEnter;
+    private boolean mMoreFinishExit;
+    private boolean mMoreFinishFrame;
+    private boolean mMoreStartEnter;
+    private boolean mMoreStartExit;
+    private boolean mMoreStartFrame;
 
     public void printTo(String prefix, PrintWriter pw) {
         pw.print(prefix); pw.print("mSurface="); pw.print(mSurface);
                 pw.print(" mWidth="); pw.print(mWidth);
                 pw.print(" mHeight="); pw.println(mHeight);
         pw.print(prefix); pw.print("mBlackFrame="); pw.println(mBlackFrame);
+        if (mBlackFrame != null) {
+            mBlackFrame.printTo(prefix + "  ", pw);
+        }
         pw.print(prefix); pw.print("mSnapshotRotation="); pw.print(mSnapshotRotation);
                 pw.print(" mSnapshotDeltaRotation="); pw.print(mSnapshotDeltaRotation);
                 pw.print(" mCurRotation="); pw.println(mCurRotation);
@@ -117,21 +139,29 @@
                 pw.print(" "); mStartExitTransformation.printShortString(pw); pw.println();
         pw.print(prefix); pw.print("mStartEnterAnimation="); pw.print(mStartEnterAnimation);
                 pw.print(" "); mStartEnterTransformation.printShortString(pw); pw.println();
+        pw.print(prefix); pw.print("mStartFrameAnimation="); pw.print(mStartFrameAnimation);
+                pw.print(" "); mStartFrameTransformation.printShortString(pw); pw.println();
         pw.print(prefix); pw.print("mFinishExitAnimation="); pw.print(mFinishExitAnimation);
                 pw.print(" "); mFinishExitTransformation.printShortString(pw); pw.println();
         pw.print(prefix); pw.print("mFinishEnterAnimation="); pw.print(mFinishEnterAnimation);
                 pw.print(" "); mFinishEnterTransformation.printShortString(pw); pw.println();
+        pw.print(prefix); pw.print("mFinishFrameAnimation="); pw.print(mFinishFrameAnimation);
+                pw.print(" "); mFinishFrameTransformation.printShortString(pw); pw.println();
         pw.print(prefix); pw.print("mRotateExitAnimation="); pw.print(mRotateExitAnimation);
                 pw.print(" "); mRotateExitTransformation.printShortString(pw); pw.println();
         pw.print(prefix); pw.print("mRotateEnterAnimation="); pw.print(mRotateEnterAnimation);
                 pw.print(" "); mRotateEnterTransformation.printShortString(pw); pw.println();
-        pw.print(prefix); pw.print("mLastRotateExitAnimation=");
-                pw.print(mLastRotateExitAnimation);
-                pw.print(" "); mLastRotateExitTransformation.printShortString(pw); pw.println();
+        pw.print(prefix); pw.print("mRotateFrameAnimation="); pw.print(mRotateFrameAnimation);
+                pw.print(" "); mRotateFrameTransformation.printShortString(pw); pw.println();
         pw.print(prefix); pw.print("mExitTransformation=");
                 mExitTransformation.printShortString(pw); pw.println();
         pw.print(prefix); pw.print("mEnterTransformation=");
                 mEnterTransformation.printShortString(pw); pw.println();
+        pw.print(prefix); pw.print("mFrameTransformation=");
+                mEnterTransformation.printShortString(pw); pw.println();
+        pw.print(prefix); pw.print("mFrameInitialMatrix=");
+                mFrameInitialMatrix.printShortString(pw);
+                pw.println();
         pw.print(prefix); pw.print("mSnapshotInitialMatrix=");
                 mSnapshotInitialMatrix.printShortString(pw);
                 pw.print(" mSnapshotFinalMatrix="); mSnapshotFinalMatrix.printShortString(pw);
@@ -172,7 +202,7 @@
                     mSurface = null;
                     return;
                 }
-                mSurface.setLayer(FREEZE_LAYER + 1);
+                mSurface.setLayer(FREEZE_LAYER);
                 mSurface.show();
             } catch (Surface.OutOfResourcesException e) {
                 Slog.w(TAG, "Unable to allocate freeze surface", e);
@@ -293,10 +323,14 @@
                     com.android.internal.R.anim.screen_rotate_start_exit);
             mStartEnterAnimation = AnimationUtils.loadAnimation(mContext,
                     com.android.internal.R.anim.screen_rotate_start_enter);
+            mStartFrameAnimation = AnimationUtils.loadAnimation(mContext,
+                    com.android.internal.R.anim.screen_rotate_start_frame);
             mFinishExitAnimation = AnimationUtils.loadAnimation(mContext,
                     com.android.internal.R.anim.screen_rotate_finish_exit);
             mFinishEnterAnimation = AnimationUtils.loadAnimation(mContext,
                     com.android.internal.R.anim.screen_rotate_finish_enter);
+            mFinishFrameAnimation = AnimationUtils.loadAnimation(mContext,
+                    com.android.internal.R.anim.screen_rotate_finish_frame);
         }
 
         if (DEBUG_STATE) Slog.v(TAG, "Rotation delta: " + delta + " finalWidth="
@@ -309,24 +343,32 @@
                         com.android.internal.R.anim.screen_rotate_0_exit);
                 mRotateEnterAnimation = AnimationUtils.loadAnimation(mContext,
                         com.android.internal.R.anim.screen_rotate_0_enter);
+                mRotateFrameAnimation = AnimationUtils.loadAnimation(mContext,
+                        com.android.internal.R.anim.screen_rotate_0_frame);
                 break;
             case Surface.ROTATION_90:
                 mRotateExitAnimation = AnimationUtils.loadAnimation(mContext,
                         com.android.internal.R.anim.screen_rotate_plus_90_exit);
                 mRotateEnterAnimation = AnimationUtils.loadAnimation(mContext,
                         com.android.internal.R.anim.screen_rotate_plus_90_enter);
+                mRotateFrameAnimation = AnimationUtils.loadAnimation(mContext,
+                        com.android.internal.R.anim.screen_rotate_plus_90_frame);
                 break;
             case Surface.ROTATION_180:
                 mRotateExitAnimation = AnimationUtils.loadAnimation(mContext,
                         com.android.internal.R.anim.screen_rotate_180_exit);
                 mRotateEnterAnimation = AnimationUtils.loadAnimation(mContext,
                         com.android.internal.R.anim.screen_rotate_180_enter);
+                mRotateFrameAnimation = AnimationUtils.loadAnimation(mContext,
+                        com.android.internal.R.anim.screen_rotate_180_frame);
                 break;
             case Surface.ROTATION_270:
                 mRotateExitAnimation = AnimationUtils.loadAnimation(mContext,
                         com.android.internal.R.anim.screen_rotate_minus_90_exit);
                 mRotateEnterAnimation = AnimationUtils.loadAnimation(mContext,
                         com.android.internal.R.anim.screen_rotate_minus_90_enter);
+                mRotateFrameAnimation = AnimationUtils.loadAnimation(mContext,
+                        com.android.internal.R.anim.screen_rotate_minus_90_frame);
                 break;
         }
 
@@ -340,13 +382,18 @@
                     mOriginalWidth, mOriginalHeight);
             mStartExitAnimation.initialize(finalWidth, finalHeight,
                     mOriginalWidth, mOriginalHeight);
+            mStartFrameAnimation.initialize(finalWidth, finalHeight,
+                    mOriginalWidth, mOriginalHeight);
             mFinishEnterAnimation.initialize(finalWidth, finalHeight,
                     mOriginalWidth, mOriginalHeight);
             mFinishExitAnimation.initialize(finalWidth, finalHeight,
                     mOriginalWidth, mOriginalHeight);
+            mFinishFrameAnimation.initialize(finalWidth, finalHeight,
+                    mOriginalWidth, mOriginalHeight);
         }
         mRotateEnterAnimation.initialize(finalWidth, finalHeight, mOriginalWidth, mOriginalHeight);
         mRotateExitAnimation.initialize(finalWidth, finalHeight, mOriginalWidth, mOriginalHeight);
+        mRotateFrameAnimation.initialize(finalWidth, finalHeight, mOriginalWidth, mOriginalHeight);
         mAnimRunning = false;
         mFinishAnimReady = false;
         mFinishAnimStartTime = -1;
@@ -356,15 +403,21 @@
             mStartExitAnimation.scaleCurrentDuration(animationScale);
             mStartEnterAnimation.restrictDuration(maxAnimationDuration);
             mStartEnterAnimation.scaleCurrentDuration(animationScale);
+            mStartFrameAnimation.restrictDuration(maxAnimationDuration);
+            mStartFrameAnimation.scaleCurrentDuration(animationScale);
             mFinishExitAnimation.restrictDuration(maxAnimationDuration);
             mFinishExitAnimation.scaleCurrentDuration(animationScale);
             mFinishEnterAnimation.restrictDuration(maxAnimationDuration);
             mFinishEnterAnimation.scaleCurrentDuration(animationScale);
+            mFinishFrameAnimation.restrictDuration(maxAnimationDuration);
+            mFinishFrameAnimation.scaleCurrentDuration(animationScale);
         }
         mRotateExitAnimation.restrictDuration(maxAnimationDuration);
         mRotateExitAnimation.scaleCurrentDuration(animationScale);
         mRotateEnterAnimation.restrictDuration(maxAnimationDuration);
         mRotateEnterAnimation.scaleCurrentDuration(animationScale);
+        mRotateFrameAnimation.restrictDuration(maxAnimationDuration);
+        mRotateFrameAnimation.scaleCurrentDuration(animationScale);
 
         if (mBlackFrame == null) {
             if (WindowManagerService.SHOW_LIGHT_TRANSACTIONS || DEBUG_STATE) Slog.i(
@@ -372,10 +425,20 @@
                     ">>> OPEN TRANSACTION ScreenRotationAnimation.startAnimation");
             Surface.openTransaction();
 
+            // Compute the transformation matrix that must be applied
+            // the the black frame to make it stay in the initial position
+            // before the new screen rotation.  This is different than the
+            // snapshot transformation because the snapshot is always based
+            // of the native orientation of the screen, not the orientation
+            // we were last in.
+            createRotationMatrix(delta, mOriginalWidth, mOriginalHeight, mFrameInitialMatrix);
+
             try {
-                Rect outer = new Rect(-finalWidth*1, -finalHeight*1, finalWidth*2, finalHeight*2);
-                Rect inner = new Rect(0, 0, finalWidth, finalHeight);
-                mBlackFrame = new BlackFrame(session, outer, inner, FREEZE_LAYER);
+                Rect outer = new Rect(-mOriginalWidth*1, -mOriginalHeight*1,
+                        mOriginalWidth*2, mOriginalHeight*2);
+                Rect inner = new Rect(0, 0, mOriginalWidth, mOriginalHeight);
+                mBlackFrame = new BlackFrame(session, outer, inner, FREEZE_LAYER + 1);
+                mBlackFrame.setMatrix(mFrameInitialMatrix);
             } catch (Surface.OutOfResourcesException e) {
                 Slog.w(TAG, "Unable to allocate black surface", e);
             } finally {
@@ -432,13 +495,21 @@
             mStartEnterAnimation.cancel();
             mStartEnterAnimation = null;
         }
+        if (mStartFrameAnimation != null) {
+            mStartFrameAnimation.cancel();
+            mStartFrameAnimation = null;
+        }
         if (mFinishExitAnimation != null) {
             mFinishExitAnimation.cancel();
             mFinishExitAnimation = null;
         }
-        if (mStartEnterAnimation != null) {
-            mStartEnterAnimation.cancel();
-            mStartEnterAnimation = null;
+        if (mFinishEnterAnimation != null) {
+            mFinishEnterAnimation.cancel();
+            mFinishEnterAnimation = null;
+        }
+        if (mFinishFrameAnimation != null) {
+            mFinishFrameAnimation.cancel();
+            mFinishFrameAnimation = null;
         }
         if (mRotateExitAnimation != null) {
             mRotateExitAnimation.cancel();
@@ -448,17 +519,210 @@
             mRotateEnterAnimation.cancel();
             mRotateEnterAnimation = null;
         }
+        if (mRotateFrameAnimation != null) {
+            mRotateFrameAnimation.cancel();
+            mRotateFrameAnimation = null;
+        }
     }
 
     public boolean isAnimating() {
         return mStartEnterAnimation != null || mStartExitAnimation != null
-                && mFinishEnterAnimation != null || mFinishExitAnimation != null
-                && mRotateEnterAnimation != null || mRotateExitAnimation != null;
+                || mStartFrameAnimation != null
+                || mFinishEnterAnimation != null || mFinishExitAnimation != null
+                || mFinishFrameAnimation != null
+                || mRotateEnterAnimation != null || mRotateExitAnimation != null
+                || mRotateFrameAnimation != null;
     }
 
+    @Override
     public boolean stepAnimation(long now) {
+
+        if (mFinishAnimReady && mFinishAnimStartTime < 0) {
+            if (DEBUG_STATE) Slog.v(TAG, "Step: finish anim now ready");
+            mFinishAnimStartTime = now;
+        }
+
+        // If the start animation is no longer running, we want to keep its
+        // transformation intact until the finish animation also completes.
+
+        mMoreStartExit = false;
+        if (mStartExitAnimation != null) {
+            mStartExitTransformation.clear();
+            mMoreStartExit = mStartExitAnimation.getTransformation(now, mStartExitTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped start exit: " + mStartExitTransformation);
+            if (!mMoreStartExit) {
+                if (DEBUG_STATE) Slog.v(TAG, "Start exit animation done!");
+                mStartExitAnimation.cancel();
+                mStartExitAnimation = null;
+            }
+        }
+
+        mMoreStartEnter = false;
+        if (mStartEnterAnimation != null) {
+            mStartEnterTransformation.clear();
+            mMoreStartEnter = mStartEnterAnimation.getTransformation(now, mStartEnterTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped start enter: " + mStartEnterTransformation);
+            if (!mMoreStartEnter) {
+                if (DEBUG_STATE) Slog.v(TAG, "Start enter animation done!");
+                mStartEnterAnimation.cancel();
+                mStartEnterAnimation = null;
+            }
+        }
+
+        mMoreStartFrame = false;
+        if (mStartFrameAnimation != null) {
+            mStartFrameTransformation.clear();
+            mMoreStartFrame = mStartFrameAnimation.getTransformation(now, mStartFrameTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped start frame: " + mStartFrameTransformation);
+            if (!mMoreStartFrame) {
+                if (DEBUG_STATE) Slog.v(TAG, "Start frame animation done!");
+                mStartFrameAnimation.cancel();
+                mStartFrameAnimation = null;
+            }
+        }
+
+        long finishNow = mFinishAnimReady ? (now - mFinishAnimStartTime) : 0;
+        if (DEBUG_STATE) Slog.v(TAG, "Step: finishNow=" + finishNow);
+
+        mFinishExitTransformation.clear();
+        mMoreFinishExit = false;
+        if (mFinishExitAnimation != null) {
+            mMoreFinishExit = mFinishExitAnimation.getTransformation(finishNow, mFinishExitTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped finish exit: " + mFinishExitTransformation);
+            if (!mMoreStartExit && !mMoreFinishExit) {
+                if (DEBUG_STATE) Slog.v(TAG, "Finish exit animation done, clearing start/finish anims!");
+                mStartExitTransformation.clear();
+                mFinishExitAnimation.cancel();
+                mFinishExitAnimation = null;
+                mFinishExitTransformation.clear();
+            }
+        }
+
+        mFinishEnterTransformation.clear();
+        mMoreFinishEnter = false;
+        if (mFinishEnterAnimation != null) {
+            mMoreFinishEnter = mFinishEnterAnimation.getTransformation(finishNow, mFinishEnterTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped finish enter: " + mFinishEnterTransformation);
+            if (!mMoreStartEnter && !mMoreFinishEnter) {
+                if (DEBUG_STATE) Slog.v(TAG, "Finish enter animation done, clearing start/finish anims!");
+                mStartEnterTransformation.clear();
+                mFinishEnterAnimation.cancel();
+                mFinishEnterAnimation = null;
+                mFinishEnterTransformation.clear();
+            }
+        }
+
+        mFinishFrameTransformation.clear();
+        mMoreFinishFrame = false;
+        if (mFinishFrameAnimation != null) {
+            mMoreFinishFrame = mFinishFrameAnimation.getTransformation(finishNow, mFinishFrameTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped finish frame: " + mFinishFrameTransformation);
+            if (!mMoreStartFrame && !mMoreFinishFrame) {
+                if (DEBUG_STATE) Slog.v(TAG, "Finish frame animation done, clearing start/finish anims!");
+                mStartFrameTransformation.clear();
+                mFinishFrameAnimation.cancel();
+                mFinishFrameAnimation = null;
+                mFinishFrameTransformation.clear();
+            }
+        }
+
+        mRotateExitTransformation.clear();
+        mMoreRotateExit = false;
+        if (mRotateExitAnimation != null) {
+            mMoreRotateExit = mRotateExitAnimation.getTransformation(now, mRotateExitTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped rotate exit: " + mRotateExitTransformation);
+            if (!mMoreFinishExit && !mMoreRotateExit) {
+                if (DEBUG_STATE) Slog.v(TAG, "Rotate exit animation done!");
+                mRotateExitAnimation.cancel();
+                mRotateExitAnimation = null;
+                mRotateExitTransformation.clear();
+            }
+        }
+
+        mRotateEnterTransformation.clear();
+        mMoreRotateEnter = false;
+        if (mRotateEnterAnimation != null) {
+            mMoreRotateEnter = mRotateEnterAnimation.getTransformation(now, mRotateEnterTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped rotate enter: " + mRotateEnterTransformation);
+            if (!mMoreFinishEnter && !mMoreRotateEnter) {
+                if (DEBUG_STATE) Slog.v(TAG, "Rotate enter animation done!");
+                mRotateEnterAnimation.cancel();
+                mRotateEnterAnimation = null;
+                mRotateEnterTransformation.clear();
+            }
+        }
+
+        mRotateFrameTransformation.clear();
+        mMoreRotateFrame = false;
+        if (mRotateFrameAnimation != null) {
+            mMoreRotateFrame = mRotateFrameAnimation.getTransformation(now, mRotateFrameTransformation);
+            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped rotate frame: " + mRotateFrameTransformation);
+            if (!mMoreFinishFrame && !mMoreRotateFrame) {
+                if (DEBUG_STATE) Slog.v(TAG, "Rotate frame animation done!");
+                mRotateFrameAnimation.cancel();
+                mRotateFrameAnimation = null;
+                mRotateFrameTransformation.clear();
+            }
+        }
+
+        mExitTransformation.set(mRotateExitTransformation);
+        mExitTransformation.compose(mStartExitTransformation);
+        mExitTransformation.compose(mFinishExitTransformation);
+
+        mEnterTransformation.set(mRotateEnterTransformation);
+        mEnterTransformation.compose(mStartEnterTransformation);
+        mEnterTransformation.compose(mFinishEnterTransformation);
+
+        //mFrameTransformation.set(mRotateExitTransformation);
+        //mFrameTransformation.compose(mStartExitTransformation);
+        //mFrameTransformation.compose(mFinishExitTransformation);
+        mFrameTransformation.set(mRotateFrameTransformation);
+        mFrameTransformation.compose(mStartFrameTransformation);
+        mFrameTransformation.compose(mFinishFrameTransformation);
+        mFrameTransformation.getMatrix().preConcat(mFrameInitialMatrix);
+
+        if (DEBUG_TRANSFORMS) Slog.v(TAG, "Final exit: " + mExitTransformation);
+        if (DEBUG_TRANSFORMS) Slog.v(TAG, "Final enter: " + mEnterTransformation);
+        if (DEBUG_TRANSFORMS) Slog.v(TAG, "Final frame: " + mFrameTransformation);
+
+        final boolean more = mMoreStartEnter || mMoreStartExit || mMoreStartFrame
+                || mMoreFinishEnter || mMoreFinishExit || mMoreFinishFrame
+                || mMoreRotateEnter || mMoreRotateExit || mMoreRotateFrame
+                || !mFinishAnimReady;
+
+        mSnapshotFinalMatrix.setConcat(mExitTransformation.getMatrix(), mSnapshotInitialMatrix);
+
+        if (DEBUG_STATE) Slog.v(TAG, "Step: more=" + more);
+
+        return more;
+    }
+
+    void updateSurfaces() {
+        if (!mMoreStartExit && !mMoreFinishExit && !mMoreRotateExit) {
+            if (mSurface != null) {
+                if (DEBUG_STATE) Slog.v(TAG, "Exit animations done, hiding screenshot surface");
+                mSurface.hide();
+            }
+        }
+
+        if (!mMoreStartFrame && !mMoreFinishFrame && !mMoreRotateFrame) {
+            if (mBlackFrame != null) {
+                if (DEBUG_STATE) Slog.v(TAG, "Frame animations done, hiding black frame");
+                mBlackFrame.hide();
+            }
+        } else {
+            if (mBlackFrame != null) {
+                mBlackFrame.setMatrix(mFrameTransformation.getMatrix());
+            }
+        }
+
+        setSnapshotTransform(mSnapshotFinalMatrix, mExitTransformation.getAlpha());
+    }
+    
+    public boolean startAndFinishAnimationLocked(long now) {
         if (!isAnimating()) {
             if (DEBUG_STATE) Slog.v(TAG, "Step: no animations running");
+            mFinishAnimReady = false;
             return false;
         }
 
@@ -470,150 +734,31 @@
             if (mStartExitAnimation != null) {
                 mStartExitAnimation.setStartTime(now);
             }
+            if (mStartFrameAnimation != null) {
+                mStartFrameAnimation.setStartTime(now);
+            }
             if (mFinishEnterAnimation != null) {
                 mFinishEnterAnimation.setStartTime(0);
             }
             if (mFinishExitAnimation != null) {
                 mFinishExitAnimation.setStartTime(0);
             }
+            if (mFinishFrameAnimation != null) {
+                mFinishFrameAnimation.setStartTime(0);
+            }
             if (mRotateEnterAnimation != null) {
                 mRotateEnterAnimation.setStartTime(now);
             }
             if (mRotateExitAnimation != null) {
                 mRotateExitAnimation.setStartTime(now);
             }
+            if (mRotateFrameAnimation != null) {
+                mRotateFrameAnimation.setStartTime(now);
+            }
             mAnimRunning = true;
         }
-
-        if (mFinishAnimReady && mFinishAnimStartTime < 0) {
-            if (DEBUG_STATE) Slog.v(TAG, "Step: finish anim now ready");
-            mFinishAnimStartTime = now;
-        }
-
-        // If the start animation is no longer running, we want to keep its
-        // transformation intact until the finish animation also completes.
-
-        boolean moreStartExit = false;
-        if (mStartExitAnimation != null) {
-            mStartExitTransformation.clear();
-            moreStartExit = mStartExitAnimation.getTransformation(now, mStartExitTransformation);
-            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped start exit: " + mStartExitTransformation);
-            if (!moreStartExit) {
-                if (DEBUG_STATE) Slog.v(TAG, "Start exit animation done!");
-                mStartExitAnimation.cancel();
-                mStartExitAnimation = null;
-            }
-        }
-
-        boolean moreStartEnter = false;
-        if (mStartEnterAnimation != null) {
-            mStartEnterTransformation.clear();
-            moreStartEnter = mStartEnterAnimation.getTransformation(now, mStartEnterTransformation);
-            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped start enter: " + mStartEnterTransformation);
-            if (!moreStartEnter) {
-                if (DEBUG_STATE) Slog.v(TAG, "Start enter animation done!");
-                mStartEnterAnimation.cancel();
-                mStartEnterAnimation = null;
-            }
-        }
-
-        long finishNow = mFinishAnimReady ? (now - mFinishAnimStartTime) : 0;
-        if (DEBUG_STATE) Slog.v(TAG, "Step: finishNow=" + finishNow);
-
-        mFinishExitTransformation.clear();
-        boolean moreFinishExit = false;
-        if (mFinishExitAnimation != null) {
-            moreFinishExit = mFinishExitAnimation.getTransformation(finishNow, mFinishExitTransformation);
-            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped finish exit: " + mFinishExitTransformation);
-            if (!moreStartExit && !moreFinishExit) {
-                if (DEBUG_STATE) Slog.v(TAG, "Finish exit animation done, clearing start/finish anims!");
-                mStartExitTransformation.clear();
-                mFinishExitAnimation.cancel();
-                mFinishExitAnimation = null;
-                mFinishExitTransformation.clear();
-            }
-        }
-
-        mFinishEnterTransformation.clear();
-        boolean moreFinishEnter = false;
-        if (mFinishEnterAnimation != null) {
-            moreFinishEnter = mFinishEnterAnimation.getTransformation(finishNow, mFinishEnterTransformation);
-            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped finish enter: " + mFinishEnterTransformation);
-            if (!moreStartEnter && !moreFinishEnter) {
-                if (DEBUG_STATE) Slog.v(TAG, "Finish enter animation done, clearing start/finish anims!");
-                mStartEnterTransformation.clear();
-                mFinishEnterAnimation.cancel();
-                mFinishEnterAnimation = null;
-                mFinishEnterTransformation.clear();
-            }
-        }
-
-        mRotateExitTransformation.clear();
-        boolean moreRotateExit = false;
-        if (mRotateExitAnimation != null) {
-            moreRotateExit = mRotateExitAnimation.getTransformation(now, mRotateExitTransformation);
-            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped rotate exit: " + mRotateExitTransformation);
-        }
-
-        if (!moreFinishExit && !moreRotateExit) {
-            if (DEBUG_STATE) Slog.v(TAG, "Rotate exit animation done!");
-            mRotateExitAnimation.cancel();
-            mRotateExitAnimation = null;
-            mRotateExitTransformation.clear();
-        }
-
-        mRotateEnterTransformation.clear();
-        boolean moreRotateEnter = false;
-        if (mRotateEnterAnimation != null) {
-            moreRotateEnter = mRotateEnterAnimation.getTransformation(now, mRotateEnterTransformation);
-            if (DEBUG_TRANSFORMS) Slog.v(TAG, "Stepped rotate enter: " + mRotateEnterTransformation);
-        }
-
-        if (!moreFinishEnter && !moreRotateEnter) {
-            if (DEBUG_STATE) Slog.v(TAG, "Rotate enter animation done!");
-            mRotateEnterAnimation.cancel();
-            mRotateEnterAnimation = null;
-            mRotateEnterTransformation.clear();
-        }
-
-        mExitTransformation.set(mRotateExitTransformation);
-        mExitTransformation.compose(mStartExitTransformation);
-        mExitTransformation.compose(mFinishExitTransformation);
-
-        mEnterTransformation.set(mRotateEnterTransformation);
-        mEnterTransformation.compose(mStartEnterTransformation);
-        mEnterTransformation.compose(mFinishEnterTransformation);
-
-        if (DEBUG_TRANSFORMS) Slog.v(TAG, "Final exit: " + mExitTransformation);
-        if (DEBUG_TRANSFORMS) Slog.v(TAG, "Final enter: " + mEnterTransformation);
-
-        if (!moreStartExit && !moreFinishExit && !moreRotateExit) {
-            if (mSurface != null) {
-                if (DEBUG_STATE) Slog.v(TAG, "Exit animations done, hiding screenshot surface");
-                mSurface.hide();
-            }
-        }
-
-        if (!moreStartEnter && !moreFinishEnter && !moreRotateEnter) {
-            if (mBlackFrame != null) {
-                if (DEBUG_STATE) Slog.v(TAG, "Enter animations done, hiding black frame");
-                mBlackFrame.hide();
-            }
-        } else {
-            if (mBlackFrame != null) {
-                mBlackFrame.setMatrix(mEnterTransformation.getMatrix());
-            }
-        }
-
-        mSnapshotFinalMatrix.setConcat(mExitTransformation.getMatrix(), mSnapshotInitialMatrix);
-        setSnapshotTransform(mSnapshotFinalMatrix, mExitTransformation.getAlpha());
-
-        final boolean more = moreStartEnter || moreStartExit || moreFinishEnter || moreFinishExit
-                || moreRotateEnter || moreRotateExit || !mFinishAnimReady;
-
-        if (DEBUG_STATE) Slog.v(TAG, "Step: more=" + more);
-
-        return more;
+        
+        return true;
     }
 
     public Transformation getEnterTransformation() {
diff --git a/services/java/com/android/server/wm/WindowManagerService.java b/services/java/com/android/server/wm/WindowManagerService.java
index 008793c..1c5a70f 100644
--- a/services/java/com/android/server/wm/WindowManagerService.java
+++ b/services/java/com/android/server/wm/WindowManagerService.java
@@ -617,6 +617,18 @@
     final AnimationRunnable mAnimationRunnable = new AnimationRunnable();
     boolean mAnimationScheduled;
 
+    interface StepAnimator {
+        /**
+         * Continue the stepping of an ongoing animation. When the animation completes this method
+         * must disable the animation on the StepAnimator. 
+         * @param currentTime Animation time in milliseconds. Use SystemClock.uptimeMillis().
+         * @return True if the animation is still going on, false if the animation has completed
+         *      and stepAnimation has cleared the animation locally.
+         */
+        boolean stepAnimation(long currentTime);
+    }
+    final ArrayList<StepAnimator> mStepAnimators = new ArrayList<StepAnimator>();
+    
     final class DragInputEventReceiver extends InputEventReceiver {
         public DragInputEventReceiver(InputChannel inputChannel, Looper looper) {
             super(inputChannel, looper);
@@ -7615,37 +7627,54 @@
     }
 
     /**
+     * Run through each of the animating objects saved in mStepAnimators.
+     */
+    private void stepAnimations() {
+        final long currentTime = SystemClock.uptimeMillis();
+        for (final StepAnimator stepAnimator : mStepAnimators) {
+            final boolean more = stepAnimator.stepAnimation(currentTime);
+            if (DEBUG_ANIM) {
+                Slog.v(TAG, "stepAnimations: " + currentTime + ": Stepped " + stepAnimator
+                        + (more ? " more" : " done"));
+            }
+        }
+    }
+    
+    /**
      * Extracted from {@link #performLayoutAndPlaceSurfacesLockedInner} to reduce size of method.
      * Update animations of all applications, including those associated with exiting/removed apps.
      *
      * @param currentTime The time which animations use for calculating transitions.
      * @param innerDw Width of app window.
      * @param innerDh Height of app window.
-     * @return true if rotation has stopped, false otherwise
      */
     private void updateWindowsAppsAndRotationAnimationsLocked(long currentTime,
                                                           int innerDw, int innerDh) {
         int i;
-        for (i = mWindows.size() - 1; i >= 0; i--) {
-            mInnerFields.mAnimating |= mWindows.get(i).stepAnimationLocked(currentTime);
-        }
-
         final int NAT = mAppTokens.size();
         for (i=0; i<NAT; i++) {
-            mInnerFields.mAnimating |=
-                    mAppTokens.get(i).stepAnimationLocked(currentTime, innerDw, innerDh);
+            final AppWindowToken appToken = mAppTokens.get(i);
+            if (appToken.startAndFinishAnimationLocked(currentTime, innerDw, innerDh)) {
+                mStepAnimators.add(appToken);
+                mInnerFields.mAnimating = true;
+            }
         }
         final int NEAT = mExitingAppTokens.size();
         for (i=0; i<NEAT; i++) {
-            mInnerFields.mAnimating |=
-                    mExitingAppTokens.get(i).stepAnimationLocked(currentTime, innerDw, innerDh);
+            final AppWindowToken appToken = mExitingAppTokens.get(i);
+            if (appToken.startAndFinishAnimationLocked(currentTime, innerDw, innerDh)) {
+                mStepAnimators.add(appToken);
+                mInnerFields.mAnimating = true;
+            }
         }
 
         if (mScreenRotationAnimation != null) {
-            if (mScreenRotationAnimation.isAnimating()) {
-                if (mScreenRotationAnimation.stepAnimation(currentTime)) {
+            if (mScreenRotationAnimation.isAnimating() ||
+                    mScreenRotationAnimation.mFinishAnimReady) {
+                if (mScreenRotationAnimation.startAndFinishAnimationLocked(currentTime)) {
                     mInnerFields.mUpdateRotation = false;
                     mInnerFields.mAnimating = true;
+                    mStepAnimators.add(mScreenRotationAnimation);
                 } else {
                     mInnerFields.mUpdateRotation = true;
                     mScreenRotationAnimation.kill();
@@ -7704,7 +7733,13 @@
                 }
 
                 final boolean wasAnimating = w.mWasAnimating;
-                final boolean nowAnimating = w.mLocalAnimating;
+                
+                
+                final boolean nowAnimating = w.startAndFinishAnimationLocked(currentTime);
+                if (nowAnimating) {
+                    mStepAnimators.add(w);
+                    mInnerFields.mAnimating = true;
+                }
 
                 if (DEBUG_WALLPAPER) {
                     Slog.v(TAG, w + ": wasAnimating=" + wasAnimating +
@@ -8290,6 +8325,10 @@
         // difficult because we do need to resize surfaces in some
         // cases while they are hidden such as when first showing a
         // window.
+        
+        if (mScreenRotationAnimation != null) {
+            mScreenRotationAnimation.updateSurfaces();
+        }
         boolean displayed = false;
 
         w.computeShownFrameLocked();
@@ -8562,7 +8601,7 @@
             // so we want to leave all of them as unblurred (for
             // performance reasons).
             mInnerFields.mObscured = true;
-        } else if (canBeSeen && (attrFlags & FLAG_BLUR_BEHIND | FLAG_DIM_BEHIND) != 0) {
+        } else if (canBeSeen && (attrFlags & (FLAG_BLUR_BEHIND | FLAG_DIM_BEHIND)) != 0) {
             if (localLOGV) Slog.v(TAG, "Win " + w
                     + ": blurring=" + mInnerFields.mBlurring
                     + " obscured=" + mInnerFields.mObscured);
@@ -8735,6 +8774,7 @@
                 mInnerFields.mWindowAnimationBackground = null;
                 mInnerFields.mWindowAnimationBackgroundColor = 0;
 
+                mStepAnimators.clear();
                 changes = updateWindowsAndWallpaperLocked(currentTime, dw, dh, innerDw, innerDh);
 
                 if (mInnerFields.mTokenMayBeDrawn) {
@@ -8782,9 +8822,10 @@
 
             // Update animations of all applications, including those
             // associated with exiting/removed apps
-            mInnerFields.mAnimating = false;
 
             updateWindowsAppsAndRotationAnimationsLocked(currentTime, innerDw, innerDh);
+            
+            stepAnimations();
 
             // THIRD LOOP: Update the surfaces of all windows.
 
@@ -9667,8 +9708,8 @@
             pw.println();
             pw.println("  Application tokens in Z order:");
             for (int i=mAppTokens.size()-1; i>=0; i--) {
-                pw.print("  App #"); pw.print(i); pw.print(": ");
-                        pw.println(mAppTokens.get(i));
+                pw.print("  App #"); pw.print(i); pw.println(": ");
+                        mAppTokens.get(i).dump(pw, "    ");
             }
         }
         if (mFinishedStarting.size() > 0) {
diff --git a/services/java/com/android/server/wm/WindowState.java b/services/java/com/android/server/wm/WindowState.java
index eeecad1..b9ee660 100644
--- a/services/java/com/android/server/wm/WindowState.java
+++ b/services/java/com/android/server/wm/WindowState.java
@@ -54,7 +54,8 @@
 /**
  * A window in the window manager.
  */
-final class WindowState implements WindowManagerPolicy.WindowState {
+final class WindowState implements WindowManagerPolicy.WindowState,
+        WindowManagerService.StepAnimator {
     static final boolean DEBUG_VISIBILITY = WindowManagerService.DEBUG_VISIBILITY;
     static final boolean SHOW_TRANSACTIONS = WindowManagerService.SHOW_TRANSACTIONS;
     static final boolean SHOW_LIGHT_TRANSACTIONS = WindowManagerService.SHOW_LIGHT_TRANSACTIONS;
@@ -977,9 +978,26 @@
         return true;
     }
 
+    @Override
+    public boolean stepAnimation(long currentTime) {
+        if ((mAnimation == null) || !mLocalAnimating) {
+            return false;
+        }
+        mTransformation.clear();
+        final boolean more = mAnimation.getTransformation(currentTime, mTransformation);
+        if (WindowManagerService.DEBUG_ANIM) Slog.v(
+            WindowManagerService.TAG, "Stepped animation in " + this +
+            ": more=" + more + ", xform=" + mTransformation);
+        if (!more) {
+            mAnimation.cancel();
+            mAnimation = null;
+        }
+        return more;
+    }
+
     // This must be called while inside a transaction.  Returns true if
     // there is more animation to run.
-    boolean stepAnimationLocked(long currentTime) {
+    boolean startAndFinishAnimationLocked(long currentTime) {
         // Save the animation state as it was before this step so WindowManagerService can tell if
         // we just started or just stopped animating by comparing mWasAnimating with isAnimating().
         mWasAnimating = mAnimating;
@@ -1001,24 +1019,12 @@
                     mLocalAnimating = true;
                     mAnimating = true;
                 }
-                mTransformation.clear();
-                final boolean more = mAnimation.getTransformation(
-                    currentTime, mTransformation);
-                if (WindowManagerService.DEBUG_ANIM) Slog.v(
-                    WindowManagerService.TAG, "Stepped animation in " + this +
-                    ": more=" + more + ", xform=" + mTransformation);
-                if (more) {
-                    // we're not done!
+                if ((mAnimation != null) && mLocalAnimating) {
                     return true;
                 }
                 if (WindowManagerService.DEBUG_ANIM) Slog.v(
                     WindowManagerService.TAG, "Finished animation in " + this +
                     " @ " + currentTime);
-
-                if (mAnimation != null) {
-                    mAnimation.cancel();
-                    mAnimation = null;
-                }
                 //WindowManagerService.this.dump();
             }
             mHasLocalTransformation = false;
diff --git a/services/surfaceflinger/EventThread.cpp b/services/surfaceflinger/EventThread.cpp
index af0da0b..3c045d7 100644
--- a/services/surfaceflinger/EventThread.cpp
+++ b/services/surfaceflinger/EventThread.cpp
@@ -14,6 +14,8 @@
  * limitations under the License.
  */
 
+#define ATRACE_TAG ATRACE_TAG_GRAPHICS
+
 #include <stdint.h>
 #include <sys/types.h>
 
@@ -21,6 +23,7 @@
 #include <gui/DisplayEventReceiver.h>
 
 #include <utils/Errors.h>
+#include <utils/Trace.h>
 
 #include "DisplayHardware/DisplayHardware.h"
 #include "DisplayEventConnection.h"
@@ -146,6 +149,7 @@
             // at least one listener requested VSYNC
             mLock.unlock();
             timestamp = mHw.waitForRefresh();
+            ATRACE_INT("VSYNC", mDeliveredEvents&1);
             mLock.lock();
             mDeliveredEvents++;
             mLastVSyncTimestamp = timestamp;
diff --git a/services/surfaceflinger/SurfaceFlinger.cpp b/services/surfaceflinger/SurfaceFlinger.cpp
index 42ed4fa..7f61fe4 100644
--- a/services/surfaceflinger/SurfaceFlinger.cpp
+++ b/services/surfaceflinger/SurfaceFlinger.cpp
@@ -460,6 +460,7 @@
 
 void SurfaceFlinger::postFramebuffer()
 {
+    ATRACE_CALL();
     // mSwapRegion can be empty here is some cases, for instance if a hidden
     // or fully transparent window is updating.
     // in that case, we need to flip anyways to not risk a deadlock with
@@ -504,6 +505,8 @@
 
 void SurfaceFlinger::handleTransaction(uint32_t transactionFlags)
 {
+    ATRACE_CALL();
+
     Mutex::Autolock _l(mStateLock);
     const nsecs_t now = systemTime();
     mDebugInTransaction = now;
@@ -601,6 +604,8 @@
 void SurfaceFlinger::computeVisibleRegions(
     const LayerVector& currentLayers, Region& dirtyRegion, Region& opaqueRegion)
 {
+    ATRACE_CALL();
+
     const GraphicPlane& plane(graphicPlane(0));
     const Transform& planeTransform(plane.transform());
     const DisplayHardware& hw(plane.displayHardware());
@@ -841,6 +846,8 @@
 
 void SurfaceFlinger::handleRepaint()
 {
+    ATRACE_CALL();
+
     // compute the invalid region
     mSwapRegion.orSelf(mDirtyRegion);
 
diff --git a/telephony/java/com/android/internal/telephony/IccCard.java b/telephony/java/com/android/internal/telephony/IccCard.java
index a9ef762..530a8dc 100644
--- a/telephony/java/com/android/internal/telephony/IccCard.java
+++ b/telephony/java/com/android/internal/telephony/IccCard.java
@@ -44,7 +44,7 @@
 /**
  * {@hide}
  */
-public abstract class IccCard {
+public class IccCard {
     protected String mLogTag;
     protected boolean mDbg;
 
@@ -68,6 +68,10 @@
     private boolean mIccFdnEnabled = false; // Default to disabled.
                                             // Will be updated when SIM_READY.
 
+    /* Parameter is3gpp's values to be passed to constructor */
+    public final static boolean CARD_IS_3GPP = true;
+    public final static boolean CARD_IS_NOT_3GPP = false;
+
 
     /* The extra data for broacasting intent INTENT_ICC_STATE_CHANGE */
     static public final String INTENT_KEY_ICC_STATE = "ss";
@@ -162,8 +166,11 @@
         return State.UNKNOWN;
     }
 
-    public IccCard(PhoneBase phone, String logTag, Boolean dbg) {
+    public IccCard(PhoneBase phone, String logTag, Boolean is3gpp, Boolean dbg) {
         mPhone = phone;
+        this.is3gpp = is3gpp;
+        mCdmaSSM = CdmaSubscriptionSourceManager.getInstance(mPhone.getContext(),
+                mPhone.mCM, mHandler, EVENT_CDMA_SUBSCRIPTION_SOURCE_CHANGED, null);
         mPhone.mCM.registerForOffOrNotAvailable(mHandler, EVENT_RADIO_OFF_OR_NOT_AVAILABLE, null);
         mPhone.mCM.registerForOn(mHandler, EVENT_RADIO_ON, null);
         mPhone.mCM.registerForIccStatusChanged(mHandler, EVENT_ICC_STATUS_CHANGED, null);
@@ -175,6 +182,7 @@
         mPhone.mCM.unregisterForIccStatusChanged(mHandler);
         mPhone.mCM.unregisterForOffOrNotAvailable(mHandler);
         mPhone.mCM.unregisterForOn(mHandler);
+        mCdmaSSM.dispose(mHandler);
     }
 
     protected void finalize() {
@@ -447,7 +455,9 @@
      *         yet available
      *
      */
-    public abstract String getServiceProviderName();
+    public String getServiceProviderName () {
+        return mPhone.mIccRecords.getServiceProviderName();
+    }
 
     protected void updateStateProperty() {
         mPhone.setSystemProperty(TelephonyProperties.PROPERTY_SIM_STATE, getState().toString());
@@ -912,7 +922,13 @@
         Log.d(mLogTag, "[IccCard] " + msg);
     }
 
-    protected abstract int getCurrentApplicationIndex();
+    protected int getCurrentApplicationIndex() {
+        if (is3gpp) {
+            return mIccCardStatus.getGsmUmtsSubscriptionAppIndex();
+        } else {
+            return mIccCardStatus.getCdmaSubscriptionAppIndex();
+        }
+    }
 
     public String getAid() {
         String aid = "";
diff --git a/telephony/java/com/android/internal/telephony/PhoneBase.java b/telephony/java/com/android/internal/telephony/PhoneBase.java
index 49f64c9..0b5a82c 100644
--- a/telephony/java/com/android/internal/telephony/PhoneBase.java
+++ b/telephony/java/com/android/internal/telephony/PhoneBase.java
@@ -41,7 +41,6 @@
 import com.android.internal.telephony.ims.IsimRecords;
 import com.android.internal.telephony.test.SimulatedRadioControl;
 import com.android.internal.telephony.gsm.SIMRecords;
-import com.android.internal.telephony.gsm.SimCard;
 
 import java.util.Locale;
 
diff --git a/telephony/java/com/android/internal/telephony/cdma/CDMALTEPhone.java b/telephony/java/com/android/internal/telephony/cdma/CDMALTEPhone.java
index 54e651a..3084c14 100644
--- a/telephony/java/com/android/internal/telephony/cdma/CDMALTEPhone.java
+++ b/telephony/java/com/android/internal/telephony/cdma/CDMALTEPhone.java
@@ -28,13 +28,13 @@
 import android.util.Log;
 
 import com.android.internal.telephony.CommandsInterface;
+import com.android.internal.telephony.IccCard;
 import com.android.internal.telephony.OperatorInfo;
 import com.android.internal.telephony.Phone;
 import com.android.internal.telephony.PhoneNotifier;
 import com.android.internal.telephony.PhoneProxy;
 import com.android.internal.telephony.SMSDispatcher;
 import com.android.internal.telephony.gsm.GsmSMSDispatcher;
-import com.android.internal.telephony.gsm.SimCard;
 import com.android.internal.telephony.ims.IsimRecords;
 
 public class CDMALTEPhone extends CDMAPhone {
@@ -79,7 +79,7 @@
 
     @Override
     protected void initSstIcc() {
-        mIccCard = new SimCard(this, LOG_TAG, DBG);
+        mIccCard = new IccCard(this, LOG_TAG, IccCard.CARD_IS_3GPP, DBG);
         mIccRecords = new CdmaLteUiccRecords(this);
         mIccFileHandler = new CdmaLteUiccFileHandler(this);
         // CdmaLteServiceStateTracker registers with IccCard to know
diff --git a/telephony/java/com/android/internal/telephony/cdma/CDMAPhone.java b/telephony/java/com/android/internal/telephony/cdma/CDMAPhone.java
index d25291d..b5dca65 100755
--- a/telephony/java/com/android/internal/telephony/cdma/CDMAPhone.java
+++ b/telephony/java/com/android/internal/telephony/cdma/CDMAPhone.java
@@ -46,6 +46,7 @@
 import com.android.internal.telephony.CommandException;
 import com.android.internal.telephony.CommandsInterface;
 import com.android.internal.telephony.Connection;
+import com.android.internal.telephony.IccCard;
 import com.android.internal.telephony.IccException;
 import com.android.internal.telephony.IccFileHandler;
 import com.android.internal.telephony.IccPhoneBookInterfaceManager;
@@ -148,7 +149,7 @@
     }
 
     protected void initSstIcc() {
-        mIccCard = new RuimCard(this, LOG_TAG, DBG);
+        mIccCard = new IccCard(this, LOG_TAG, IccCard.CARD_IS_NOT_3GPP, DBG);
         mIccRecords = new RuimRecords(this);
         mIccFileHandler = new RuimFileHandler(this);
         // CdmaServiceStateTracker registers with IccCard to know
diff --git a/telephony/java/com/android/internal/telephony/cdma/CdmaConnection.java b/telephony/java/com/android/internal/telephony/cdma/CdmaConnection.java
index 40825f8..98ad3b1 100755
--- a/telephony/java/com/android/internal/telephony/cdma/CdmaConnection.java
+++ b/telephony/java/com/android/internal/telephony/cdma/CdmaConnection.java
@@ -432,7 +432,7 @@
                     return DisconnectCause.OUT_OF_SERVICE;
                 } else if (phone.mCdmaSubscriptionSource ==
                                CdmaSubscriptionSourceManager.SUBSCRIPTION_FROM_RUIM
-                           && phone.getIccCard().getState() != RuimCard.State.READY) {
+                           && phone.getIccCard().getState() != IccCard.State.READY) {
                     return DisconnectCause.ICC_ERROR;
                 } else if (causeCode==CallFailCause.NORMAL_CLEARING) {
                     return DisconnectCause.NORMAL;
diff --git a/telephony/java/com/android/internal/telephony/cdma/RuimCard.java b/telephony/java/com/android/internal/telephony/cdma/RuimCard.java
deleted file mode 100644
index 674fada..0000000
--- a/telephony/java/com/android/internal/telephony/cdma/RuimCard.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2006 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.internal.telephony.cdma;
-
-import com.android.internal.telephony.IccCard;
-
-/**
- * Note: this class shares common code with SimCard, consider a base class to minimize code
- * duplication.
- * {@hide}
- */
-public final class RuimCard extends IccCard {
-
-    RuimCard(CDMAPhone phone, String LOG_TAG, boolean dbg) {
-        super(phone, LOG_TAG, dbg);
-        is3gpp = false;
-        mCdmaSSM = CdmaSubscriptionSourceManager.getInstance(mPhone.getContext(),
-                       mPhone.mCM, mHandler, EVENT_CDMA_SUBSCRIPTION_SOURCE_CHANGED, null);
-
-        updateStateProperty();
-    }
-
-    @Override
-    public void dispose() {
-        super.dispose();
-        mCdmaSSM.dispose(mHandler);
-    }
-
-    @Override
-    public String getServiceProviderName () {
-        return mPhone.mIccRecords.getServiceProviderName();
-    }
-
-    @Override
-    protected int getCurrentApplicationIndex() {
-        if (mIccCardStatus == null) {
-            return -1;
-        }
-        return mIccCardStatus.getCdmaSubscriptionAppIndex();
-    }
- }
-
diff --git a/telephony/java/com/android/internal/telephony/cdma/RuimRecords.java b/telephony/java/com/android/internal/telephony/cdma/RuimRecords.java
index 17a200e..e518c4c 100755
--- a/telephony/java/com/android/internal/telephony/cdma/RuimRecords.java
+++ b/telephony/java/com/android/internal/telephony/cdma/RuimRecords.java
@@ -30,8 +30,8 @@
 import com.android.internal.telephony.AdnRecordLoader;
 import com.android.internal.telephony.CommandsInterface;
 import com.android.internal.telephony.IccRefreshResponse;
+import com.android.internal.telephony.IccCard;
 import com.android.internal.telephony.TelephonyProperties;
-import com.android.internal.telephony.cdma.RuimCard;
 import com.android.internal.telephony.MccTable;
 
 // can't be used since VoiceMailConstants is not public
@@ -346,7 +346,7 @@
         recordsLoadedRegistrants.notifyRegistrants(
             new AsyncResult(null, null, null));
         phone.mIccCard.broadcastIccStateChangedIntent(
-                RuimCard.INTENT_VALUE_ICC_LOADED, null);
+                IccCard.INTENT_VALUE_ICC_LOADED, null);
     }
 
     private void onRuimReady() {
@@ -355,7 +355,7 @@
         */
 
         phone.mIccCard.broadcastIccStateChangedIntent(
-                RuimCard.INTENT_VALUE_ICC_READY, null);
+                IccCard.INTENT_VALUE_ICC_READY, null);
 
         fetchRuimRecords();
 
diff --git a/telephony/java/com/android/internal/telephony/gsm/GSMPhone.java b/telephony/java/com/android/internal/telephony/gsm/GSMPhone.java
index af7c78c..4c846f1 100644
--- a/telephony/java/com/android/internal/telephony/gsm/GSMPhone.java
+++ b/telephony/java/com/android/internal/telephony/gsm/GSMPhone.java
@@ -56,6 +56,7 @@
 import com.android.internal.telephony.CallStateException;
 import com.android.internal.telephony.CommandsInterface;
 import com.android.internal.telephony.Connection;
+import com.android.internal.telephony.IccCard;
 import com.android.internal.telephony.IccFileHandler;
 import com.android.internal.telephony.IccPhoneBookInterfaceManager;
 import com.android.internal.telephony.IccSmsInterfaceManager;
@@ -135,7 +136,7 @@
         }
 
         mCM.setPhoneType(Phone.PHONE_TYPE_GSM);
-        mIccCard = new SimCard(this, LOG_TAG, true);
+        mIccCard = new IccCard(this, LOG_TAG, IccCard.CARD_IS_3GPP, true);
         mCT = new GsmCallTracker(this);
         mSST = new GsmServiceStateTracker (this);
         mSMS = new GsmSMSDispatcher(this, mSmsStorageMonitor, mSmsUsageMonitor);
diff --git a/telephony/java/com/android/internal/telephony/gsm/GsmConnection.java b/telephony/java/com/android/internal/telephony/gsm/GsmConnection.java
index c1ad7b3..f7c6025 100644
--- a/telephony/java/com/android/internal/telephony/gsm/GsmConnection.java
+++ b/telephony/java/com/android/internal/telephony/gsm/GsmConnection.java
@@ -370,7 +370,7 @@
                 } else if (serviceState == ServiceState.STATE_OUT_OF_SERVICE
                         || serviceState == ServiceState.STATE_EMERGENCY_ONLY ) {
                     return DisconnectCause.OUT_OF_SERVICE;
-                } else if (phone.getIccCard().getState() != SimCard.State.READY) {
+                } else if (phone.getIccCard().getState() != IccCard.State.READY) {
                     return DisconnectCause.ICC_ERROR;
                 } else if (causeCode == CallFailCause.ERROR_UNSPECIFIED) {
                     if (phone.mSST.mRestrictedState.isCsRestricted()) {
diff --git a/telephony/java/com/android/internal/telephony/gsm/GsmMmiCode.java b/telephony/java/com/android/internal/telephony/gsm/GsmMmiCode.java
index 16d3129..205c73d 100644
--- a/telephony/java/com/android/internal/telephony/gsm/GsmMmiCode.java
+++ b/telephony/java/com/android/internal/telephony/gsm/GsmMmiCode.java
@@ -765,7 +765,7 @@
                         // invalid length
                         handlePasswordError(com.android.internal.R.string.invalidPin);
                     } else if (sc.equals(SC_PIN) &&
-                               phone.mIccCard.getState() == SimCard.State.PUK_REQUIRED ) {
+                               phone.mIccCard.getState() == IccCard.State.PUK_REQUIRED ) {
                         // Sim is puk-locked
                         handlePasswordError(com.android.internal.R.string.needPuk);
                     } else {
diff --git a/telephony/java/com/android/internal/telephony/gsm/SIMRecords.java b/telephony/java/com/android/internal/telephony/gsm/SIMRecords.java
index d98aa62..1fb99e3 100755
--- a/telephony/java/com/android/internal/telephony/gsm/SIMRecords.java
+++ b/telephony/java/com/android/internal/telephony/gsm/SIMRecords.java
@@ -30,6 +30,7 @@
 import com.android.internal.telephony.AdnRecordLoader;
 import com.android.internal.telephony.BaseCommands;
 import com.android.internal.telephony.CommandsInterface;
+import com.android.internal.telephony.IccCard;
 import com.android.internal.telephony.IccFileHandler;
 import com.android.internal.telephony.IccRecords;
 import com.android.internal.telephony.IccUtils;
@@ -583,7 +584,7 @@
                     MccTable.updateMccMncConfiguration(phone, imsi.substring(0, 3 + mncLength));
                 }
                 phone.mIccCard.broadcastIccStateChangedIntent(
-                        SimCard.INTENT_VALUE_ICC_IMSI, null);
+                        IccCard.INTENT_VALUE_ICC_IMSI, null);
             break;
 
             case EVENT_GET_MBI_DONE:
@@ -1275,7 +1276,7 @@
         recordsLoadedRegistrants.notifyRegistrants(
             new AsyncResult(null, null, null));
         phone.mIccCard.broadcastIccStateChangedIntent(
-                SimCard.INTENT_VALUE_ICC_LOADED, null);
+                IccCard.INTENT_VALUE_ICC_LOADED, null);
     }
 
     //***** Private methods
@@ -1300,7 +1301,7 @@
           READY is sent before IMSI ready
         */
         phone.mIccCard.broadcastIccStateChangedIntent(
-                SimCard.INTENT_VALUE_ICC_READY, null);
+                IccCard.INTENT_VALUE_ICC_READY, null);
 
         fetchSimRecords();
     }
diff --git a/telephony/java/com/android/internal/telephony/gsm/SimCard.java b/telephony/java/com/android/internal/telephony/gsm/SimCard.java
deleted file mode 100644
index 0e68e07..0000000
--- a/telephony/java/com/android/internal/telephony/gsm/SimCard.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright (C) 2006 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.internal.telephony.gsm;
-
-import android.util.Log;
-
-import com.android.internal.telephony.IccCard;
-import com.android.internal.telephony.Phone;
-import com.android.internal.telephony.PhoneBase;
-import com.android.internal.telephony.TelephonyProperties;
-import android.os.SystemProperties;
-
-/**
- * {@hide}
- */
-public final class SimCard extends IccCard {
-
-    public SimCard(PhoneBase phone, String logTag, Boolean dbg) {
-        super(phone, logTag, dbg);
-        updateStateProperty();
-    }
-
-    @Override
-    public String getServiceProviderName () {
-        return mPhone.mIccRecords.getServiceProviderName();
-    }
-
-    @Override
-    protected int getCurrentApplicationIndex() {
-        if (mIccCardStatus == null) {
-            return -1;
-        }
-        return mIccCardStatus.getGsmUmtsSubscriptionAppIndex();
-    }
-}
diff --git a/tests/BiDiTests/Android-private.mk b/tests/BiDiTests/Android.mk
similarity index 100%
rename from tests/BiDiTests/Android-private.mk
rename to tests/BiDiTests/Android.mk
diff --git a/tests/DumpRenderTree/src/com/android/dumprendertree/TestShellActivity.java b/tests/DumpRenderTree/src/com/android/dumprendertree/TestShellActivity.java
index 83c9c3d..856ebcc 100644
--- a/tests/DumpRenderTree/src/com/android/dumprendertree/TestShellActivity.java
+++ b/tests/DumpRenderTree/src/com/android/dumprendertree/TestShellActivity.java
@@ -45,8 +45,10 @@
 import android.webkit.SslErrorHandler;
 import android.webkit.WebChromeClient;
 import android.webkit.WebSettings;
+import android.webkit.WebSettingsClassic;
 import android.webkit.WebStorage;
 import android.webkit.WebView;
+import android.webkit.WebViewClassic;
 import android.webkit.WebViewClient;
 import android.widget.LinearLayout;
 
@@ -112,10 +114,10 @@
             case DUMP_AS_TEXT:
                 callback.arg1 = mDumpTopFrameAsText ? 1 : 0;
                 callback.arg2 = mDumpChildFramesAsText ? 1 : 0;
-                mWebView.documentAsText(callback);
+                mWebViewClassic.documentAsText(callback);
                 break;
             case EXT_REPR:
-                mWebView.externalRepresentation(callback);
+                mWebViewClassic.externalRepresentation(callback);
                 break;
             default:
                 finished();
@@ -144,6 +146,7 @@
 
         CookieManager.setAcceptFileSchemeCookies(true);
         mWebView = new WebView(this);
+        mWebViewClassic = WebViewClassic.fromWebView(mWebView);
         mEventSender = new WebViewEventSender(mWebView);
         mCallbackProxy = new CallbackProxy(mEventSender, this);
 
@@ -158,7 +161,7 @@
         // Expose window.gc function to JavaScript. JSC build exposes
         // this function by default, but V8 requires the flag to turn it on.
         // WebView::setJsFlags is noop in JSC build.
-        mWebView.setJsFlags("--expose_gc");
+        mWebViewClassic.setJsFlags("--expose_gc");
 
         mHandler = new AsyncHandler();
 
@@ -168,7 +171,7 @@
         }
 
         // This is asynchronous, but it gets processed by WebCore before it starts loading pages.
-        mWebView.useMockDeviceOrientation();
+        mWebViewClassic.useMockDeviceOrientation();
     }
 
     @Override
@@ -290,6 +293,7 @@
         super.onDestroy();
         mWebView.destroy();
         mWebView = null;
+        mWebViewClassic = null;
     }
 
     @Override
@@ -531,8 +535,8 @@
 
     public void setMockDeviceOrientation(boolean canProvideAlpha, double alpha,
             boolean canProvideBeta, double beta, boolean canProvideGamma, double gamma) {
-        mWebView.setMockDeviceOrientation(canProvideAlpha, alpha, canProvideBeta, beta,
-                canProvideGamma, gamma);
+        WebViewClassic.fromWebView(mWebView).setMockDeviceOrientation(canProvideAlpha, alpha,
+                canProvideBeta, beta, canProvideGamma, gamma);
     }
 
     public void overridePreference(String key, boolean value) {
@@ -541,10 +545,10 @@
         // WebView for the main frame. EventSender suffers from the same
         // problem.
         if (WEBKIT_OFFLINE_WEB_APPLICATION_CACHE_ENABLED.equals(key)) {
-            mWebView.getSettings().setAppCacheEnabled(value);
+            mWebViewClassic.getSettings().setAppCacheEnabled(value);
         } else if (WEBKIT_USES_PAGE_CACHE_PREFERENCE_KEY.equals(key)) {
             // Cache the maximum possible number of pages.
-            mWebView.getSettings().setPageCacheCapacity(Integer.MAX_VALUE);
+            mWebViewClassic.getSettings().setPageCacheCapacity(Integer.MAX_VALUE);
         } else {
             Log.w(LOGTAG, "LayoutTestController.overridePreference(): " +
                   "Unsupported preference '" + key + "'");
@@ -552,7 +556,7 @@
     }
 
     public void setXSSAuditorEnabled (boolean flag) {
-        mWebView.getSettings().setXSSAuditorEnabled(flag);
+        mWebViewClassic.getSettings().setXSSAuditorEnabled(flag);
     }
 
     private final WebViewClient mViewClient = new WebViewClient(){
@@ -855,7 +859,7 @@
         Bitmap bitmap = Bitmap.createBitmap(view.getContentWidth(), view.getContentHeight(),
                 Config.ARGB_8888);
         canvas.setBitmap(bitmap);
-        view.drawPage(canvas);
+        WebViewClassic.fromWebView(view).drawPage(canvas);
         try {
             FileOutputStream fos = new FileOutputStream(fileName);
             if(!bitmap.compress(CompressFormat.PNG, 90, fos)) {
@@ -885,11 +889,11 @@
         // single event rather than a stream of events (like what would generally happen in
         // a real use of touch events in a WebView)  and so if the WebView drops the event,
         // the test will fail as the test expects one callback for every touch it synthesizes.
-        webview.setTouchInterval(-1);
+        WebViewClassic.fromWebView(webview).setTouchInterval(-1);
     }
 
     public void setDefaultWebSettings(WebView webview) {
-        WebSettings settings = webview.getSettings();
+        WebSettingsClassic settings = WebViewClassic.fromWebView(webview).getSettings();
         settings.setAppCacheEnabled(true);
         settings.setAppCachePath(getApplicationContext().getCacheDir().getPath());
         settings.setAppCacheMaxSize(Long.MAX_VALUE);
@@ -906,6 +910,7 @@
         settings.setProperty("use_minimal_memory", "false");
     }
 
+    private WebViewClassic mWebViewClassic;
     private WebView mWebView;
     private WebViewEventSender mEventSender;
     private AsyncHandler mHandler;
diff --git a/tests/DumpRenderTree2/src/com/android/dumprendertree2/LayoutTestsExecutor.java b/tests/DumpRenderTree2/src/com/android/dumprendertree2/LayoutTestsExecutor.java
index f59da37..fc22472 100644
--- a/tests/DumpRenderTree2/src/com/android/dumprendertree2/LayoutTestsExecutor.java
+++ b/tests/DumpRenderTree2/src/com/android/dumprendertree2/LayoutTestsExecutor.java
@@ -41,9 +41,11 @@
 import android.webkit.SslErrorHandler;
 import android.webkit.WebChromeClient;
 import android.webkit.WebSettings;
+import android.webkit.WebSettingsClassic;
 import android.webkit.WebStorage;
 import android.webkit.WebStorage.QuotaUpdater;
 import android.webkit.WebView;
+import android.webkit.WebViewClassic;
 import android.webkit.WebViewClient;
 
 import java.lang.Thread.UncaughtExceptionHandler;
@@ -369,11 +371,12 @@
          * a real use of touch events in a WebView)  and so if the WebView drops the event,
          * the test will fail as the test expects one callback for every touch it synthesizes.
          */
-        webView.setTouchInterval(-1);
+        WebViewClassic webViewClassic = WebViewClassic.fromWebView(webView);
+        webViewClassic.setTouchInterval(-1);
 
-        webView.clearCache(true);
+        webViewClassic.clearCache(true);
 
-        WebSettings webViewSettings = webView.getSettings();
+        WebSettingsClassic webViewSettings = webViewClassic.getSettings();
         webViewSettings.setAppCacheEnabled(true);
         webViewSettings.setAppCachePath(getApplicationContext().getCacheDir().getPath());
         // Use of larger values causes unexplained AppCache database corruption.
@@ -391,7 +394,7 @@
         webViewSettings.setPageCacheCapacity(0);
 
         // This is asynchronous, but it gets processed by WebCore before it starts loading pages.
-        mCurrentWebView.useMockDeviceOrientation();
+        WebViewClassic.fromWebView(mCurrentWebView).useMockDeviceOrientation();
 
         // Must do this after setting the AppCache path.
         WebStorage.getInstance().deleteAllData();
@@ -625,10 +628,12 @@
                     String key = msg.getData().getString("key");
                     boolean value = msg.getData().getBoolean("value");
                     if (WEBKIT_OFFLINE_WEB_APPLICATION_CACHE_ENABLED.equals(key)) {
-                        mCurrentWebView.getSettings().setAppCacheEnabled(value);
+                        WebViewClassic.fromWebView(mCurrentWebView).getSettings().
+                                setAppCacheEnabled(value);
                     } else if (WEBKIT_USES_PAGE_CACHE_PREFERENCE_KEY.equals(key)) {
                         // Cache the maximum possible number of pages.
-                        mCurrentWebView.getSettings().setPageCacheCapacity(Integer.MAX_VALUE);
+                        WebViewClassic.fromWebView(mCurrentWebView).getSettings().
+                                setPageCacheCapacity(Integer.MAX_VALUE);
                     } else {
                         Log.w(LOG_TAG, "LayoutTestController.overridePreference(): " +
                               "Unsupported preference '" + key + "'");
@@ -656,7 +661,8 @@
                     break;
 
                 case MSG_SET_XSS_AUDITOR_ENABLED:
-                    mCurrentWebView.getSettings().setXSSAuditorEnabled(msg.arg1 == 1);
+                    WebViewClassic.fromWebView(mCurrentWebView).getSettings().
+                            setXSSAuditorEnabled(msg.arg1 == 1);
                     break;
 
                 case MSG_WAIT_UNTIL_DONE:
@@ -728,8 +734,8 @@
         Log.i(LOG_TAG, mCurrentTestRelativePath + ": setMockDeviceOrientation(" + canProvideAlpha +
                 ", " + alpha + ", " + canProvideBeta + ", " + beta + ", " + canProvideGamma +
                 ", " + gamma + ")");
-        mCurrentWebView.setMockDeviceOrientation(canProvideAlpha, alpha, canProvideBeta, beta,
-                canProvideGamma, gamma);
+        WebViewClassic.fromWebView(mCurrentWebView).setMockDeviceOrientation(canProvideAlpha,
+                alpha, canProvideBeta, beta, canProvideGamma, gamma);
     }
 
     public void setXSSAuditorEnabled(boolean flag) {
diff --git a/tests/DumpRenderTree2/src/com/android/dumprendertree2/TextResult.java b/tests/DumpRenderTree2/src/com/android/dumprendertree2/TextResult.java
index 3d2b98b..fd1c0ad 100644
--- a/tests/DumpRenderTree2/src/com/android/dumprendertree2/TextResult.java
+++ b/tests/DumpRenderTree2/src/com/android/dumprendertree2/TextResult.java
@@ -20,6 +20,7 @@
 import android.os.Handler;
 import android.os.Message;
 import android.webkit.WebView;
+import android.webkit.WebViewClassic;
 
 import name.fraser.neil.plaintext.diff_match_patch;
 
@@ -233,7 +234,7 @@
          */
         msg.arg1 = 1;
         msg.arg2 = mDumpChildFramesAsText ? 1 : 0;
-        webview.documentAsText(msg);
+        WebViewClassic.fromWebView(webview).documentAsText(msg);
     }
 
     @Override
diff --git a/tests/TileBenchmark/src/com/test/tilebenchmark/ProfiledWebView.java b/tests/TileBenchmark/src/com/test/tilebenchmark/ProfiledWebView.java
index a38ac25..87baf76 100644
--- a/tests/TileBenchmark/src/com/test/tilebenchmark/ProfiledWebView.java
+++ b/tests/TileBenchmark/src/com/test/tilebenchmark/ProfiledWebView.java
@@ -20,8 +20,9 @@
 import android.os.CountDownTimer;
 import android.util.AttributeSet;
 import android.util.Log;
-import android.webkit.WebSettings;
+import android.webkit.WebSettingsClassic;
 import android.webkit.WebView;
+import android.webkit.WebViewClassic;
 import android.widget.Toast;
 
 import java.util.ArrayList;
@@ -29,7 +30,7 @@
 import com.test.tilebenchmark.ProfileActivity.ProfileCallback;
 import com.test.tilebenchmark.RunData.TileData;
 
-public class ProfiledWebView extends WebView {
+public class ProfiledWebView extends WebView implements WebViewClassic.PageSwapDelegate {
     private static final String LOGTAG = "ProfiledWebView";
 
     private int mSpeed;
@@ -80,7 +81,7 @@
     }
 
     public void init(Context c) {
-        WebSettings settings = getSettings();
+        WebSettingsClassic settings = getWebViewClassic().getSettings();
         settings.setJavaScriptEnabled(true);
         settings.setSupportZoom(true);
         settings.setEnableSmoothTransition(true);
@@ -118,7 +119,7 @@
         mCallback = callback;
         mIsTesting = false;
         mIsScrolling = false;
-        WebSettings settings = getSettings();
+        WebSettingsClassic settings = getWebViewClassic().getSettings();
         settings.setProperty("tree_updates", "0");
 
 
@@ -134,7 +135,7 @@
                     // invalidate all content, and kick off redraw
                     Log.d("ProfiledWebView",
                             "kicking off test with callback registration, and tile discard...");
-                    discardAllTextures();
+                    getWebViewClassic().discardAllTextures();
                     invalidate();
                     mIsScrolling = true;
                     mContentInvalMillis = System.currentTimeMillis();
@@ -142,30 +143,29 @@
             }.start();
         } else {
             mIsTesting = true;
-            tileProfilingStart();
+            getWebViewClassic().tileProfilingStart();
         }
     }
 
     /*
      * Called after the manual contentInvalidateAll, after the tiles have all
      * been redrawn.
+     * From PageSwapDelegate.
      */
     @Override
-    protected void pageSwapCallback(boolean startAnim) {
-        super.pageSwapCallback(startAnim);
-
+    public void onPageSwapOccurred(boolean startAnim) {
         if (!mIsTesting && mIsScrolling) {
             // kick off testing
             mContentInvalMillis = System.currentTimeMillis() - mContentInvalMillis;
             Log.d("ProfiledWebView", "REDRAW TOOK " + mContentInvalMillis + "millis");
             mIsTesting = true;
             invalidate(); // ensure a redraw so that auto-scrolling can occur
-            tileProfilingStart();
+            getWebViewClassic().tileProfilingStart();
         }
     }
 
     private double animFramerate() {
-        WebSettings settings = getSettings();
+        WebSettingsClassic settings = getWebViewClassic().getSettings();
         String updatesString = settings.getProperty("tree_updates");
         int updates = (updatesString == null) ? -1 : Integer.parseInt(updatesString);
 
@@ -180,7 +180,7 @@
     }
 
     public void setDoubleBuffering(boolean useDoubleBuffering) {
-        WebSettings settings = getSettings();
+        WebSettingsClassic settings = getWebViewClassic().getSettings();
         settings.setProperty("use_double_buffering", useDoubleBuffering ? "true" : "false");
     }
 
@@ -188,15 +188,15 @@
      * Called once the page has stopped scrolling
      */
     public void stopScrollTest() {
-        tileProfilingStop();
+        getWebViewClassic().tileProfilingStop();
         mIsTesting = false;
 
         if (mCallback == null) {
-            tileProfilingClear();
+            getWebViewClassic().tileProfilingClear();
             return;
         }
 
-        RunData data = new RunData(super.tileProfilingNumFrames());
+        RunData data = new RunData(getWebViewClassic().tileProfilingNumFrames());
         // record the time spent (before scrolling) rendering the page
         data.singleStats.put(getResources().getString(R.string.render_millis),
                 (double)mContentInvalMillis);
@@ -209,24 +209,24 @@
 
         for (int frame = 0; frame < data.frames.length; frame++) {
             data.frames[frame] = new TileData[
-                    tileProfilingNumTilesInFrame(frame)];
+                    getWebViewClassic().tileProfilingNumTilesInFrame(frame)];
             for (int tile = 0; tile < data.frames[frame].length; tile++) {
-                int left = tileProfilingGetInt(frame, tile, "left");
-                int top = tileProfilingGetInt(frame, tile, "top");
-                int right = tileProfilingGetInt(frame, tile, "right");
-                int bottom = tileProfilingGetInt(frame, tile, "bottom");
+                int left = getWebViewClassic().tileProfilingGetInt(frame, tile, "left");
+                int top = getWebViewClassic().tileProfilingGetInt(frame, tile, "top");
+                int right = getWebViewClassic().tileProfilingGetInt(frame, tile, "right");
+                int bottom = getWebViewClassic().tileProfilingGetInt(frame, tile, "bottom");
 
-                boolean isReady = super.tileProfilingGetInt(
+                boolean isReady = getWebViewClassic().tileProfilingGetInt(
                         frame, tile, "isReady") == 1;
-                int level = tileProfilingGetInt(frame, tile, "level");
+                int level = getWebViewClassic().tileProfilingGetInt(frame, tile, "level");
 
-                float scale = tileProfilingGetFloat(frame, tile, "scale");
+                float scale = getWebViewClassic().tileProfilingGetFloat(frame, tile, "scale");
 
                 data.frames[frame][tile] = data.new TileData(left, top, right, bottom,
                         isReady, level, scale);
             }
         }
-        tileProfilingClear();
+        getWebViewClassic().tileProfilingClear();
 
         mCallback.profileCallback(data);
     }
@@ -244,4 +244,8 @@
     public void setAutoScrollSpeed(int speedInt) {
         mSpeed = speedInt;
     }
+
+    public WebViewClassic getWebViewClassic() {
+        return WebViewClassic.fromWebView(this);
+    }
 }
diff --git a/wifi/java/android/net/wifi/SupplicantStateTracker.java b/wifi/java/android/net/wifi/SupplicantStateTracker.java
index 104a02d..6aeac5f 100644
--- a/wifi/java/android/net/wifi/SupplicantStateTracker.java
+++ b/wifi/java/android/net/wifi/SupplicantStateTracker.java
@@ -175,7 +175,7 @@
                 case WifiStateMachine.CMD_RESET_SUPPLICANT_STATE:
                     transitionTo(mUninitializedState);
                     break;
-                case WifiStateMachine.CMD_CONNECT_NETWORK:
+                case WifiManager.CONNECT_NETWORK:
                     mNetworksDisabledDuringConnect = true;
                     break;
                 default:
diff --git a/wifi/java/android/net/wifi/WifiConfigStore.java b/wifi/java/android/net/wifi/WifiConfigStore.java
index 5dffa60..46ad036 100644
--- a/wifi/java/android/net/wifi/WifiConfigStore.java
+++ b/wifi/java/android/net/wifi/WifiConfigStore.java
@@ -261,6 +261,7 @@
      * Add/update the specified configuration and save config
      *
      * @param config WifiConfiguration to be saved
+     * @return network update result
      */
     NetworkUpdateResult saveNetwork(WifiConfiguration config) {
         boolean newNetwork = (config.networkId == INVALID_NETWORK_ID);
@@ -285,7 +286,10 @@
                     config.status = Status.CURRENT;
                     break;
                 case DISCONNECTED:
-                    config.status = Status.ENABLED;
+                    //If network is already disabled, keep the status
+                    if (config.status == Status.CURRENT) {
+                        config.status = Status.ENABLED;
+                    }
                     break;
                 default:
                     //do nothing, retain the existing state
@@ -298,8 +302,9 @@
      * Forget the specified network and save config
      *
      * @param netId network to forget
+     * @return {@code true} if it succeeds, {@code false} otherwise
      */
-    void forgetNetwork(int netId) {
+    boolean forgetNetwork(int netId) {
         if (mWifiNative.removeNetwork(netId)) {
             mWifiNative.saveConfig();
             WifiConfiguration config = mConfiguredNetworks.get(netId);
@@ -309,8 +314,10 @@
             }
             writeIpAndProxyConfigurations();
             sendConfiguredNetworksChangedBroadcast();
+            return true;
         } else {
             loge("Failed to remove network " + netId);
+            return false;
         }
     }
 
@@ -321,6 +328,7 @@
      * state machine
      *
      * @param config wifi configuration to add/update
+     * @return network Id
      */
     int addOrUpdateNetwork(WifiConfiguration config) {
         NetworkUpdateResult result = addOrUpdateNetworkNative(config);
@@ -335,6 +343,7 @@
      * state machine for network removal
      *
      * @param netId network to be removed
+     * @return {@code true} if it succeeds, {@code false} otherwise
      */
     boolean removeNetwork(int netId) {
         boolean ret = mWifiNative.removeNetwork(netId);
@@ -356,6 +365,7 @@
      * state machine for connecting to a network
      *
      * @param netId network to be removed
+     * @return {@code true} if it succeeds, {@code false} otherwise
      */
     boolean enableNetwork(int netId, boolean disableOthers) {
         boolean ret = enableNetworkWithoutBroadcast(netId, disableOthers);
@@ -378,6 +388,7 @@
     /**
      * Disable a network. Note that there is no saveConfig operation.
      * @param netId network to be disabled
+     * @return {@code true} if it succeeds, {@code false} otherwise
      */
     boolean disableNetwork(int netId) {
         return disableNetwork(netId, WifiConfiguration.DISABLED_UNKNOWN_REASON);
@@ -387,6 +398,7 @@
      * Disable a network. Note that there is no saveConfig operation.
      * @param netId network to be disabled
      * @param reason reason code network was disabled
+     * @return {@code true} if it succeeds, {@code false} otherwise
      */
     boolean disableNetwork(int netId, int reason) {
         boolean ret = mWifiNative.disableNetwork(netId);
@@ -402,6 +414,7 @@
 
     /**
      * Save the configured networks in supplicant to disk
+     * @return {@code true} if it succeeds, {@code false} otherwise
      */
     boolean saveConfig() {
         return mWifiNative.saveConfig();
@@ -410,6 +423,8 @@
     /**
      * Start WPS pin method configuration with pin obtained
      * from the access point
+     * @param config WPS configuration
+     * @return Wps result containing status and pin
      */
     WpsResult startWpsWithPinFromAccessPoint(WpsInfo config) {
         WpsResult result = new WpsResult();
@@ -445,6 +460,8 @@
 
     /**
      * Start WPS push button configuration
+     * @param config WPS configuration
+     * @return WpsResult indicating status and pin
      */
     WpsResult startWpsPbc(WpsInfo config) {
         WpsResult result = new WpsResult();
@@ -461,6 +478,7 @@
 
     /**
      * Fetch the link properties for a given network id
+     * @return LinkProperties for the given network id
      */
     LinkProperties getLinkProperties(int netId) {
         WifiConfiguration config = mConfiguredNetworks.get(netId);
@@ -474,6 +492,7 @@
      *       right now until NetworkUtils is fixed. When we do
      *       that, we should remove handling DhcpInfo and move
      *       to using LinkProperties
+     * @return DhcpInfoInternal for the given network id
      */
     DhcpInfoInternal getIpConfiguration(int netId) {
         DhcpInfoInternal dhcpInfoInternal = new DhcpInfoInternal();
@@ -516,6 +535,7 @@
 
     /**
      * clear IP configuration for a given network id
+     * @param network id
      */
     void clearIpConfiguration(int netId) {
         WifiConfiguration config = mConfiguredNetworks.get(netId);
@@ -530,6 +550,8 @@
 
     /**
      * Fetch the proxy properties for a given network id
+     * @param network id
+     * @return ProxyProperties for the network id
      */
     ProxyProperties getProxyProperties(int netId) {
         LinkProperties linkProperties = getLinkProperties(netId);
@@ -541,6 +563,8 @@
 
     /**
      * Return if the specified network is using static IP
+     * @param network id
+     * @return {@code true} if using static ip for netId
      */
     boolean isUsingStaticIp(int netId) {
         WifiConfiguration config = mConfiguredNetworks.get(netId);
@@ -599,16 +623,6 @@
         sendConfiguredNetworksChangedBroadcast();
     }
 
-    void updateIpAndProxyFromWpsConfig(int netId, WpsInfo wpsConfig) {
-        WifiConfiguration config = mConfiguredNetworks.get(netId);
-        if (config != null) {
-            config.ipAssignment = wpsConfig.ipAssignment;
-            config.proxySettings = wpsConfig.proxySettings;
-            config.linkProperties = wpsConfig.linkProperties;
-            writeIpAndProxyConfigurations();
-        }
-    }
-
     /* Mark all networks except specified netId as disabled */
     private void markAllNetworksDisabledExcept(int netId) {
         for(WifiConfiguration config : mConfiguredNetworks.values()) {
@@ -895,7 +909,7 @@
                         }
                     }
                 } else {
-                    loge("Missing id while parsing configuration");
+                    if (DBG) log("Missing id while parsing configuration");
                 }
             }
         } catch (EOFException ignore) {
diff --git a/wifi/java/android/net/wifi/WifiManager.java b/wifi/java/android/net/wifi/WifiManager.java
index 1acfd3a..d746810 100644
--- a/wifi/java/android/net/wifi/WifiManager.java
+++ b/wifi/java/android/net/wifi/WifiManager.java
@@ -23,11 +23,15 @@
 import android.os.Binder;
 import android.os.IBinder;
 import android.os.Handler;
+import android.os.Looper;
+import android.os.Message;
 import android.os.RemoteException;
 import android.os.WorkSource;
 import android.os.Messenger;
+import android.util.SparseArray;
 
 import com.android.internal.util.AsyncChannel;
+import com.android.internal.util.Protocol;
 
 import java.util.List;
 
@@ -289,24 +293,6 @@
     public static final String EXTRA_SUPPLICANT_ERROR = "supplicantError";
 
     /**
-     * Broadcast intent action for reporting errors
-     * @hide
-     */
-    @SdkConstant(SdkConstantType.BROADCAST_INTENT_ACTION)
-    public static final String ERROR_ACTION = "android.net.wifi.ERROR";
-    /**
-     * The type of error being reported
-     * @hide
-     */
-    public static final String EXTRA_ERROR_CODE = "errorCode";
-
-    /**
-     * Valid error codes
-     * @hide
-     */
-    public static final int WPS_OVERLAP_ERROR = 1;
-
-    /**
      * Broadcast intent action indicating that the configured networks changed.
      * This can be as a result of adding/updating/deleting a network
      * @hide
@@ -466,9 +452,6 @@
     /* Number of currently active WifiLocks and MulticastLocks */
     private int mActiveLockCount;
 
-    /* For communication with WifiService */
-    private AsyncChannel mAsyncChannel = new AsyncChannel();
-
     /**
      * Create a new WifiManager instance.
      * Applications will almost always want to use
@@ -622,17 +605,6 @@
     }
 
     /**
-     * Disable a configured network asynchronously.  This call is for abnormal network
-     * events, and the user may be notified of network change, if they recently attempted
-     * to connect to the specified network.
-     * @param netId the ID of the network as returned by {@link #addNetwork}.
-     * @hide
-     */
-    public void disableNetwork(int netId, int reason) {
-        mAsyncChannel.sendMessage(CMD_DISABLE_NETWORK, netId, reason);
-    }
-
-    /**
      * Disassociate from the currently active access point. This may result
      * in the asynchronous delivery of state change events.
      * @return {@code true} if the operation succeeded
@@ -1067,37 +1039,258 @@
 
     /* TODO: deprecate synchronous API and open up the following API */
 
+    private static final int BASE = Protocol.BASE_WIFI_MANAGER;
+
     /* Commands to WifiService */
     /** @hide */
-    public static final int CMD_CONNECT_NETWORK             = 1;
+    public static final int CONNECT_NETWORK                 = BASE + 1;
     /** @hide */
-    public static final int CMD_FORGET_NETWORK              = 2;
+    public static final int CONNECT_NETWORK_FAILED          = BASE + 2;
     /** @hide */
-    public static final int CMD_SAVE_NETWORK                = 3;
-    /** @hide */
-    public static final int CMD_START_WPS                   = 4;
-    /** @hide */
-    public static final int CMD_DISABLE_NETWORK             = 5;
+    public static final int CONNECT_NETWORK_SUCCEEDED       = BASE + 3;
 
-    /* Events from WifiService */
     /** @hide */
-    public static final int CMD_WPS_COMPLETED               = 11;
+    public static final int FORGET_NETWORK                  = BASE + 4;
+    /** @hide */
+    public static final int FORGET_NETWORK_FAILED           = BASE + 5;
+    /** @hide */
+    public static final int FORGET_NETWORK_SUCCEEDED        = BASE + 6;
+
+    /** @hide */
+    public static final int SAVE_NETWORK                    = BASE + 7;
+    /** @hide */
+    public static final int SAVE_NETWORK_FAILED             = BASE + 8;
+    /** @hide */
+    public static final int SAVE_NETWORK_SUCCEEDED          = BASE + 9;
+
+    /** @hide */
+    public static final int START_WPS                       = BASE + 10;
+    /** @hide */
+    public static final int START_WPS_SUCCEEDED             = BASE + 11;
+    /** @hide */
+    public static final int WPS_FAILED                      = BASE + 12;
+    /** @hide */
+    public static final int WPS_COMPLETED                   = BASE + 13;
+
+    /** @hide */
+    public static final int CANCEL_WPS                      = BASE + 14;
+    /** @hide */
+    public static final int CANCEL_WPS_FAILED               = BASE + 15;
+    /** @hide */
+    public static final int CANCEL_WPS_SUCCEDED             = BASE + 16;
+
+    /** @hide */
+    public static final int DISABLE_NETWORK                 = BASE + 17;
+    /** @hide */
+    public static final int DISABLE_NETWORK_FAILED          = BASE + 18;
+    /** @hide */
+    public static final int DISABLE_NETWORK_SUCCEEDED       = BASE + 19;
 
     /* For system use only */
     /** @hide */
-    public static final int CMD_ENABLE_TRAFFIC_STATS_POLL   = 21;
+    public static final int ENABLE_TRAFFIC_STATS_POLL       = BASE + 21;
     /** @hide */
-    public static final int CMD_TRAFFIC_STATS_POLL          = 22;
+    public static final int TRAFFIC_STATS_POLL              = BASE + 22;
+
 
     /**
-     * Initiate an asynchronous channel connection setup
-     * @param srcContext is the context of the source
-     * @param srcHandler is the handler on which the source receives messages
+     * Passed with {@link ActionListener#onFailure}.
+     * Indicates that the operation failed due to an internal error.
      * @hide
      */
-     public void asyncConnect(Context srcContext, Handler srcHandler) {
-        mAsyncChannel.connect(srcContext, srcHandler, getWifiServiceMessenger());
-     }
+    public static final int ERROR                       = 0;
+
+    /**
+     * Passed with {@link ActionListener#onFailure}.
+     * Indicates that the operation is already in progress
+     * @hide
+     */
+    public static final int IN_PROGRESS                 = 1;
+
+    /**
+     * Passed with {@link ActionListener#onFailure}.
+     * Indicates that the operation failed because the framework is busy and
+     * unable to service the request
+     * @hide
+     */
+    public static final int BUSY                        = 2;
+
+    /* WPS specific errors */
+    /** WPS overlap detected {@hide} */
+    public static final int WPS_OVERLAP_ERROR           = 3;
+    /** WEP on WPS is prohibited {@hide} */
+    public static final int WPS_WEP_PROHIBITED          = 4;
+    /** TKIP only prohibited {@hide} */
+    public static final int WPS_TKIP_ONLY_PROHIBITED    = 5;
+    /** Authentication failure on WPS {@hide} */
+    public static final int WPS_AUTH_FAILURE            = 6;
+    /** WPS timed out {@hide} */
+    public static final int WPS_TIMED_OUT               = 7;
+
+    /** Interface for callback invocation when framework channel is lost {@hide} */
+    public interface ChannelListener {
+        /**
+         * The channel to the framework has been disconnected.
+         * Application could try re-initializing using {@link #initialize}
+         */
+        public void onChannelDisconnected();
+    }
+
+    /** Interface for callback invocation on an application action {@hide} */
+    public interface ActionListener {
+        /** The operation succeeded */
+        public void onSuccess();
+        /**
+         * The operation failed
+         * @param reason The reason for failure could be one of
+         * {@link #ERROR}, {@link #IN_PROGRESS} or {@link #BUSY}
+         */
+        public void onFailure(int reason);
+    }
+
+    /** Interface for callback invocation on a start WPS action {@hide} */
+    public interface WpsListener {
+        /** WPS start succeeded */
+        public void onStartSuccess(String pin);
+
+        /** WPS operation completed succesfully */
+        public void onCompletion();
+
+        /**
+         * WPS operation failed
+         * @param reason The reason for failure could be one of
+         * {@link #IN_PROGRESS}, {@link #WPS_OVERLAP_ERROR},{@link #ERROR} or {@link #BUSY}
+         */
+        public void onFailure(int reason);
+    }
+
+    /**
+     * A channel that connects the application to the Wifi framework.
+     * Most operations require a Channel as an argument. An instance of Channel is obtained
+     * by doing a call on {@link #initialize}
+     * @hide
+     */
+    public static class Channel {
+        Channel(Looper looper, ChannelListener l) {
+            mAsyncChannel = new AsyncChannel();
+            mHandler = new WifiHandler(looper);
+            mChannelListener = l;
+        }
+        private ChannelListener mChannelListener;
+        private SparseArray<Object> mListenerMap = new SparseArray<Object>();
+        private Object mListenerMapLock = new Object();
+        private int mListenerKey = 0;
+        private static final int INVALID_KEY = -1;
+
+        AsyncChannel mAsyncChannel;
+        WifiHandler mHandler;
+        class WifiHandler extends Handler {
+            WifiHandler(Looper looper) {
+                super(looper);
+            }
+
+            @Override
+            public void handleMessage(Message message) {
+                Object listener = removeListener(message.arg2);
+                switch (message.what) {
+                    case AsyncChannel.CMD_CHANNEL_DISCONNECTED:
+                        if (mChannelListener != null) {
+                            mChannelListener.onChannelDisconnected();
+                            mChannelListener = null;
+                        }
+                        break;
+                        /* ActionListeners grouped together */
+                    case WifiManager.CONNECT_NETWORK_FAILED:
+                    case WifiManager.FORGET_NETWORK_FAILED:
+                    case WifiManager.SAVE_NETWORK_FAILED:
+                    case WifiManager.CANCEL_WPS_FAILED:
+                    case WifiManager.DISABLE_NETWORK_FAILED:
+                        if (listener != null) {
+                            ((ActionListener) listener).onFailure(message.arg1);
+                        }
+                        break;
+                        /* ActionListeners grouped together */
+                    case WifiManager.CONNECT_NETWORK_SUCCEEDED:
+                    case WifiManager.FORGET_NETWORK_SUCCEEDED:
+                    case WifiManager.SAVE_NETWORK_SUCCEEDED:
+                    case WifiManager.CANCEL_WPS_SUCCEDED:
+                    case WifiManager.DISABLE_NETWORK_SUCCEEDED:
+                        if (listener != null) {
+                            ((ActionListener) listener).onSuccess();
+                        }
+                        break;
+                    case WifiManager.START_WPS_SUCCEEDED:
+                        if (listener != null) {
+                            WpsResult result = (WpsResult) message.obj;
+                            ((WpsListener) listener).onStartSuccess(result.pin);
+                            //Listener needs to stay until completion or failure
+                            synchronized(mListenerMapLock) {
+                                mListenerMap.put(message.arg2, listener);
+                            }
+                        }
+                        break;
+                    case WifiManager.WPS_COMPLETED:
+                        if (listener != null) {
+                            ((WpsListener) listener).onCompletion();
+                        }
+                        break;
+                    case WifiManager.WPS_FAILED:
+                        if (listener != null) {
+                            ((WpsListener) listener).onFailure(message.arg1);
+                        }
+                        break;
+                    default:
+                        //ignore
+                        break;
+                }
+            }
+        }
+
+        int putListener(Object listener) {
+            if (listener == null) return INVALID_KEY;
+            int key;
+            synchronized (mListenerMapLock) {
+                do {
+                    key = mListenerKey++;
+                } while (key == INVALID_KEY);
+                mListenerMap.put(key, listener);
+            }
+            return key;
+        }
+
+        Object removeListener(int key) {
+            if (key == INVALID_KEY) return null;
+            synchronized (mListenerMapLock) {
+                Object listener = mListenerMap.get(key);
+                mListenerMap.remove(key);
+                return listener;
+            }
+        }
+    }
+
+    /**
+     * Registers the application with the Wi-Fi framework. This function
+     * must be the first to be called before any Wi-Fi operations are performed.
+     *
+     * @param srcContext is the context of the source
+     * @param srcLooper is the Looper on which the callbacks are receivied
+     * @param listener for callback at loss of framework communication. Can be null.
+     * @return Channel instance that is necessary for performing any further Wi-Fi operations.
+     *         A null is returned upon failure to initialize.
+     * @hide
+     */
+    public Channel initialize(Context srcContext, Looper srcLooper, ChannelListener listener) {
+        Messenger messenger = getWifiServiceMessenger();
+        if (messenger == null) return null;
+
+        Channel c = new Channel(srcLooper, listener);
+        if (c.mAsyncChannel.connectSync(srcContext, c.mHandler, messenger)
+                == AsyncChannel.STATUS_SUCCESSFUL) {
+            return c;
+        } else {
+            return null;
+        }
+    }
 
     /**
      * Connect to a network with the given configuration. The network also
@@ -1107,15 +1300,20 @@
      * sequence of addNetwork(), enableNetwork(), saveConfiguration() and
      * reconnect()
      *
+     * @param c is the channel created at {@link #initialize}
      * @param config the set of variables that describe the configuration,
      *            contained in a {@link WifiConfiguration} object.
+     * @param listener for callbacks on success or failure. Can be null.
      * @hide
      */
-    public void connectNetwork(WifiConfiguration config) {
-        if (config == null) {
-            return;
-        }
-        mAsyncChannel.sendMessage(CMD_CONNECT_NETWORK, config);
+    public void connect(Channel c, WifiConfiguration config, ActionListener listener) {
+        if (c == null) throw new IllegalArgumentException("Channel needs to be initialized");
+        if (config == null) throw new IllegalArgumentException("config cannot be null");
+
+        // Use INVALID_NETWORK_ID for arg1 when passing a config object
+        // arg1 is used to pass network id when the network already exists
+        c.mAsyncChannel.sendMessage(CONNECT_NETWORK, WifiConfiguration.INVALID_NETWORK_ID,
+                c.putListener(listener), config);
     }
 
     /**
@@ -1124,15 +1322,17 @@
      * This function is used instead of a enableNetwork(), saveConfiguration() and
      * reconnect()
      *
+     * @param c is the channel created at {@link #initialize}
      * @param networkId the network id identifiying the network in the
      *                supplicant configuration list
+     * @param listener for callbacks on success or failure. Can be null.
      * @hide
      */
-    public void connectNetwork(int networkId) {
-        if (networkId < 0) {
-            return;
-        }
-        mAsyncChannel.sendMessage(CMD_CONNECT_NETWORK, networkId);
+    public void connect(Channel c, int networkId, ActionListener listener) {
+        if (c == null) throw new IllegalArgumentException("Channel needs to be initialized");
+        if (networkId < 0) throw new IllegalArgumentException("Network id cannot be negative");
+
+        c.mAsyncChannel.sendMessage(CONNECT_NETWORK, networkId, c.putListener(listener));
     }
 
     /**
@@ -1146,16 +1346,17 @@
      * For an existing network, it accomplishes the task of updateNetwork()
      * and saveConfiguration()
      *
+     * @param c is the channel created at {@link #initialize}
      * @param config the set of variables that describe the configuration,
      *            contained in a {@link WifiConfiguration} object.
+     * @param listener for callbacks on success or failure. Can be null.
      * @hide
      */
-    public void saveNetwork(WifiConfiguration config) {
-        if (config == null) {
-            return;
-        }
+    public void save(Channel c, WifiConfiguration config, ActionListener listener) {
+        if (c == null) throw new IllegalArgumentException("Channel needs to be initialized");
+        if (config == null) throw new IllegalArgumentException("config cannot be null");
 
-        mAsyncChannel.sendMessage(CMD_SAVE_NETWORK, config);
+        c.mAsyncChannel.sendMessage(SAVE_NETWORK, 0, c.putListener(listener), config);
     }
 
     /**
@@ -1164,33 +1365,65 @@
      * This function is used instead of a sequence of removeNetwork()
      * and saveConfiguration().
      *
+     * @param c is the channel created at {@link #initialize}
      * @param config the set of variables that describe the configuration,
      *            contained in a {@link WifiConfiguration} object.
+     * @param listener for callbacks on success or failure. Can be null.
      * @hide
      */
-    public void forgetNetwork(int netId) {
-        if (netId < 0) {
-            return;
-        }
+    public void forget(Channel c, int netId, ActionListener listener) {
+        if (c == null) throw new IllegalArgumentException("Channel needs to be initialized");
+        if (netId < 0) throw new IllegalArgumentException("Network id cannot be negative");
 
-        mAsyncChannel.sendMessage(CMD_FORGET_NETWORK, netId);
+        c.mAsyncChannel.sendMessage(FORGET_NETWORK, netId, c.putListener(listener));
+    }
+
+    /**
+     * Disable network
+     *
+     * @param c is the channel created at {@link #initialize}
+     * @param netId is the network Id
+     * @param listener for callbacks on success or failure. Can be null.
+     * @hide
+     */
+    public void disable(Channel c, int netId, ActionListener listener) {
+        if (c == null) throw new IllegalArgumentException("Channel needs to be initialized");
+        if (netId < 0) throw new IllegalArgumentException("Network id cannot be negative");
+
+        c.mAsyncChannel.sendMessage(DISABLE_NETWORK, netId, c.putListener(listener));
     }
 
     /**
      * Start Wi-fi Protected Setup
      *
+     * @param c is the channel created at {@link #initialize}
      * @param config WPS configuration
+     * @param listener for callbacks on success or failure. Can be null.
      * @hide
      */
-    public void startWps(WpsInfo config) {
-        if (config == null) {
-            return;
-        }
+    public void startWps(Channel c, WpsInfo config, WpsListener listener) {
+        if (c == null) throw new IllegalArgumentException("Channel needs to be initialized");
+        if (config == null) throw new IllegalArgumentException("config cannot be null");
 
-        mAsyncChannel.sendMessage(CMD_START_WPS, config);
+        c.mAsyncChannel.sendMessage(START_WPS, 0, c.putListener(listener), config);
     }
 
     /**
+     * Cancel any ongoing Wi-fi Protected Setup
+     *
+     * @param c is the channel created at {@link #initialize}
+     * @param listener for callbacks on success or failure. Can be null.
+     * @hide
+     */
+    public void cancelWps(Channel c, ActionListener listener) {
+        if (c == null) throw new IllegalArgumentException("Channel needs to be initialized");
+
+        c.mAsyncChannel.sendMessage(CANCEL_WPS, 0, c.putListener(listener));
+    }
+
+
+
+    /**
      * Get a reference to WifiService handler. This is used by a client to establish
      * an AsyncChannel communication with WifiService
      *
diff --git a/wifi/java/android/net/wifi/WifiMonitor.java b/wifi/java/android/net/wifi/WifiMonitor.java
index d05e0b8..c406fa0 100644
--- a/wifi/java/android/net/wifi/WifiMonitor.java
+++ b/wifi/java/android/net/wifi/WifiMonitor.java
@@ -64,7 +64,23 @@
        "pre-shared key may be incorrect";
 
     /* WPS events */
+    private static final String WPS_SUCCESS_STR = "WPS-SUCCESS";
+
+    /* Format: WPS-FAIL msg=%d [config_error=%d] [reason=%d (%s)] */
+    private static final String WPS_FAIL_STR    = "WPS-FAIL";
+    private static final String WPS_FAIL_PATTERN =
+            "WPS-FAIL msg=\\d+(?: config_error=(\\d+))?(?: reason=(\\d+))?";
+
+    /* config error code values for config_error=%d */
+    private static final int CONFIG_MULTIPLE_PBC_DETECTED = 12;
+    private static final int CONFIG_AUTH_FAILURE = 18;
+
+    /* reason code values for reason=%d */
+    private static final int REASON_TKIP_ONLY_PROHIBITED = 1;
+    private static final int REASON_WEP_PROHIBITED = 2;
+
     private static final String WPS_OVERLAP_STR = "WPS-OVERLAP-DETECTED";
+    private static final String WPS_TIMEOUT_STR = "WPS-TIMEOUT";
 
     /**
      * Names of events from wpa_supplicant (minus the prefix). In the
@@ -221,10 +237,16 @@
     public static final int SUPPLICANT_STATE_CHANGE_EVENT        = BASE + 6;
     /* Password failure and EAP authentication failure */
     public static final int AUTHENTICATION_FAILURE_EVENT         = BASE + 7;
-    /* WPS overlap detected */
-    public static final int WPS_OVERLAP_EVENT                    = BASE + 8;
+    /* WPS success detected */
+    public static final int WPS_SUCCESS_EVENT                    = BASE + 8;
+    /* WPS failure detected */
+    public static final int WPS_FAIL_EVENT                       = BASE + 9;
+     /* WPS overlap detected */
+    public static final int WPS_OVERLAP_EVENT                    = BASE + 10;
+     /* WPS timeout detected */
+    public static final int WPS_TIMEOUT_EVENT                    = BASE + 11;
     /* Driver was hung */
-    public static final int DRIVER_HUNG_EVENT                    = BASE + 9;
+    public static final int DRIVER_HUNG_EVENT                    = BASE + 12;
 
     /* P2P events */
     public static final int P2P_DEVICE_FOUND_EVENT               = BASE + 21;
@@ -304,8 +326,14 @@
                     if (eventStr.startsWith(WPA_EVENT_PREFIX_STR) &&
                             0 < eventStr.indexOf(PASSWORD_MAY_BE_INCORRECT_STR)) {
                         mStateMachine.sendMessage(AUTHENTICATION_FAILURE_EVENT);
+                    } else if (eventStr.startsWith(WPS_SUCCESS_STR)) {
+                        mStateMachine.sendMessage(WPS_SUCCESS_EVENT);
+                    } else if (eventStr.startsWith(WPS_FAIL_STR)) {
+                        handleWpsFailEvent(eventStr);
                     } else if (eventStr.startsWith(WPS_OVERLAP_STR)) {
                         mStateMachine.sendMessage(WPS_OVERLAP_EVENT);
+                    } else if (eventStr.startsWith(WPS_TIMEOUT_STR)) {
+                        mStateMachine.sendMessage(WPS_TIMEOUT_EVENT);
                     } else if (eventStr.startsWith(P2P_EVENT_PREFIX_STR)) {
                         handleP2pEvents(eventStr);
                     } else if (eventStr.startsWith(HOST_AP_EVENT_PREFIX_STR)) {
@@ -443,6 +471,43 @@
             }
         }
 
+        private void handleWpsFailEvent(String dataString) {
+            final Pattern p = Pattern.compile(WPS_FAIL_PATTERN);
+            Matcher match = p.matcher(dataString);
+            if (match.find()) {
+                String cfgErr = match.group(1);
+                String reason = match.group(2);
+
+                if (reason != null) {
+                    switch(Integer.parseInt(reason)) {
+                        case REASON_TKIP_ONLY_PROHIBITED:
+                            mStateMachine.sendMessage(mStateMachine.obtainMessage(WPS_FAIL_EVENT,
+                                    WifiManager.WPS_TKIP_ONLY_PROHIBITED, 0));
+                            return;
+                        case REASON_WEP_PROHIBITED:
+                            mStateMachine.sendMessage(mStateMachine.obtainMessage(WPS_FAIL_EVENT,
+                                    WifiManager.WPS_WEP_PROHIBITED, 0));
+                            return;
+                    }
+                }
+                if (cfgErr != null) {
+                    switch(Integer.parseInt(cfgErr)) {
+                        case CONFIG_AUTH_FAILURE:
+                            mStateMachine.sendMessage(mStateMachine.obtainMessage(WPS_FAIL_EVENT,
+                                    WifiManager.WPS_AUTH_FAILURE, 0));
+                            return;
+                        case CONFIG_MULTIPLE_PBC_DETECTED:
+                            mStateMachine.sendMessage(mStateMachine.obtainMessage(WPS_FAIL_EVENT,
+                                    WifiManager.WPS_OVERLAP_ERROR, 0));
+                            return;
+                    }
+                }
+            }
+            //For all other errors, return a generic internal error
+            mStateMachine.sendMessage(mStateMachine.obtainMessage(WPS_FAIL_EVENT,
+                    WifiManager.ERROR, 0));
+        }
+
         /**
          * Handle p2p events
          */
diff --git a/wifi/java/android/net/wifi/WifiNative.java b/wifi/java/android/net/wifi/WifiNative.java
index e3dd3a6..ecd4073 100644
--- a/wifi/java/android/net/wifi/WifiNative.java
+++ b/wifi/java/android/net/wifi/WifiNative.java
@@ -388,27 +388,37 @@
         return doStringCommand("SIGNAL_POLL");
     }
 
-    public boolean startWpsPbc() {
-        return doBooleanCommand("WPS_PBC");
-    }
-
     public boolean startWpsPbc(String bssid) {
-        return doBooleanCommand("WPS_PBC " + bssid);
+        if (TextUtils.isEmpty(bssid)) {
+            return doBooleanCommand("WPS_PBC");
+        } else {
+            return doBooleanCommand("WPS_PBC " + bssid);
+        }
     }
 
     public boolean startWpsPinKeypad(String pin) {
+        if (TextUtils.isEmpty(pin)) return false;
         return doBooleanCommand("WPS_PIN any " + pin);
     }
 
     public String startWpsPinDisplay(String bssid) {
-        return doStringCommand("WPS_PIN " + bssid);
+        if (TextUtils.isEmpty(bssid)) {
+            return doStringCommand("WPS_PIN any");
+        } else {
+            return doStringCommand("WPS_PIN " + bssid);
+        }
     }
 
     /* Configures an access point connection */
     public boolean startWpsRegistrar(String bssid, String pin) {
+        if (TextUtils.isEmpty(bssid) || TextUtils.isEmpty(pin)) return false;
         return doBooleanCommand("WPS_REG " + bssid + " " + pin);
     }
 
+    public boolean cancelWps() {
+        return doBooleanCommand("WPS_CANCEL");
+    }
+
     public boolean setPersistentReconnect(boolean enabled) {
         int value = (enabled == true) ? 1 : 0;
         return doBooleanCommand("SET persistent_reconnect " + value);
@@ -539,7 +549,7 @@
     }
 
     public boolean p2pGroupRemove(String iface) {
-        if (iface == null) return false;
+        if (TextUtils.isEmpty(iface)) return false;
         return doBooleanCommand("P2P_GROUP_REMOVE " + iface);
     }
 
@@ -549,7 +559,7 @@
 
     /* Invite a peer to a group */
     public boolean p2pInvite(WifiP2pGroup group, String deviceAddress) {
-        if (deviceAddress == null) return false;
+        if (TextUtils.isEmpty(deviceAddress)) return false;
 
         if (group == null) {
             return doBooleanCommand("P2P_INVITE peer=" + deviceAddress);
@@ -561,19 +571,19 @@
 
     /* Reinvoke a persistent connection */
     public boolean p2pReinvoke(int netId, String deviceAddress) {
-        if (deviceAddress == null || netId < 0) return false;
+        if (TextUtils.isEmpty(deviceAddress) || netId < 0) return false;
 
         return doBooleanCommand("P2P_INVITE persistent=" + netId + " peer=" + deviceAddress);
     }
 
 
     public String p2pGetInterfaceAddress(String deviceAddress) {
-        if (deviceAddress == null) return null;
+        if (TextUtils.isEmpty(deviceAddress)) return null;
 
         //  "p2p_peer deviceAddress" returns a multi-line result containing
         //      intended_addr=fa:7b:7a:42:82:13
         String peerInfo = p2pPeer(deviceAddress);
-        if (peerInfo == null) return null;
+        if (TextUtils.isEmpty(peerInfo)) return null;
         String[] tokens= peerInfo.split("\n");
 
         for (String token : tokens) {
diff --git a/wifi/java/android/net/wifi/WifiStateMachine.java b/wifi/java/android/net/wifi/WifiStateMachine.java
index e140d80..843620c 100644
--- a/wifi/java/android/net/wifi/WifiStateMachine.java
+++ b/wifi/java/android/net/wifi/WifiStateMachine.java
@@ -184,7 +184,6 @@
     private WifiInfo mWifiInfo;
     private NetworkInfo mNetworkInfo;
     private SupplicantStateTracker mSupplicantStateTracker;
-    private WpsStateMachine mWpsStateMachine;
     private DhcpStateMachine mDhcpStateMachine;
 
     private AlarmManager mAlarmManager;
@@ -275,16 +274,14 @@
     static final int CMD_ENABLE_NETWORK                   = BASE + 54;
     /* Enable all networks */
     static final int CMD_ENABLE_ALL_NETWORKS              = BASE + 55;
-    /* Disable a network. The device does not attempt a connection to the given network. */
-    static final int CMD_DISABLE_NETWORK                  = BASE + 56;
     /* Blacklist network. De-prioritizes the given BSSID for connection. */
-    static final int CMD_BLACKLIST_NETWORK                = BASE + 57;
+    static final int CMD_BLACKLIST_NETWORK                = BASE + 56;
     /* Clear the blacklist network list */
-    static final int CMD_CLEAR_BLACKLIST                  = BASE + 58;
+    static final int CMD_CLEAR_BLACKLIST                  = BASE + 57;
     /* Save configuration */
-    static final int CMD_SAVE_CONFIG                      = BASE + 59;
+    static final int CMD_SAVE_CONFIG                      = BASE + 58;
     /* Get configured networks*/
-    static final int CMD_GET_CONFIGURED_NETWORKS          = BASE + 60;
+    static final int CMD_GET_CONFIGURED_NETWORKS          = BASE + 59;
 
     /* Supplicant commands after driver start*/
     /* Initiate a scan */
@@ -328,28 +325,7 @@
     static final int MULTICAST_V6  = 1;
     static final int MULTICAST_V4  = 0;
 
-    /* Connect to a specified network (network id
-     * or WifiConfiguration) This involves increasing
-     * the priority of the network, enabling the network
-     * (while disabling others) and issuing a reconnect.
-     * Note that CMD_RECONNECT just does a reconnect to
-     * an existing network. All the networks get enabled
-     * upon a successful connection or a failure.
-     */
-    static final int CMD_CONNECT_NETWORK                  = BASE + 86;
-    /* Save the specified network. This involves adding
-     * an enabled network (if new) and updating the
-     * config and issuing a save on supplicant config.
-     */
-    static final int CMD_SAVE_NETWORK                     = BASE + 87;
-    /* Delete the specified network. This involves
-     * removing the network and issuing a save on
-     * supplicant config.
-     */
-    static final int CMD_FORGET_NETWORK                   = BASE + 88;
-    /* Start Wi-Fi protected setup */
-    static final int CMD_START_WPS                        = BASE + 89;
-    /* Set the frequency band */
+   /* Set the frequency band */
     static final int CMD_SET_FREQUENCY_BAND               = BASE + 90;
     /* Enable background scan for configured networks */
     static final int CMD_ENABLE_BACKGROUND_SCAN           = BASE + 91;
@@ -358,12 +334,6 @@
     /* Reset the supplicant state tracker */
     static final int CMD_RESET_SUPPLICANT_STATE           = BASE + 111;
 
-    /* Commands/events reported by WpsStateMachine */
-    /* Indicates the completion of WPS activity */
-    static final int WPS_COMPLETED_EVENT                  = BASE + 121;
-    /* Reset the WPS state machine */
-    static final int CMD_RESET_WPS_STATE                  = BASE + 122;
-
     /* P2p commands */
     public static final int CMD_ENABLE_P2P                = BASE + 131;
     public static final int CMD_DISABLE_P2P               = BASE + 132;
@@ -476,7 +446,7 @@
     /* Network is not connected, supplicant assoc+auth is not complete */
     private State mDisconnectedState = new DisconnectedState();
     /* Waiting for WPS to be completed*/
-    private State mWaitForWpsCompletionState = new WaitForWpsCompletionState();
+    private State mWpsRunningState = new WpsRunningState();
 
     /* Soft ap is starting up */
     private State mSoftApStartingState = new SoftApStartingState();
@@ -570,7 +540,6 @@
         mWifiInfo = new WifiInfo();
         mSupplicantStateTracker = new SupplicantStateTracker(context, this, mWifiConfigStore,
                 getHandler());
-        mWpsStateMachine = new WpsStateMachine(context, this, mWifiConfigStore, getHandler());
         mLinkProperties = new LinkProperties();
 
         WifiApConfigStore wifiApConfigStore = WifiApConfigStore.makeWifiApConfigStore(
@@ -639,7 +608,7 @@
                             addState(mConnectedState, mL2ConnectedState);
                         addState(mDisconnectingState, mConnectModeState);
                         addState(mDisconnectedState, mConnectModeState);
-                        addState(mWaitForWpsCompletionState, mConnectModeState);
+                        addState(mWpsRunningState, mConnectModeState);
                 addState(mDriverStoppingState, mSupplicantStartedState);
                 addState(mDriverStoppedState, mSupplicantStartedState);
             addState(mSupplicantStoppingState, mDefaultState);
@@ -908,9 +877,8 @@
      * @return {@code true} if the operation succeeds, {@code false} otherwise
      */
     public boolean syncDisableNetwork(AsyncChannel channel, int netId) {
-        Message resultMsg = channel.sendMessageSynchronously(CMD_DISABLE_NETWORK, netId,
-                WifiConfiguration.DISABLED_UNKNOWN_REASON);
-        boolean result = (resultMsg.arg1 != FAILURE);
+        Message resultMsg = channel.sendMessageSynchronously(WifiManager.DISABLE_NETWORK, netId);
+        boolean result = (resultMsg.arg1 != WifiManager.DISABLE_NETWORK_FAILED);
         resultMsg.recycle();
         return result;
     }
@@ -933,39 +901,6 @@
         sendMessage(obtainMessage(CMD_CLEAR_BLACKLIST));
     }
 
-    public void connectNetwork(int netId) {
-        sendMessage(obtainMessage(CMD_CONNECT_NETWORK, netId, 0));
-    }
-
-    public void connectNetwork(WifiConfiguration wifiConfig) {
-        /* arg1 is used to indicate netId, force a netId value of
-         * WifiConfiguration.INVALID_NETWORK_ID when we are passing
-         * a configuration since the default value of 0 is a valid netId
-         */
-        sendMessage(obtainMessage(CMD_CONNECT_NETWORK, WifiConfiguration.INVALID_NETWORK_ID,
-                0, wifiConfig));
-    }
-
-    public void saveNetwork(WifiConfiguration wifiConfig) {
-        sendMessage(obtainMessage(CMD_SAVE_NETWORK, wifiConfig));
-    }
-
-    public void forgetNetwork(int netId) {
-        sendMessage(obtainMessage(CMD_FORGET_NETWORK, netId, 0));
-    }
-
-    public void disableNetwork(Messenger replyTo, int netId, int reason) {
-        Message message = obtainMessage(CMD_DISABLE_NETWORK, netId, reason);
-        message.replyTo = replyTo;
-        sendMessage(message);
-    }
-
-    public void startWps(Messenger replyTo, WpsInfo config) {
-        Message msg = obtainMessage(CMD_START_WPS, config);
-        msg.replyTo = replyTo;
-        sendMessage(msg);
-    }
-
     public void enableRssiPolling(boolean enabled) {
        sendMessage(obtainMessage(CMD_ENABLE_RSSI_POLL, enabled ? 1 : 0, 0));
     }
@@ -1563,13 +1498,6 @@
         mContext.sendStickyBroadcast(intent);
     }
 
-    private void sendErrorBroadcast(int errorCode) {
-        Intent intent = new Intent(WifiManager.ERROR_ACTION);
-        intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
-        intent.putExtra(WifiManager.EXTRA_ERROR_CODE, errorCode);
-        mContext.sendBroadcast(intent);
-    }
-
     private void sendLinkConfigurationChangedBroadcast() {
         Intent intent = new Intent(WifiManager.LINK_CONFIGURATION_CHANGED_ACTION);
         intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
@@ -1626,7 +1554,6 @@
         }
 
         mSupplicantStateTracker.sendMessage(Message.obtain(message));
-        mWpsStateMachine.sendMessage(Message.obtain(message));
 
         return state;
     }
@@ -1836,14 +1763,13 @@
                     /* Synchronous call returns */
                 case CMD_PING_SUPPLICANT:
                 case CMD_ENABLE_NETWORK:
-                case CMD_DISABLE_NETWORK:
                 case CMD_ADD_OR_UPDATE_NETWORK:
                 case CMD_REMOVE_NETWORK:
                 case CMD_SAVE_CONFIG:
-                    mReplyChannel.replyToMessage(message, message.what, FAILURE);
+                    replyToMessage(message, message.what, FAILURE);
                     break;
                 case CMD_GET_CONFIGURED_NETWORKS:
-                    mReplyChannel.replyToMessage(message, message.what,
+                    replyToMessage(message, message.what,
                             mWifiConfigStore.getConfiguredNetworks());
                     break;
                 case CMD_ENABLE_RSSI_POLL:
@@ -1886,9 +1812,6 @@
                 case CMD_SET_HIGH_PERF_MODE:
                 case CMD_SET_COUNTRY_CODE:
                 case CMD_SET_FREQUENCY_BAND:
-                case CMD_CONNECT_NETWORK:
-                case CMD_SAVE_NETWORK:
-                case CMD_FORGET_NETWORK:
                 case CMD_RSSI_POLL:
                 case CMD_ENABLE_ALL_NETWORKS:
                 case DhcpStateMachine.CMD_PRE_DHCP_ACTION:
@@ -1905,10 +1828,29 @@
                     setWifiEnabled(false);
                     setWifiEnabled(true);
                     break;
-                case CMD_START_WPS:
-                    /* Return failure when the state machine cannot handle WPS initiation*/
-                    mReplyChannel.replyToMessage(message, WifiManager.CMD_WPS_COMPLETED,
-                                new WpsResult(Status.FAILURE));
+                case WifiManager.CONNECT_NETWORK:
+                    replyToMessage(message, WifiManager.CONNECT_NETWORK_FAILED,
+                            WifiManager.BUSY);
+                    break;
+                case WifiManager.FORGET_NETWORK:
+                    replyToMessage(message, WifiManager.FORGET_NETWORK_FAILED,
+                            WifiManager.BUSY);
+                    break;
+                case WifiManager.SAVE_NETWORK:
+                    replyToMessage(message, WifiManager.SAVE_NETWORK_FAILED,
+                            WifiManager.BUSY);
+                    break;
+                case WifiManager.START_WPS:
+                    replyToMessage(message, WifiManager.WPS_FAILED,
+                            WifiManager.BUSY);
+                    break;
+                case WifiManager.CANCEL_WPS:
+                    replyToMessage(message, WifiManager.CANCEL_WPS_FAILED,
+                            WifiManager.BUSY);
+                    break;
+                case WifiManager.DISABLE_NETWORK:
+                    replyToMessage(message, WifiManager.DISABLE_NETWORK_FAILED,
+                            WifiManager.BUSY);
                     break;
                 default:
                     loge("Error! unhandled message" + message);
@@ -2222,7 +2164,6 @@
                     /* Reset the supplicant state to indicate the supplicant
                      * state is not known at this time */
                     mSupplicantStateTracker.sendMessage(CMD_RESET_SUPPLICANT_STATE);
-                    mWpsStateMachine.sendMessage(CMD_RESET_WPS_STATE);
                     /* Initialize data structures */
                     mLastBssid = null;
                     mLastNetworkId = WifiConfiguration.INVALID_NETWORK_ID;
@@ -2306,7 +2247,6 @@
                     handleNetworkDisconnect();
                     sendSupplicantConnectionChangedBroadcast(false);
                     mSupplicantStateTracker.sendMessage(CMD_RESET_SUPPLICANT_STATE);
-                    mWpsStateMachine.sendMessage(CMD_RESET_WPS_STATE);
                     transitionTo(mDriverLoadedState);
                     sendMessageDelayed(CMD_START_SUPPLICANT, SUPPLICANT_RESTART_INTERVAL_MSECS);
                     break;
@@ -2318,20 +2258,20 @@
                     break;
                 case CMD_PING_SUPPLICANT:
                     boolean ok = mWifiNative.ping();
-                    mReplyChannel.replyToMessage(message, message.what, ok ? SUCCESS : FAILURE);
+                    replyToMessage(message, message.what, ok ? SUCCESS : FAILURE);
                     break;
                 case CMD_ADD_OR_UPDATE_NETWORK:
                     config = (WifiConfiguration) message.obj;
-                    mReplyChannel.replyToMessage(message, CMD_ADD_OR_UPDATE_NETWORK,
+                    replyToMessage(message, CMD_ADD_OR_UPDATE_NETWORK,
                             mWifiConfigStore.addOrUpdateNetwork(config));
                     break;
                 case CMD_REMOVE_NETWORK:
                     ok = mWifiConfigStore.removeNetwork(message.arg1);
-                    mReplyChannel.replyToMessage(message, message.what, ok ? SUCCESS : FAILURE);
+                    replyToMessage(message, message.what, ok ? SUCCESS : FAILURE);
                     break;
                 case CMD_ENABLE_NETWORK:
                     ok = mWifiConfigStore.enableNetwork(message.arg1, message.arg2 == 1);
-                    mReplyChannel.replyToMessage(message, message.what, ok ? SUCCESS : FAILURE);
+                    replyToMessage(message, message.what, ok ? SUCCESS : FAILURE);
                     break;
                 case CMD_ENABLE_ALL_NETWORKS:
                     long time =  android.os.SystemClock.elapsedRealtime();
@@ -2340,9 +2280,14 @@
                         mLastEnableAllNetworksTime = time;
                     }
                     break;
-                case CMD_DISABLE_NETWORK:
-                    ok = mWifiConfigStore.disableNetwork(message.arg1, message.arg2);
-                    mReplyChannel.replyToMessage(message, message.what, ok ? SUCCESS : FAILURE);
+                case WifiManager.DISABLE_NETWORK:
+                    if (mWifiConfigStore.disableNetwork(message.arg1,
+                            WifiConfiguration.DISABLED_UNKNOWN_REASON) == true) {
+                        replyToMessage(message, WifiManager.DISABLE_NETWORK_SUCCEEDED);
+                    } else {
+                        replyToMessage(message, WifiManager.DISABLE_NETWORK_FAILED,
+                                WifiManager.ERROR);
+                    }
                     break;
                 case CMD_BLACKLIST_NETWORK:
                     mWifiNative.addToBlacklist((String)message.obj);
@@ -2352,7 +2297,7 @@
                     break;
                 case CMD_SAVE_CONFIG:
                     ok = mWifiConfigStore.saveConfig();
-                    mReplyChannel.replyToMessage(message, CMD_SAVE_CONFIG, ok ? SUCCESS : FAILURE);
+                    replyToMessage(message, CMD_SAVE_CONFIG, ok ? SUCCESS : FAILURE);
 
                     // Inform the backup manager about a data change
                     IBackupManager ibm = IBackupManager.Stub.asInterface(
@@ -2373,12 +2318,25 @@
                 case CMD_SET_SCAN_MODE:
                     mIsScanMode = (message.arg1 == SCAN_ONLY_MODE);
                     break;
-                case CMD_SAVE_NETWORK:
+                case WifiManager.SAVE_NETWORK:
                     config = (WifiConfiguration) message.obj;
-                    mWifiConfigStore.saveNetwork(config);
+                    NetworkUpdateResult result = mWifiConfigStore.saveNetwork(config);
+                    if (result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID) {
+                        replyToMessage(message, WifiManager.SAVE_NETWORK_SUCCEEDED);
+                    } else {
+                        loge("Failed to save network");
+                        replyToMessage(message, WifiManager.SAVE_NETWORK_FAILED,
+                                WifiManager.ERROR);
+                    }
                     break;
-                case CMD_FORGET_NETWORK:
-                    mWifiConfigStore.forgetNetwork(message.arg1);
+                case WifiManager.FORGET_NETWORK:
+                    if (mWifiConfigStore.forgetNetwork(message.arg1)) {
+                        replyToMessage(message, WifiManager.FORGET_NETWORK_SUCCEEDED);
+                    } else {
+                        loge("Failed to forget network");
+                        replyToMessage(message, WifiManager.FORGET_NETWORK_FAILED,
+                                WifiManager.ERROR);
+                    }
                     break;
                 default:
                     return NOT_HANDLED;
@@ -2417,7 +2375,6 @@
             setWifiState(WIFI_STATE_DISABLING);
             sendSupplicantConnectionChangedBroadcast(false);
             mSupplicantStateTracker.sendMessage(CMD_RESET_SUPPLICANT_STATE);
-            mWpsStateMachine.sendMessage(CMD_RESET_WPS_STATE);
         }
         @Override
         public boolean processMessage(Message message) {
@@ -2810,10 +2767,6 @@
                 case WifiMonitor.AUTHENTICATION_FAILURE_EVENT:
                     mSupplicantStateTracker.sendMessage(WifiMonitor.AUTHENTICATION_FAILURE_EVENT);
                     break;
-                case WifiMonitor.WPS_OVERLAP_EVENT:
-                    /* We just need to broadcast the error */
-                    sendErrorBroadcast(WifiManager.WPS_OVERLAP_ERROR);
-                    break;
                 case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT:
                     SupplicantState state = handleSupplicantStateChange(message);
                     // Due to a WEXT bug, during the time of driver start/stop
@@ -2850,7 +2803,7 @@
                 case CMD_REASSOCIATE:
                     mWifiNative.reassociate();
                     break;
-                case CMD_CONNECT_NETWORK:
+                case WifiManager.CONNECT_NETWORK:
                     int netId = message.arg1;
                     WifiConfiguration config = (WifiConfiguration) message.obj;
 
@@ -2868,15 +2821,44 @@
                     }
 
                     /* The state tracker handles enabling networks upon completion/failure */
-                    mSupplicantStateTracker.sendMessage(CMD_CONNECT_NETWORK);
+                    mSupplicantStateTracker.sendMessage(WifiManager.CONNECT_NETWORK);
 
-                    mWifiNative.reconnect();
+                    if (mWifiNative.reconnect()) {
+                        replyToMessage(message, WifiManager.CONNECT_NETWORK_SUCCEEDED);
+                    } else {
+                        loge("Failed to initiate connection");
+                        replyToMessage(message, WifiManager.CONNECT_NETWORK_FAILED,
+                                WifiManager.ERROR);
+                    }
+
                     /* Expect a disconnection from the old connection */
                     transitionTo(mDisconnectingState);
                     break;
-                case CMD_START_WPS:
-                    mWpsStateMachine.sendMessage(Message.obtain(message));
-                    transitionTo(mWaitForWpsCompletionState);
+                case WifiManager.START_WPS:
+                    WpsInfo wpsInfo = (WpsInfo) message.obj;
+                    WpsResult result;
+                    switch (wpsInfo.setup) {
+                        case WpsInfo.PBC:
+                            result = mWifiConfigStore.startWpsPbc(wpsInfo);
+                            break;
+                        case WpsInfo.KEYPAD:
+                            result = mWifiConfigStore.startWpsWithPinFromAccessPoint(wpsInfo);
+                            break;
+                        case WpsInfo.DISPLAY:
+                            result = mWifiConfigStore.startWpsWithPinFromDevice(wpsInfo);
+                            break;
+                        default:
+                            result = new WpsResult(Status.FAILURE);
+                            Log.e(TAG, "Invalid setup for WPS");
+                            break;
+                    }
+                    if (result.status == Status.SUCCESS) {
+                        replyToMessage(message, WifiManager.START_WPS_SUCCEEDED, result);
+                        transitionTo(mWpsRunningState);
+                    } else {
+                        Log.e(TAG, "Failed to start WPS with config " + wpsInfo.toString());
+                        replyToMessage(message, WifiManager.WPS_FAILED, WifiManager.ERROR);
+                    }
                     break;
                 case WifiMonitor.SCAN_RESULTS_EVENT:
                     /* Set the scan setting back to "connect" mode */
@@ -2910,7 +2892,6 @@
         }
     }
 
-
     class L2ConnectedState extends State {
         @Override
         public void enter() {
@@ -2964,13 +2945,13 @@
                     /* Have the parent state handle the rest */
                     return NOT_HANDLED;
                     /* Ignore connection to same network */
-                case CMD_CONNECT_NETWORK:
+                case WifiManager.CONNECT_NETWORK:
                     int netId = message.arg1;
                     if (mWifiInfo.getNetworkId() == netId) {
                         break;
                     }
                     return NOT_HANDLED;
-                case CMD_SAVE_NETWORK:
+                case WifiManager.SAVE_NETWORK:
                     WifiConfiguration config = (WifiConfiguration) message.obj;
                     NetworkUpdateResult result = mWifiConfigStore.saveNetwork(config);
                     if (mWifiInfo.getNetworkId() == result.getNetworkId()) {
@@ -2984,6 +2965,14 @@
                             sendLinkConfigurationChangedBroadcast();
                         }
                     }
+
+                    if (result.getNetworkId() != WifiConfiguration.INVALID_NETWORK_ID) {
+                        replyToMessage(message, WifiManager.SAVE_NETWORK_SUCCEEDED);
+                    } else {
+                        loge("Failed to save network");
+                        replyToMessage(message, WifiManager.SAVE_NETWORK_FAILED,
+                                WifiManager.ERROR);
+                    }
                     break;
                     /* Ignore */
                 case WifiMonitor.NETWORK_CONNECTION_EVENT:
@@ -3073,7 +3062,7 @@
                   handleFailedIpConfiguration();
                   transitionTo(mDisconnectingState);
                   break;
-             case CMD_SAVE_NETWORK:
+             case WifiManager.SAVE_NETWORK:
                   deferMessage(message);
                   break;
                   /* Defer any power mode changes since we must keep active power mode at DHCP */
@@ -3309,36 +3298,77 @@
         }
     }
 
-    class WaitForWpsCompletionState extends State {
+    class WpsRunningState extends State {
+        //Tracks the source to provide a reply
+        private Message mSourceMessage;
         @Override
         public void enter() {
             if (DBG) log(getName() + "\n");
             EventLog.writeEvent(EVENTLOG_WIFI_STATE_CHANGED, getName());
+            mSourceMessage = Message.obtain(getCurrentMessage());
         }
         @Override
         public boolean processMessage(Message message) {
             if (DBG) log(getName() + message.toString() + "\n");
             switch (message.what) {
+                case WifiMonitor.WPS_SUCCESS_EVENT:
+                    replyToMessage(mSourceMessage, WifiManager.WPS_COMPLETED);
+                    mSourceMessage.recycle();
+                    mSourceMessage = null;
+                    transitionTo(mDisconnectedState);
+                    break;
+                case WifiMonitor.WPS_OVERLAP_EVENT:
+                    replyToMessage(mSourceMessage, WifiManager.WPS_FAILED,
+                            WifiManager.WPS_OVERLAP_ERROR);
+                    mSourceMessage.recycle();
+                    mSourceMessage = null;
+                    transitionTo(mDisconnectedState);
+                    break;
+                case WifiMonitor.WPS_FAIL_EVENT:
+                    //arg1 has the reason for the failure
+                    replyToMessage(mSourceMessage, WifiManager.WPS_FAILED, message.arg1);
+                    mSourceMessage.recycle();
+                    mSourceMessage = null;
+                    transitionTo(mDisconnectedState);
+                    break;
+                case WifiMonitor.WPS_TIMEOUT_EVENT:
+                    replyToMessage(mSourceMessage, WifiManager.WPS_FAILED,
+                            WifiManager.WPS_TIMED_OUT);
+                    mSourceMessage.recycle();
+                    mSourceMessage = null;
+                    transitionTo(mDisconnectedState);
+                    break;
+                case WifiManager.START_WPS:
+                    replyToMessage(message, WifiManager.WPS_FAILED, WifiManager.IN_PROGRESS);
+                    break;
+                case WifiManager.CANCEL_WPS:
+                    if (mWifiNative.cancelWps()) {
+                        replyToMessage(message, WifiManager.CANCEL_WPS_SUCCEDED);
+                    } else {
+                        replyToMessage(message, WifiManager.CANCEL_WPS_FAILED, WifiManager.ERROR);
+                    }
+                    transitionTo(mDisconnectedState);
+                    break;
                 /* Defer all commands that can cause connections to a different network
                  * or put the state machine out of connect mode
                  */
                 case CMD_STOP_DRIVER:
                 case CMD_SET_SCAN_MODE:
-                case CMD_CONNECT_NETWORK:
+                case WifiManager.CONNECT_NETWORK:
                 case CMD_ENABLE_NETWORK:
                 case CMD_RECONNECT:
                 case CMD_REASSOCIATE:
-                case WifiMonitor.NETWORK_CONNECTION_EVENT: /* Handled after IP & proxy update */
+                case WifiMonitor.NETWORK_CONNECTION_EVENT: /* Handled after exiting WPS state */
                     deferMessage(message);
                     break;
                 case WifiMonitor.NETWORK_DISCONNECTION_EVENT:
                     if (DBG) log("Network connection lost");
                     handleNetworkDisconnect();
                     break;
-                case WPS_COMPLETED_EVENT:
-                    /* we are still disconnected until we see a network connection
-                     * notification */
-                    transitionTo(mDisconnectedState);
+                case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT:
+                    //Throw away supplicant state changes when WPS is running.
+                    //We will start getting supplicant state changes once we get
+                    //a WPS success or failure
                     break;
                 default:
                     return NOT_HANDLED;
@@ -3346,6 +3376,12 @@
             EventLog.writeEvent(EVENTLOG_WIFI_EVENT_HANDLED, message.what);
             return HANDLED;
         }
+
+        @Override
+        public void exit() {
+            mWifiConfigStore.enableAllNetworks();
+            mWifiConfigStore.loadConfiguredNetworks();
+        }
     }
 
     class SoftApStartingState extends State {
@@ -3605,6 +3641,43 @@
         }
     }
 
+    //State machine initiated requests can have replyTo set to null indicating
+    //there are no recepients, we ignore those reply actions
+    private void replyToMessage(Message msg, int what) {
+        if (msg.replyTo == null) return;
+        Message dstMsg = obtainMessageWithArg2(msg);
+        dstMsg.what = what;
+        mReplyChannel.replyToMessage(msg, dstMsg);
+    }
+
+    private void replyToMessage(Message msg, int what, int arg1) {
+        if (msg.replyTo == null) return;
+        Message dstMsg = obtainMessageWithArg2(msg);
+        dstMsg.what = what;
+        dstMsg.arg1 = arg1;
+        mReplyChannel.replyToMessage(msg, dstMsg);
+    }
+
+    private void replyToMessage(Message msg, int what, Object obj) {
+        if (msg.replyTo == null) return;
+        Message dstMsg = obtainMessageWithArg2(msg);
+        dstMsg.what = what;
+        dstMsg.obj = obj;
+        mReplyChannel.replyToMessage(msg, dstMsg);
+    }
+
+    /**
+     * arg2 on the source message has a unique id that needs to be retained in replies
+     * to match the request
+     *
+     * see WifiManager for details
+     */
+    private Message obtainMessageWithArg2(Message srcMsg) {
+        Message msg = Message.obtain();
+        msg.arg2 = srcMsg.arg2;
+        return msg;
+    }
+
     private void log(String s) {
         Log.d(TAG, s);
     }
diff --git a/wifi/java/android/net/wifi/WpsInfo.java b/wifi/java/android/net/wifi/WpsInfo.java
index f70e5af..b80df21 100644
--- a/wifi/java/android/net/wifi/WpsInfo.java
+++ b/wifi/java/android/net/wifi/WpsInfo.java
@@ -16,9 +16,6 @@
 
 package android.net.wifi;
 
-import android.net.LinkProperties;
-import android.net.wifi.WifiConfiguration.IpAssignment;
-import android.net.wifi.WifiConfiguration.ProxySettings;
 import android.os.Parcelable;
 import android.os.Parcel;
 
@@ -51,22 +48,10 @@
     /** Passed with pin method configuration */
     public String pin;
 
-    /** @hide */
-    public IpAssignment ipAssignment;
-
-    /** @hide */
-    public ProxySettings proxySettings;
-
-    /** @hide */
-    public LinkProperties linkProperties;
-
     public WpsInfo() {
         setup = INVALID;
         BSSID = null;
         pin = null;
-        ipAssignment = IpAssignment.UNASSIGNED;
-        proxySettings = ProxySettings.UNASSIGNED;
-        linkProperties = new LinkProperties();
     }
 
     public String toString() {
@@ -77,12 +62,6 @@
         sbuf.append('\n');
         sbuf.append(" pin: ").append(pin);
         sbuf.append('\n');
-        sbuf.append("IP assignment: " + ipAssignment.toString());
-        sbuf.append("\n");
-        sbuf.append("Proxy settings: " + proxySettings.toString());
-        sbuf.append("\n");
-        sbuf.append(linkProperties.toString());
-        sbuf.append("\n");
         return sbuf.toString();
     }
 
@@ -97,9 +76,6 @@
             setup = source.setup;
             BSSID = source.BSSID;
             pin = source.pin;
-            ipAssignment = source.ipAssignment;
-            proxySettings = source.proxySettings;
-            linkProperties = new LinkProperties(source.linkProperties);
         }
     }
 
@@ -108,9 +84,6 @@
         dest.writeInt(setup);
         dest.writeString(BSSID);
         dest.writeString(pin);
-        dest.writeString(ipAssignment.name());
-        dest.writeString(proxySettings.name());
-        dest.writeParcelable(linkProperties, flags);
     }
 
     /** Implement the Parcelable interface */
@@ -121,9 +94,6 @@
                 config.setup = in.readInt();
                 config.BSSID = in.readString();
                 config.pin = in.readString();
-                config.ipAssignment = IpAssignment.valueOf(in.readString());
-                config.proxySettings = ProxySettings.valueOf(in.readString());
-                config.linkProperties = in.readParcelable(null);
                 return config;
             }
 
diff --git a/wifi/java/android/net/wifi/WpsStateMachine.java b/wifi/java/android/net/wifi/WpsStateMachine.java
deleted file mode 100644
index 441a3b0..0000000
--- a/wifi/java/android/net/wifi/WpsStateMachine.java
+++ /dev/null
@@ -1,208 +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 android.net.wifi;
-
-import com.android.internal.util.AsyncChannel;
-import com.android.internal.util.State;
-import com.android.internal.util.StateMachine;
-
-import android.content.Context;
-import android.content.Intent;
-import android.net.wifi.StateChangeResult;
-import android.net.wifi.WpsResult.Status;
-import android.os.Handler;
-import android.os.Message;
-import android.os.Parcelable;
-import android.util.Log;
-
-/**
- * Manages a WPS connection.
- *
- * WPS consists as a series of EAP exchange triggered
- * by a user action that leads to a successful connection
- * after automatic creation of configuration in the
- * supplicant. We currently support the following methods
- * of WPS setup
- * 1. Pin method: Pin can be either obtained from the device
- *    or from the access point to connect to.
- * 2. Push button method: This involves pushing a button on
- *    the access point and the device
- *
- * After a successful WPS setup, the state machine
- * reloads the configuration and updates the IP and proxy
- * settings, if any.
- */
-class WpsStateMachine extends StateMachine {
-
-    private static final String TAG = "WpsStateMachine";
-    private static final boolean DBG = false;
-
-    private WifiStateMachine mWifiStateMachine;
-    private WifiConfigStore mWifiConfigStore;
-
-    private WpsInfo mWpsInfo;
-
-    private Context mContext;
-    AsyncChannel mReplyChannel = new AsyncChannel();
-
-    private State mDefaultState = new DefaultState();
-    private State mInactiveState = new InactiveState();
-    private State mActiveState = new ActiveState();
-
-    public WpsStateMachine(Context context, WifiStateMachine wsm, WifiConfigStore wcs, Handler t) {
-        super(TAG, t.getLooper());
-
-        mContext = context;
-        mWifiStateMachine = wsm;
-        mWifiConfigStore = wcs;
-        addState(mDefaultState);
-            addState(mInactiveState, mDefaultState);
-            addState(mActiveState, mDefaultState);
-
-        setInitialState(mInactiveState);
-
-        //start the state machine
-        start();
-    }
-
-
-    /********************************************************
-     * HSM states
-     *******************************************************/
-
-    class DefaultState extends State {
-        @Override
-         public void enter() {
-             if (DBG) Log.d(TAG, getName() + "\n");
-         }
-        @Override
-        public boolean processMessage(Message message) {
-            if (DBG) Log.d(TAG, getName() + message.toString() + "\n");
-            WpsInfo wpsConfig;
-            switch (message.what) {
-                case WifiStateMachine.CMD_START_WPS:
-                    mWpsInfo = (WpsInfo) message.obj;
-                    WpsResult result;
-                    switch (mWpsInfo.setup) {
-                        case WpsInfo.PBC:
-                            result = mWifiConfigStore.startWpsPbc(mWpsInfo);
-                            break;
-                        case WpsInfo.KEYPAD:
-                            result = mWifiConfigStore.startWpsWithPinFromAccessPoint(mWpsInfo);
-                            break;
-                        case WpsInfo.DISPLAY:
-                            result = mWifiConfigStore.startWpsWithPinFromDevice(mWpsInfo);
-                            break;
-                        default:
-                            result = new WpsResult(Status.FAILURE);
-                            Log.e(TAG, "Invalid setup for WPS");
-                            break;
-                    }
-                    mReplyChannel.replyToMessage(message, WifiManager.CMD_WPS_COMPLETED, result);
-                    if (result.status == Status.SUCCESS) {
-                        transitionTo(mActiveState);
-                    } else {
-                        Log.e(TAG, "Failed to start WPS with config " + mWpsInfo.toString());
-                    }
-                    break;
-                case WifiStateMachine.CMD_RESET_WPS_STATE:
-                    transitionTo(mInactiveState);
-                    break;
-                default:
-                    Log.e(TAG, "Failed to handle " + message);
-                    break;
-            }
-            return HANDLED;
-        }
-    }
-
-    class ActiveState extends State {
-        @Override
-         public void enter() {
-             if (DBG) Log.d(TAG, getName() + "\n");
-         }
-
-        @Override
-        public boolean processMessage(Message message) {
-            boolean retValue = HANDLED;
-            if (DBG) Log.d(TAG, getName() + message.toString() + "\n");
-            switch (message.what) {
-                case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT:
-                    StateChangeResult stateChangeResult = (StateChangeResult) message.obj;
-                    SupplicantState supState = (SupplicantState) stateChangeResult.state;
-                    switch (supState) {
-                        case COMPLETED:
-                            /* During WPS setup, all other networks are disabled. After
-                             * a successful connect a new config is created in the supplicant.
-                             *
-                             * We need to enable all networks after a successful connection
-                             * and the configuration list needs to be reloaded from the supplicant.
-                             */
-                            Log.d(TAG, "WPS set up successful");
-                            mWifiConfigStore.enableAllNetworks();
-                            mWifiConfigStore.loadConfiguredNetworks();
-                            mWifiConfigStore.updateIpAndProxyFromWpsConfig(
-                                    stateChangeResult.networkId, mWpsInfo);
-                            mWifiStateMachine.sendMessage(WifiStateMachine.WPS_COMPLETED_EVENT);
-                            transitionTo(mInactiveState);
-                            break;
-                        case INACTIVE:
-                            /* A failed WPS connection */
-                            Log.d(TAG, "WPS set up failed, enabling other networks");
-                            mWifiConfigStore.enableAllNetworks();
-                            mWifiStateMachine.sendMessage(WifiStateMachine.WPS_COMPLETED_EVENT);
-                            transitionTo(mInactiveState);
-                            break;
-                        default:
-                            if (DBG) Log.d(TAG, "Ignoring supplicant state " + supState.name());
-                            break;
-                    }
-                    break;
-                case WifiStateMachine.CMD_START_WPS:
-                    /* Ignore request and send an in progress message */
-                    mReplyChannel.replyToMessage(message, WifiManager.CMD_WPS_COMPLETED,
-                                new WpsResult(Status.IN_PROGRESS));
-                    break;
-                default:
-                    retValue = NOT_HANDLED;
-            }
-            return retValue;
-        }
-    }
-
-    class InactiveState extends State {
-        @Override
-        public void enter() {
-            if (DBG) Log.d(TAG, getName() + "\n");
-        }
-
-        @Override
-        public boolean processMessage(Message message) {
-            boolean retValue = HANDLED;
-            if (DBG) Log.d(TAG, getName() + message.toString() + "\n");
-            switch (message.what) {
-                //Ignore supplicant state changes
-                case WifiMonitor.SUPPLICANT_STATE_CHANGE_EVENT:
-                    break;
-                default:
-                    retValue = NOT_HANDLED;
-            }
-            return retValue;
-        }
-    }
-
-}
diff --git a/wifi/java/android/net/wifi/p2p/WifiP2pService.java b/wifi/java/android/net/wifi/p2p/WifiP2pService.java
index 5b0e424..399dc9d 100644
--- a/wifi/java/android/net/wifi/p2p/WifiP2pService.java
+++ b/wifi/java/android/net/wifi/p2p/WifiP2pService.java
@@ -996,7 +996,7 @@
                     break;
                 case PEER_CONNECTION_USER_ACCEPT:
                     if (mSavedPeerConfig.wps.setup == WpsInfo.PBC) {
-                        mWifiNative.startWpsPbc();
+                        mWifiNative.startWpsPbc(null);
                     } else {
                         mWifiNative.startWpsPinKeypad(mSavedPeerConfig.wps.pin);
                     }
