Revert "libmojo: Uprev the library to r456626 from Chromium"

This reverts commit 8ac9103e05b66812c25348943383f9365d1ce3e0.

Reason for revert: Broke the mac_sdk
Exempt-From-Owner-Approval: Fixing mac_sdk

Change-Id: I0b74d1abaa66933a93fd6f82ff018e8948c1204e
diff --git a/base/android/animation_frame_time_histogram.cc b/base/android/animation_frame_time_histogram.cc
index c2b48d3..2cf7516 100644
--- a/base/android/animation_frame_time_histogram.cc
+++ b/base/android/animation_frame_time_histogram.cc
@@ -8,8 +8,6 @@
 #include "base/metrics/histogram_macros.h"
 #include "jni/AnimationFrameTimeHistogram_jni.h"
 
-using base::android::JavaParamRef;
-
 // static
 void SaveHistogram(JNIEnv* env,
                    const JavaParamRef<jobject>& jcaller,
diff --git a/base/android/apk_assets.cc b/base/android/apk_assets.cc
index 19a202c..5319e73 100644
--- a/base/android/apk_assets.cc
+++ b/base/android/apk_assets.cc
@@ -10,20 +10,24 @@
 #include "base/android/jni_array.h"
 #include "base/android/jni_string.h"
 #include "base/android/scoped_java_ref.h"
-#include "base/file_descriptor_store.h"
 #include "jni/ApkAssets_jni.h"
 
 namespace base {
 namespace android {
 
+bool RegisterApkAssets(JNIEnv* env) {
+  return RegisterNativesImpl(env);
+}
+
 int OpenApkAsset(const std::string& file_path,
                  base::MemoryMappedFile::Region* region) {
-  // The AssetManager API of the NDK does not expose a method for accessing raw
-  // resources :(
+  // The AAssetManager API of the NDK is does not expose a method for accessing
+  // raw resources :(.
   JNIEnv* env = base::android::AttachCurrentThread();
   ScopedJavaLocalRef<jlongArray> jarr = Java_ApkAssets_open(
-      env, base::android::GetApplicationContext(),
-      base::android::ConvertUTF8ToJavaString(env, file_path));
+      env,
+      base::android::GetApplicationContext(),
+      base::android::ConvertUTF8ToJavaString(env, file_path).obj());
   std::vector<jlong> results;
   base::android::JavaLongArrayToLongVector(env, jarr.obj(), &results);
   CHECK_EQ(3U, results.size());
@@ -33,16 +37,15 @@
   return fd;
 }
 
-bool RegisterApkAssetWithFileDescriptorStore(const std::string& key,
-                                             const base::FilePath& file_path) {
+bool RegisterApkAssetWithGlobalDescriptors(base::GlobalDescriptors::Key key,
+                                           const std::string& file_path) {
   base::MemoryMappedFile::Region region =
       base::MemoryMappedFile::Region::kWholeFile;
-  int asset_fd = OpenApkAsset(file_path.value(), &region);
-  if (asset_fd == -1)
-    return false;
-  base::FileDescriptorStore::GetInstance().Set(key, base::ScopedFD(asset_fd),
-                                               region);
-  return true;
+  int asset_fd = OpenApkAsset(file_path, &region);
+  if (asset_fd != -1) {
+    base::GlobalDescriptors::GetInstance()->Set(key, asset_fd, region);
+  }
+  return asset_fd != -1;
 }
 
 }  // namespace android
diff --git a/base/android/apk_assets.h b/base/android/apk_assets.h
index cdac000..6eb5da3 100644
--- a/base/android/apk_assets.h
+++ b/base/android/apk_assets.h
@@ -8,12 +8,14 @@
 #include <string>
 
 #include "base/android/jni_android.h"
-#include "base/files/file_path.h"
 #include "base/files/memory_mapped_file.h"
+#include "base/posix/global_descriptors.h"
 
 namespace base {
 namespace android {
 
+bool RegisterApkAssets(JNIEnv* env);
+
 // Opens an asset (e.g. a .pak file) from the apk.
 // Can be used from renderer process.
 // Fails if the asset is not stored uncompressed within the .apk.
@@ -26,12 +28,11 @@
     const std::string& file_path,
     base::MemoryMappedFile::Region* region);
 
-// Registers an uncompressed asset from within the apk in the
-// FileDescriptorStore.
+// Registers an uncompressed asset from within the apk with GlobalDescriptors.
 // Returns: true in case of success, false otherwise.
-BASE_EXPORT bool RegisterApkAssetWithFileDescriptorStore(
-    const std::string& key,
-    const base::FilePath& file_path);
+BASE_EXPORT bool RegisterApkAssetWithGlobalDescriptors(
+    base::GlobalDescriptors::Key key,
+    const std::string& file_path);
 
 }  // namespace android
 }  // namespace base
diff --git a/base/android/base_jni_onload.cc b/base/android/base_jni_onload.cc
index 0a82db4..7ab4982 100644
--- a/base/android/base_jni_onload.cc
+++ b/base/android/base_jni_onload.cc
@@ -12,11 +12,13 @@
 namespace base {
 namespace android {
 
-bool OnJNIOnLoadRegisterJNI(JNIEnv* env) {
+namespace {
+
+bool RegisterJNI(JNIEnv* env) {
   return RegisterLibraryLoaderEntryHook(env);
 }
 
-bool OnJNIOnLoadInit() {
+bool Init() {
   InitAtExitManager();
   JNIEnv* env = base::android::AttachCurrentThread();
   base::android::InitReplacementClassLoader(env,
@@ -24,5 +26,32 @@
   return true;
 }
 
+}  // namespace
+
+
+bool OnJNIOnLoadRegisterJNI(JavaVM* vm,
+                            std::vector<RegisterCallback> callbacks) {
+  base::android::InitVM(vm);
+  JNIEnv* env = base::android::AttachCurrentThread();
+
+  callbacks.push_back(base::Bind(&RegisterJNI));
+  for (std::vector<RegisterCallback>::reverse_iterator i =
+           callbacks.rbegin(); i != callbacks.rend(); ++i) {
+    if (!i->Run(env))
+      return false;
+  }
+  return true;
+}
+
+bool OnJNIOnLoadInit(std::vector<InitCallback> callbacks) {
+  callbacks.push_back(base::Bind(&Init));
+  for (std::vector<InitCallback>::reverse_iterator i =
+           callbacks.rbegin(); i != callbacks.rend(); ++i) {
+    if (!i->Run())
+      return false;
+  }
+  return true;
+}
+
 }  // namespace android
 }  // namespace base
diff --git a/base/android/base_jni_onload.h b/base/android/base_jni_onload.h
index be637d5..dcc7756 100644
--- a/base/android/base_jni_onload.h
+++ b/base/android/base_jni_onload.h
@@ -14,12 +14,17 @@
 namespace base {
 namespace android {
 
-// Returns whether JNI registration succeeded.
+// Returns whether JNI registration succeeded. Caller shall put the
+// RegisterCallback into |callbacks| in reverse order.
 typedef base::Callback<bool(JNIEnv*)> RegisterCallback;
-BASE_EXPORT bool OnJNIOnLoadRegisterJNI(JNIEnv* env);
+BASE_EXPORT bool OnJNIOnLoadRegisterJNI(
+    JavaVM* vm,
+    std::vector<RegisterCallback> callbacks);
 
-// Returns whether initialization succeeded.
-BASE_EXPORT bool OnJNIOnLoadInit();
+// Returns whether initialization succeeded. Caller shall put the
+// InitCallback into |callbacks| in reverse order.
+typedef base::Callback<bool(void)> InitCallback;
+BASE_EXPORT bool OnJNIOnLoadInit(std::vector<InitCallback> callbacks);
 
 }  // namespace android
 }  // namespace base
diff --git a/base/android/base_jni_registrar.cc b/base/android/base_jni_registrar.cc
index 972c333..bc34979 100644
--- a/base/android/base_jni_registrar.cc
+++ b/base/android/base_jni_registrar.cc
@@ -5,23 +5,30 @@
 #include "base/android/base_jni_registrar.h"
 
 #include "base/android/animation_frame_time_histogram.h"
+#include "base/android/apk_assets.h"
 #include "base/android/application_status_listener.h"
+#include "base/android/build_info.h"
+#include "base/android/callback_android.h"
 #include "base/android/command_line_android.h"
+#include "base/android/content_uri_utils.h"
 #include "base/android/context_utils.h"
 #include "base/android/cpu_features.h"
-#include "base/android/early_trace_event_binding.h"
+#include "base/android/event_log.h"
 #include "base/android/field_trial_list.h"
 #include "base/android/important_file_writer_android.h"
-#include "base/android/java_exception_reporter.h"
 #include "base/android/java_handler_thread.h"
+#include "base/android/java_runtime.h"
 #include "base/android/jni_android.h"
 #include "base/android/jni_registrar.h"
+#include "base/android/jni_utils.h"
+#include "base/android/locale_utils.h"
 #include "base/android/memory_pressure_listener_android.h"
 #include "base/android/path_service_android.h"
+#include "base/android/path_utils.h"
 #include "base/android/record_histogram.h"
 #include "base/android/record_user_action.h"
-#include "base/android/statistics_recorder_android.h"
-#include "base/android/time_utils.h"
+#include "base/android/sys_utils.h"
+#include "base/android/thread_utils.h"
 #include "base/android/trace_event_binding.h"
 #include "base/macros.h"
 #include "base/message_loop/message_pump_android.h"
@@ -34,27 +41,33 @@
 static RegistrationMethod kBaseRegisteredMethods[] = {
     {"AnimationFrameTimeHistogram",
      base::android::RegisterAnimationFrameTimeHistogram},
+    {"ApkAssets", base::android::RegisterApkAssets},
     {"ApplicationStatusListener",
      base::android::ApplicationStatusListener::RegisterBindings},
+    {"BuildInfo", base::android::BuildInfo::RegisterBindings},
+    {"CallbackAndroid", base::android::RegisterCallbackAndroid},
     {"CommandLine", base::android::RegisterCommandLine},
+    {"ContentUriUtils", base::RegisterContentUriUtils},
     {"ContextUtils", base::android::RegisterContextUtils},
     {"CpuFeatures", base::android::RegisterCpuFeatures},
-    {"EarlyTraceEvent", base::android::RegisterEarlyTraceEvent},
+    {"EventLog", base::android::RegisterEventLog},
     {"FieldTrialList", base::android::RegisterFieldTrialList},
     {"ImportantFileWriterAndroid",
      base::android::RegisterImportantFileWriterAndroid},
+    {"JNIUtils", base::android::RegisterJNIUtils},
+    {"LocaleUtils", base::android::RegisterLocaleUtils},
     {"MemoryPressureListenerAndroid",
      base::android::MemoryPressureListenerAndroid::Register},
-    {"JavaExceptionReporter", base::android::RegisterJavaExceptionReporterJni},
     {"JavaHandlerThread", base::android::JavaHandlerThread::RegisterBindings},
     {"PathService", base::android::RegisterPathService},
+    {"PathUtils", base::android::RegisterPathUtils},
     {"PowerMonitor", base::RegisterPowerMonitor},
     {"RecordHistogram", base::android::RegisterRecordHistogram},
     {"RecordUserAction", base::android::RegisterRecordUserAction},
-    {"StatisticsRecorderAndroid",
-     base::android::RegisterStatisticsRecorderAndroid},
+    {"Runtime", base::android::JavaRuntime::Register},
     {"SystemMessageHandler", base::MessagePumpForUI::RegisterBindings},
-    {"TimeUtils", base::android::RegisterTimeUtils},
+    {"SysUtils", base::android::SysUtils::Register},
+    {"ThreadUtils", base::RegisterThreadUtils},
     {"TraceEvent", base::android::RegisterTraceEvent},
 };
 
diff --git a/base/android/build_info.cc b/base/android/build_info.cc
index 80b9e0a..ef8f572 100644
--- a/base/android/build_info.cc
+++ b/base/android/build_info.cc
@@ -38,7 +38,7 @@
   }
 
   static const bool kRegisterAtExit = false;
-#if DCHECK_IS_ON()
+#ifndef NDEBUG
   static const bool kAllowedToAccessOnNonjoinableThread = true;
 #endif
 };
@@ -81,5 +81,10 @@
   java_exception_info_ = nullptr;
 }
 
+// static
+bool BuildInfo::RegisterBindings(JNIEnv* env) {
+  return RegisterNativesImpl(env);
+}
+
 }  // namespace android
 }  // namespace base
diff --git a/base/android/build_info.h b/base/android/build_info.h
index cce74f4..838d6f8 100644
--- a/base/android/build_info.h
+++ b/base/android/build_info.h
@@ -26,8 +26,7 @@
   SDK_VERSION_KITKAT_WEAR = 20,
   SDK_VERSION_LOLLIPOP = 21,
   SDK_VERSION_LOLLIPOP_MR1 = 22,
-  SDK_VERSION_MARSHMALLOW = 23,
-  SDK_VERSION_NOUGAT = 24
+  SDK_VERSION_MARSHMALLOW = 23
 };
 
 // BuildInfo is a singleton class that stores android build and device
@@ -111,6 +110,8 @@
 
   void ClearJavaExceptionInfo();
 
+  static bool RegisterBindings(JNIEnv* env);
+
  private:
   friend struct BuildInfoSingletonTraits;
 
diff --git a/base/android/command_line_android.cc b/base/android/command_line_android.cc
index 21ae182..e196aed 100644
--- a/base/android/command_line_android.cc
+++ b/base/android/command_line_android.cc
@@ -12,8 +12,6 @@
 
 using base::android::ConvertUTF8ToJavaString;
 using base::android::ConvertJavaStringToUTF8;
-using base::android::JavaParamRef;
-using base::android::ScopedJavaLocalRef;
 using base::CommandLine;
 
 namespace {
diff --git a/base/android/content_uri_utils.cc b/base/android/content_uri_utils.cc
index f7484cf..31f7b4f 100644
--- a/base/android/content_uri_utils.cc
+++ b/base/android/content_uri_utils.cc
@@ -10,16 +10,19 @@
 #include "jni/ContentUriUtils_jni.h"
 
 using base::android::ConvertUTF8ToJavaString;
-using base::android::ScopedJavaLocalRef;
 
 namespace base {
 
+bool RegisterContentUriUtils(JNIEnv* env) {
+  return RegisterNativesImpl(env);
+}
+
 bool ContentUriExists(const FilePath& content_uri) {
   JNIEnv* env = base::android::AttachCurrentThread();
   ScopedJavaLocalRef<jstring> j_uri =
       ConvertUTF8ToJavaString(env, content_uri.value());
   return Java_ContentUriUtils_contentUriExists(
-      env, base::android::GetApplicationContext(), j_uri);
+      env, base::android::GetApplicationContext(), j_uri.obj());
 }
 
 File OpenContentUriForRead(const FilePath& content_uri) {
@@ -27,7 +30,7 @@
   ScopedJavaLocalRef<jstring> j_uri =
       ConvertUTF8ToJavaString(env, content_uri.value());
   jint fd = Java_ContentUriUtils_openContentUriForRead(
-      env, base::android::GetApplicationContext(), j_uri);
+      env, base::android::GetApplicationContext(), j_uri.obj());
   if (fd < 0)
     return File();
   return File(fd);
@@ -37,8 +40,9 @@
   JNIEnv* env = base::android::AttachCurrentThread();
   ScopedJavaLocalRef<jstring> j_uri =
       ConvertUTF8ToJavaString(env, content_uri.value());
-  ScopedJavaLocalRef<jstring> j_mime = Java_ContentUriUtils_getMimeType(
-      env, base::android::GetApplicationContext(), j_uri);
+  ScopedJavaLocalRef<jstring> j_mime =
+      Java_ContentUriUtils_getMimeType(
+          env, base::android::GetApplicationContext(), j_uri.obj());
   if (j_mime.is_null())
     return std::string();
 
diff --git a/base/android/content_uri_utils.h b/base/android/content_uri_utils.h
index 6d817c0..59fa1e6 100644
--- a/base/android/content_uri_utils.h
+++ b/base/android/content_uri_utils.h
@@ -13,6 +13,8 @@
 
 namespace base {
 
+bool RegisterContentUriUtils(JNIEnv* env);
+
 // Opens a content URI for read and returns the file descriptor to the caller.
 // Returns -1 if the URI is invalid.
 BASE_EXPORT File OpenContentUriForRead(const FilePath& content_uri);
diff --git a/base/android/context_utils.cc b/base/android/context_utils.cc
index e2c4ed0..e9ab723 100644
--- a/base/android/context_utils.cc
+++ b/base/android/context_utils.cc
@@ -33,9 +33,9 @@
 
 }  // namespace
 
-const JavaRef<jobject>& GetApplicationContext() {
+jobject GetApplicationContext() {
   DCHECK(!g_application_context.Get().is_null());
-  return g_application_context.Get();
+  return g_application_context.Get().obj();
 }
 
 static void InitNativeSideApplicationContext(
diff --git a/base/android/context_utils.h b/base/android/context_utils.h
index c5289f1..f172d93 100644
--- a/base/android/context_utils.h
+++ b/base/android/context_utils.h
@@ -16,7 +16,7 @@
 // Gets a global ref to the application context set with
 // InitApplicationContext(). Ownership is retained by the function - the caller
 // must NOT release it.
-BASE_EXPORT const JavaRef<jobject>& GetApplicationContext();
+BASE_EXPORT jobject GetApplicationContext();
 
 bool RegisterContextUtils(JNIEnv* env);
 
diff --git a/base/android/event_log.cc b/base/android/event_log.cc
index 3eb5926..a4b1dd1 100644
--- a/base/android/event_log.cc
+++ b/base/android/event_log.cc
@@ -12,5 +12,9 @@
   Java_EventLog_writeEvent(AttachCurrentThread(), tag, value);
 }
 
+bool RegisterEventLog(JNIEnv* env) {
+  return RegisterNativesImpl(env);
+}
+
 }  // namespace android
 }  // namespace base
diff --git a/base/android/event_log.h b/base/android/event_log.h
index ebd5919..dad4e4c 100644
--- a/base/android/event_log.h
+++ b/base/android/event_log.h
@@ -14,6 +14,8 @@
 
 void BASE_EXPORT EventLogWriteInt(int tag, int value);
 
+bool RegisterEventLog(JNIEnv* env);
+
 }  // namespace android
 }  // namespace base
 
diff --git a/base/android/field_trial_list.cc b/base/android/field_trial_list.cc
index 5150b81..9731a48 100644
--- a/base/android/field_trial_list.cc
+++ b/base/android/field_trial_list.cc
@@ -12,8 +12,6 @@
 
 using base::android::ConvertJavaStringToUTF8;
 using base::android::ConvertUTF8ToJavaString;
-using base::android::JavaParamRef;
-using base::android::ScopedJavaLocalRef;
 
 static ScopedJavaLocalRef<jstring> FindFullName(
     JNIEnv* env,
diff --git a/base/android/fifo_utils.cc b/base/android/fifo_utils.cc
new file mode 100644
index 0000000..8f3e95f
--- /dev/null
+++ b/base/android/fifo_utils.cc
@@ -0,0 +1,25 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "base/android/fifo_utils.h"
+
+#include <sys/stat.h>
+
+#include "base/files/file_path.h"
+
+namespace base {
+namespace android {
+
+bool CreateFIFO(const FilePath& path, int mode) {
+  // Default permissions for mkfifo() is ignored, chmod() is required.
+  return mkfifo(path.value().c_str(), mode) == 0 &&
+         chmod(path.value().c_str(), mode) == 0;
+}
+
+bool RedirectStream(FILE* stream, const FilePath& path, const char* mode) {
+  return freopen(path.value().c_str(), mode, stream) != NULL;
+}
+
+}  // namespace android
+}  // namespace base
diff --git a/base/android/fifo_utils.h b/base/android/fifo_utils.h
new file mode 100644
index 0000000..0bad8e2
--- /dev/null
+++ b/base/android/fifo_utils.h
@@ -0,0 +1,31 @@
+// Copyright 2013 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef BASE_ANDROID_FIFO_UTILS_H_
+#define BASE_ANDROID_FIFO_UTILS_H_
+
+#include <stdio.h>
+
+#include "base/base_export.h"
+
+namespace base {
+
+class FilePath;
+
+namespace android {
+
+// Creates a fifo at the given |path| with POSIX permissions set to |mode|,
+// returning true if it was successfully created and permissions were set.
+BASE_EXPORT bool CreateFIFO(const FilePath& path, int mode);
+
+// Redirects the |stream| to the file provided by |path| with |mode|
+// permissions, returning true if successful.
+BASE_EXPORT bool RedirectStream(FILE* stream,
+                                const FilePath& path,
+                                const char* mode);
+
+}  // namespace android
+}  // namespace base
+
+#endif  // BASE_ANDROID_FIFO_UTILS_H_
diff --git a/base/android/java/src/org/chromium/base/ActivityState.java b/base/android/java/src/org/chromium/base/ActivityState.java
index f4e6413..98aff62 100644
--- a/base/android/java/src/org/chromium/base/ActivityState.java
+++ b/base/android/java/src/org/chromium/base/ActivityState.java
@@ -4,20 +4,10 @@
 
 package org.chromium.base;
 
-import android.support.annotation.IntDef;
-
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-
 /**
  * A set of states that represent the last state change of an Activity.
  */
 public interface ActivityState {
-
-    @Retention(RetentionPolicy.SOURCE)
-    @IntDef({CREATED, STARTED, RESUMED, PAUSED, STOPPED, DESTROYED})
-    public @interface ActivityStateEnum {}
-
     /**
      * Represents Activity#onCreate().
      */
diff --git a/base/android/java/src/org/chromium/base/ApiCompatibilityUtils.java b/base/android/java/src/org/chromium/base/ApiCompatibilityUtils.java
index f773859..9c9c16b 100644
--- a/base/android/java/src/org/chromium/base/ApiCompatibilityUtils.java
+++ b/base/android/java/src/org/chromium/base/ApiCompatibilityUtils.java
@@ -21,7 +21,6 @@
 import android.graphics.ColorFilter;
 import android.graphics.Rect;
 import android.graphics.drawable.Drawable;
-import android.net.Uri;
 import android.os.Build;
 import android.os.PowerManager;
 import android.os.Process;
@@ -32,10 +31,8 @@
 import android.view.ViewGroup.MarginLayoutParams;
 import android.view.Window;
 import android.view.WindowManager;
-import android.view.inputmethod.InputMethodSubtype;
 import android.widget.TextView;
 
-import java.io.File;
 import java.lang.reflect.Method;
 
 /**
@@ -47,22 +44,6 @@
     }
 
     /**
-     * Compares two long values numerically. The value returned is identical to what would be
-     * returned by {@link Long#compare(long, long)} which is available since API level 19.
-     */
-    public static int compareLong(long lhs, long rhs) {
-        return lhs < rhs ? -1 : (lhs == rhs ? 0 : 1);
-    }
-
-    /**
-     * Compares two boolean values. The value returned is identical to what would be returned by
-     * {@link Boolean#compare(boolean, boolean)} which is available since API level 19.
-     */
-    public static int compareBoolean(boolean lhs, boolean rhs) {
-        return lhs == rhs ? 0 : lhs ? 1 : -1;
-    }
-
-    /**
      * Returns true if view's layout direction is right-to-left.
      *
      * @param view the View whose layout is being considered
@@ -413,7 +394,13 @@
      */
     public static void setStatusBarColor(Window window, int statusBarColor) {
         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
+            // If both system bars are black, we can remove these from our layout,
+            // removing or shrinking the SurfaceFlinger overlay required for our views.
+            if (statusBarColor == Color.BLACK && window.getNavigationBarColor() == Color.BLACK) {
+                window.clearFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
+            } else {
+                window.addFlags(WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS);
+            }
             window.setStatusBarColor(statusBarColor);
         }
     }
@@ -528,19 +515,7 @@
     }
 
     /**
-     * See {@link android.os.StatFs#getAvailableBlocksLong}.
-     */
-    @SuppressWarnings("deprecation")
-    public static long getAvailableBlocks(StatFs statFs) {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
-            return statFs.getAvailableBlocksLong();
-        } else {
-            return statFs.getAvailableBlocks();
-        }
-    }
-
-    /**
-     * See {@link android.os.StatFs#getBlockCount}.
+     * See {@link android.os.StatFs#getBlockCount()}.
      */
     @SuppressWarnings("deprecation")
     public static long getBlockCount(StatFs statFs) {
@@ -552,7 +527,7 @@
     }
 
     /**
-     * See {@link android.os.StatFs#getBlockSize}.
+     * See {@link android.os.StatFs#getBlockSize()}.
      */
     @SuppressWarnings("deprecation")
     public static long getBlockSize(StatFs statFs) {
@@ -584,68 +559,4 @@
 
         return false;
     }
-
-    /**
-     * @see Context#checkPermission(String, int, int)
-     */
-    public static int checkPermission(Context context, String permission, int pid, int uid) {
-        try {
-            return context.checkPermission(permission, pid, uid);
-        } catch (RuntimeException e) {
-            // Some older versions of Android throw odd errors when checking for permissions, so
-            // just swallow the exception and treat it as the permission is denied.
-            // crbug.com/639099
-            return PackageManager.PERMISSION_DENIED;
-        }
-    }
-
-    /**
-     * @see android.view.inputmethod.InputMethodSubType#getLocate()
-     */
-    @SuppressWarnings("deprecation")
-    public static String getLocale(InputMethodSubtype inputMethodSubType) {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
-            return inputMethodSubType.getLanguageTag();
-        } else {
-            return inputMethodSubType.getLocale();
-        }
-    }
-
-    /**
-     * Get a URI for |file| which has the image capture. This function assumes that path of |file|
-     * is based on the result of UiUtils.getDirectoryForImageCapture().
-     *
-     * @param context The application context.
-     * @param file image capture file.
-     * @return URI for |file|.
-     */
-    public static Uri getUriForImageCaptureFile(Context context, File file) {
-        return Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2
-                ? ContentUriUtils.getContentUriFromFile(context, file)
-                : Uri.fromFile(file);
-    }
-
-    /**
-     * @see android.view.Window#FEATURE_INDETERMINATE_PROGRESS
-     */
-    public static void setWindowIndeterminateProgress(Window window) {
-        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
-            @SuppressWarnings("deprecation")
-            int featureNumber = Window.FEATURE_INDETERMINATE_PROGRESS;
-
-            @SuppressWarnings("deprecation")
-            int featureValue = Window.PROGRESS_VISIBILITY_OFF;
-
-            window.setFeatureInt(featureNumber, featureValue);
-        }
-    }
-
-    /**
-     *  Null-safe equivalent of {@code a.equals(b)}.
-     *
-     *  @see Objects#equals(Object, Object)
-     */
-    public static boolean objectEquals(Object a, Object b) {
-        return (a == null) ? (b == null) : a.equals(b);
-    }
 }
diff --git a/base/android/java/src/org/chromium/base/ApplicationStatus.java b/base/android/java/src/org/chromium/base/ApplicationStatus.java
index 8d82ed7..37af12d 100644
--- a/base/android/java/src/org/chromium/base/ApplicationStatus.java
+++ b/base/android/java/src/org/chromium/base/ApplicationStatus.java
@@ -4,14 +4,11 @@
 
 package org.chromium.base;
 
-import android.annotation.SuppressLint;
 import android.app.Activity;
 import android.app.Application;
 import android.app.Application.ActivityLifecycleCallbacks;
 import android.os.Bundle;
 
-import org.chromium.base.ActivityState.ActivityStateEnum;
-import org.chromium.base.ApplicationState.ApplicationStateEnum;
 import org.chromium.base.annotations.CalledByNative;
 import org.chromium.base.annotations.JNINamespace;
 import org.chromium.base.annotations.MainDex;
@@ -37,7 +34,6 @@
         /**
          * @return The current {@link ActivityState} of the activity.
          */
-        @ActivityStateEnum
         public int getStatus() {
             return mStatus;
         }
@@ -45,7 +41,7 @@
         /**
          * @param status The new {@link ActivityState} of the activity.
          */
-        public void setStatus(@ActivityStateEnum int status) {
+        public void setStatus(int status) {
             mStatus = status;
         }
 
@@ -58,7 +54,6 @@
     }
 
     private static Object sCachedApplicationStateLock = new Object();
-    @ApplicationStateEnum
     private static Integer sCachedApplicationState;
 
     /** Last activity that was shown (or null if none or it was destroyed). */
@@ -94,7 +89,7 @@
          * Called when the application's state changes.
          * @param newState The application state.
          */
-        public void onApplicationStateChange(@ApplicationStateEnum int newState);
+        public void onApplicationStateChange(int newState);
     }
 
     /**
@@ -106,7 +101,7 @@
          * @param activity The activity that had a state change.
          * @param newState New activity state.
          */
-        public void onActivityStateChange(Activity activity, @ActivityStateEnum int newState);
+        public void onActivityStateChange(Activity activity, int newState);
     }
 
     private ApplicationStatus() {}
@@ -175,7 +170,7 @@
      * @param activity Current activity.
      * @param newState New state value.
      */
-    private static void onStateChange(Activity activity, @ActivityStateEnum int newState) {
+    private static void onStateChange(Activity activity, int newState) {
         if (activity == null) throw new IllegalArgumentException("null activity is not supported");
 
         if (sActivity == null
@@ -188,13 +183,7 @@
         int oldApplicationState = getStateForApplication();
 
         if (newState == ActivityState.CREATED) {
-            // TODO(tedchoc): crbug/691100.  The timing of application callback lifecycles were
-            //                changed in O and the activity info may have been lazily created
-            //                on first access to avoid a crash on startup.  This should be removed
-            //                once the new lifecycle APIs are available.
-            if (!BuildInfo.isAtLeastO()) {
-                assert !sActivityInfo.containsKey(activity);
-            }
+            assert !sActivityInfo.containsKey(activity);
             sActivityInfo.put(activity, new ActivityInfo());
         }
 
@@ -206,13 +195,6 @@
         ActivityInfo info = sActivityInfo.get(activity);
         info.setStatus(newState);
 
-        // Remove before calling listeners so that isEveryActivityDestroyed() returns false when
-        // this was the last activity.
-        if (newState == ActivityState.DESTROYED) {
-            sActivityInfo.remove(activity);
-            if (activity == sActivity) sActivity = null;
-        }
-
         // Notify all state observers that are specifically listening to this activity.
         for (ActivityStateListener listener : info.getListeners()) {
             listener.onActivityStateChange(activity, newState);
@@ -230,6 +212,11 @@
                 listener.onApplicationStateChange(applicationState);
             }
         }
+
+        if (newState == ActivityState.DESTROYED) {
+            sActivityInfo.remove(activity);
+            if (activity == sActivity) sActivity = null;
+        }
     }
 
     /**
@@ -302,7 +289,6 @@
      * @param activity The activity whose state is to be returned.
      * @return The state of the specified activity (see {@link ActivityState}).
      */
-    @ActivityStateEnum
     public static int getStateForActivity(Activity activity) {
         ActivityInfo info = sActivityInfo.get(activity);
         return info != null ? info.getStatus() : ActivityState.DESTROYED;
@@ -311,7 +297,6 @@
     /**
      * @return The state of the application (see {@link ApplicationState}).
      */
-    @ApplicationStateEnum
     @CalledByNative
     public static int getStateForApplication() {
         synchronized (sCachedApplicationStateLock) {
@@ -358,19 +343,11 @@
      * @param listener Listener to receive state changes.
      * @param activity Activity to track or {@code null} to track all activities.
      */
-    @SuppressLint("NewApi")
     public static void registerStateListenerForActivity(ActivityStateListener listener,
             Activity activity) {
         assert activity != null;
 
         ActivityInfo info = sActivityInfo.get(activity);
-        // TODO(tedchoc): crbug/691100.  The timing of application callback lifecycles were changed
-        //                in O and the activity info may need to be lazily created if the onCreate
-        //                event has not yet been received.
-        if (BuildInfo.isAtLeastO() && info == null && !activity.isDestroyed()) {
-            info = new ActivityInfo();
-            sActivityInfo.put(activity, info);
-        }
         assert info != null && info.getStatus() != ActivityState.DESTROYED;
         info.getListeners().addObserver(listener);
     }
@@ -453,7 +430,6 @@
      *         HAS_STOPPED_ACTIVITIES if none are running/paused and one is stopped.
      *         HAS_DESTROYED_ACTIVITIES if none are running/paused/stopped.
      */
-    @ApplicationStateEnum
     private static int determineApplicationState() {
         boolean hasPausedActivity = false;
         boolean hasStoppedActivity = false;
@@ -478,5 +454,5 @@
 
     // Called to notify the native side of state changes.
     // IMPORTANT: This is always called on the main thread!
-    private static native void nativeOnApplicationStateChange(@ApplicationStateEnum int newState);
+    private static native void nativeOnApplicationStateChange(int newState);
 }
diff --git a/base/android/java/src/org/chromium/base/BaseChromiumApplication.java b/base/android/java/src/org/chromium/base/BaseChromiumApplication.java
index 6b97bdd..44c69dc 100644
--- a/base/android/java/src/org/chromium/base/BaseChromiumApplication.java
+++ b/base/android/java/src/org/chromium/base/BaseChromiumApplication.java
@@ -10,7 +10,6 @@
 import android.os.Bundle;
 import android.view.Window;
 
-import org.chromium.base.annotations.SuppressFBWarnings;
 import org.chromium.base.multidex.ChromiumMultiDexInstaller;
 
 import java.lang.reflect.InvocationHandler;
@@ -22,7 +21,8 @@
  * Basic application functionality that should be shared among all browser applications.
  */
 public class BaseChromiumApplication extends Application {
-    private static final String TAG = "base";
+
+    private static final String TAG = "cr.base";
     private static final String TOOLBAR_CALLBACK_INTERNAL_WRAPPER_CLASS =
             "android.support.v7.internal.app.ToolbarActionBar$ToolbarCallbackWrapper";
     // In builds using the --use_unpublished_apis flag, the ToolbarActionBar class name does not
@@ -42,8 +42,6 @@
     @Override
     protected void attachBaseContext(Context base) {
         super.attachBaseContext(base);
-        assert getBaseContext() != null;
-        checkAppBeingReplaced();
         ChromiumMultiDexInstaller.install(this);
     }
 
@@ -60,7 +58,7 @@
     }
 
     private ObserverList<WindowFocusChangedListener> mWindowFocusListeners =
-            new ObserverList<>();
+            new ObserverList<WindowFocusChangedListener>();
 
     /**
      * Intercepts calls to an existing Window.Callback. Most invocations are passed on directly
@@ -146,18 +144,6 @@
         ((BaseChromiumApplication) context.getApplicationContext()).initCommandLine();
     }
 
-    /** Ensure this application object is not out-of-date. */
-    @SuppressFBWarnings("DM_EXIT")
-    private void checkAppBeingReplaced() {
-        // During app update the old apk can still be triggered by broadcasts and spin up an
-        // out-of-date application. Kill old applications in this bad state. See
-        // http://crbug.com/658130 for more context and http://b.android.com/56296 for the bug.
-        if (getResources() == null) {
-            Log.e(TAG, "getResources() null, closing app.");
-            System.exit(0);
-        }
-    }
-
     /** Register hooks and listeners to start tracking the application status. */
     private void startTrackingApplicationStatus() {
         ApplicationStatus.initialize(this);
@@ -172,7 +158,7 @@
 
             @Override
             public void onActivityDestroyed(Activity activity) {
-                if (BuildConfig.DCHECK_IS_ON) {
+                if (BuildConfig.IS_DEBUG) {
                     assert (Proxy.isProxyClass(activity.getWindow().getCallback().getClass())
                             || activity.getWindow().getCallback().getClass().getName().equals(
                                     TOOLBAR_CALLBACK_WRAPPER_CLASS)
@@ -183,7 +169,7 @@
 
             @Override
             public void onActivityPaused(Activity activity) {
-                if (BuildConfig.DCHECK_IS_ON) {
+                if (BuildConfig.IS_DEBUG) {
                     assert (Proxy.isProxyClass(activity.getWindow().getCallback().getClass())
                             || activity.getWindow().getCallback().getClass().getName().equals(
                                     TOOLBAR_CALLBACK_WRAPPER_CLASS)
@@ -194,7 +180,7 @@
 
             @Override
             public void onActivityResumed(Activity activity) {
-                if (BuildConfig.DCHECK_IS_ON) {
+                if (BuildConfig.IS_DEBUG) {
                     assert (Proxy.isProxyClass(activity.getWindow().getCallback().getClass())
                             || activity.getWindow().getCallback().getClass().getName().equals(
                                     TOOLBAR_CALLBACK_WRAPPER_CLASS)
@@ -205,7 +191,7 @@
 
             @Override
             public void onActivitySaveInstanceState(Activity activity, Bundle outState) {
-                if (BuildConfig.DCHECK_IS_ON) {
+                if (BuildConfig.IS_DEBUG) {
                     assert (Proxy.isProxyClass(activity.getWindow().getCallback().getClass())
                             || activity.getWindow().getCallback().getClass().getName().equals(
                                     TOOLBAR_CALLBACK_WRAPPER_CLASS)
@@ -216,7 +202,7 @@
 
             @Override
             public void onActivityStarted(Activity activity) {
-                if (BuildConfig.DCHECK_IS_ON) {
+                if (BuildConfig.IS_DEBUG) {
                     assert (Proxy.isProxyClass(activity.getWindow().getCallback().getClass())
                             || activity.getWindow().getCallback().getClass().getName().equals(
                                     TOOLBAR_CALLBACK_WRAPPER_CLASS)
@@ -227,7 +213,7 @@
 
             @Override
             public void onActivityStopped(Activity activity) {
-                if (BuildConfig.DCHECK_IS_ON) {
+                if (BuildConfig.IS_DEBUG) {
                     assert (Proxy.isProxyClass(activity.getWindow().getCallback().getClass())
                             || activity.getWindow().getCallback().getClass().getName().equals(
                                     TOOLBAR_CALLBACK_WRAPPER_CLASS)
diff --git a/base/android/java/src/org/chromium/base/BuildInfo.java b/base/android/java/src/org/chromium/base/BuildInfo.java
index 141b62b..ea6a019 100644
--- a/base/android/java/src/org/chromium/base/BuildInfo.java
+++ b/base/android/java/src/org/chromium/base/BuildInfo.java
@@ -11,6 +11,7 @@
 import android.content.pm.PackageManager.NameNotFoundException;
 import android.os.Build;
 import android.os.StrictMode;
+import android.util.Log;
 
 import org.chromium.base.annotations.CalledByNative;
 
@@ -71,7 +72,7 @@
             PackageInfo packageInfo = packageManager.getPackageInfo("com.google.android.gms", 0);
             msg = Integer.toString(packageInfo.versionCode);
         } catch (NameNotFoundException e) {
-            Log.d(TAG, "GMS package is not found.", e);
+            Log.d(TAG, "GMS package is not found: %s", e);
         }
         return msg;
     }
@@ -136,13 +137,6 @@
         return Build.TYPE;
     }
 
-    /**
-     * Check if this is a debuggable build of Android. Use this to enable developer-only features.
-     */
-    public static boolean isDebugAndroid() {
-        return "eng".equals(Build.TYPE) || "userdebug".equals(Build.TYPE);
-    }
-
     @CalledByNative
     public static int getSdkInt() {
         return Build.VERSION.SDK_INT;
@@ -154,21 +148,4 @@
     public static boolean isGreaterThanN() {
         return Build.VERSION.SDK_INT > 24 || Build.VERSION.CODENAME.equals("NMR1");
     }
-
-    /**
-     * @return Whether the current device is running Android O release or newer.
-     */
-    public static boolean isAtLeastO() {
-        return !"REL".equals(Build.VERSION.CODENAME)
-                && ("O".equals(Build.VERSION.CODENAME) || Build.VERSION.CODENAME.startsWith("OMR"));
-    }
-
-    /**
-     * @return Whether the current app targets the SDK for at least O
-     */
-    public static boolean targetsAtLeastO(Context appContext) {
-        return isAtLeastO()
-                && appContext.getApplicationInfo().targetSdkVersion
-                == Build.VERSION_CODES.CUR_DEVELOPMENT;
-    }
 }
diff --git a/base/android/java/src/org/chromium/base/CommandLine.java b/base/android/java/src/org/chromium/base/CommandLine.java
index b6246f3..efef22a 100644
--- a/base/android/java/src/org/chromium/base/CommandLine.java
+++ b/base/android/java/src/org/chromium/base/CommandLine.java
@@ -134,8 +134,8 @@
      * @param file The fully qualified command line file.
      */
     public static void initFromFile(String file) {
-        // Arbitrary clamp of 16k on the amount of file we read in.
-        char[] buffer = readUtf8FileFullyCrashIfTooBig(file, 16 * 1024);
+        // Arbitrary clamp of 8k on the amount of file we read in.
+        char[] buffer = readUtf8FileFully(file, 8 * 1024);
         init(buffer == null ? null : tokenizeQuotedAruments(buffer));
     }
 
@@ -238,10 +238,10 @@
     /**
      * @param fileName the file to read in.
      * @param sizeLimit cap on the file size.
-     * @return Array of chars read from the file, or null if the file cannot be read.
-     * @throws RuntimeException if the file size exceeds |sizeLimit|.
+     * @return Array of chars read from the file, or null if the file cannot be read
+     *         or if its length exceeds |sizeLimit|.
      */
-    private static char[] readUtf8FileFullyCrashIfTooBig(String fileName, int sizeLimit) {
+    private static char[] readUtf8FileFully(String fileName, int sizeLimit) {
         Reader reader = null;
         File f = new File(fileName);
         long fileLength = f.length();
@@ -251,8 +251,9 @@
         }
 
         if (fileLength > sizeLimit) {
-            throw new RuntimeException(
-                    "File " + fileName + " length " + fileLength + " exceeds limit " + sizeLimit);
+            Log.w(TAG, "File " + fileName + " length " + fileLength + " exceeds limit "
+                    + sizeLimit);
+            return null;
         }
 
         try {
diff --git a/base/android/java/src/org/chromium/base/CommandLineInitUtil.java b/base/android/java/src/org/chromium/base/CommandLineInitUtil.java
index bec9b40..6aa227c 100644
--- a/base/android/java/src/org/chromium/base/CommandLineInitUtil.java
+++ b/base/android/java/src/org/chromium/base/CommandLineInitUtil.java
@@ -51,9 +51,7 @@
     public static void initCommandLine(Context context, String fileName) {
         if (!CommandLine.isInitialized()) {
             File commandLineFile = getAlternativeCommandLinePath(context, fileName);
-            if (commandLineFile != null) {
-                Log.i(TAG, "Using alternative command line file in " + commandLineFile.getPath());
-            } else {
+            if (commandLineFile == null) {
                 commandLineFile = new File(COMMAND_LINE_FILE_PATH, fileName);
             }
             CommandLine.initFromFile(commandLineFile.getPath());
@@ -61,9 +59,7 @@
     }
 
     /**
-     * Use an alternative path if:
-     * - The current build is "eng" or "userdebug", OR
-     * - adb is enabled and this is the debug app.
+     * Use an alternative path if adb is enabled and this is the debug app.
      */
     @SuppressFBWarnings("DMI_HARDCODED_ABSOLUTE_FILENAME")
     private static File getAlternativeCommandLinePath(Context context, String fileName) {
@@ -71,15 +67,13 @@
                 new File(COMMAND_LINE_FILE_PATH_DEBUG_APP, fileName);
         if (!alternativeCommandLineFile.exists()) return null;
         try {
-            if (BuildInfo.isDebugAndroid()) {
-                return alternativeCommandLineFile;
-            }
-
             String debugApp = Build.VERSION.SDK_INT < 17
                     ? getDebugAppPreJBMR1(context) : getDebugAppJBMR1(context);
 
             if (debugApp != null
                     && debugApp.equals(context.getApplicationContext().getPackageName())) {
+                Log.i(TAG, "Using alternative command line file in "
+                        + alternativeCommandLineFile.getPath());
                 return alternativeCommandLineFile;
             }
         } catch (RuntimeException e) {
diff --git a/base/android/java/src/org/chromium/base/ContentUriUtils.java b/base/android/java/src/org/chromium/base/ContentUriUtils.java
index 9253f28..5448aa0 100644
--- a/base/android/java/src/org/chromium/base/ContentUriUtils.java
+++ b/base/android/java/src/org/chromium/base/ContentUriUtils.java
@@ -6,20 +6,15 @@
 
 import android.content.ContentResolver;
 import android.content.Context;
-import android.content.res.AssetFileDescriptor;
 import android.database.Cursor;
 import android.net.Uri;
-import android.os.Build;
 import android.os.ParcelFileDescriptor;
-import android.provider.DocumentsContract;
 import android.util.Log;
-import android.webkit.MimeTypeMap;
 
 import org.chromium.base.annotations.CalledByNative;
 
 import java.io.File;
 import java.io.FileNotFoundException;
-import java.io.IOException;
 
 /**
  * This class provides methods to access content URI schemes.
@@ -72,9 +67,9 @@
      */
     @CalledByNative
     public static int openContentUriForRead(Context context, String uriString) {
-        AssetFileDescriptor afd = getAssetFileDescriptor(context, uriString);
-        if (afd != null) {
-            return afd.getParcelFileDescriptor().detachFd();
+        ParcelFileDescriptor pfd = getParcelFileDescriptor(context, uriString);
+        if (pfd != null) {
+            return pfd.detachFd();
         }
         return -1;
     }
@@ -88,21 +83,7 @@
      */
     @CalledByNative
     public static boolean contentUriExists(Context context, String uriString) {
-        AssetFileDescriptor asf = null;
-        try {
-            asf = getAssetFileDescriptor(context, uriString);
-            return asf != null;
-        } finally {
-            // Do not use StreamUtil.closeQuietly here, as AssetFileDescriptor
-            // does not implement Closeable until KitKat.
-            if (asf != null) {
-                try {
-                    asf.close();
-                } catch (IOException e) {
-                    // Closing quietly.
-                }
-            }
-        }
+        return getParcelFileDescriptor(context, uriString) != null;
     }
 
     /**
@@ -115,11 +96,8 @@
     @CalledByNative
     public static String getMimeType(Context context, String uriString) {
         ContentResolver resolver = context.getContentResolver();
+        if (resolver == null) return null;
         Uri uri = Uri.parse(uriString);
-        if (isVirtualDocument(uri, context)) {
-            String[] streamTypes = resolver.getStreamTypes(uri, "*/*");
-            return (streamTypes != null && streamTypes.length > 0) ? streamTypes[0] : null;
-        }
         return resolver.getType(uri);
     }
 
@@ -128,36 +106,15 @@
      *
      * @param context {@link Context} in interest.
      * @param uriString the content URI to open.
-     * @return AssetFileDescriptor of the content URI, or NULL if the file does not exist.
+     * @return ParcelFileDescriptor of the content URI, or NULL if the file does not exist.
      */
-    private static AssetFileDescriptor getAssetFileDescriptor(Context context, String uriString) {
+    private static ParcelFileDescriptor getParcelFileDescriptor(Context context, String uriString) {
         ContentResolver resolver = context.getContentResolver();
         Uri uri = Uri.parse(uriString);
 
+        ParcelFileDescriptor pfd = null;
         try {
-            if (isVirtualDocument(uri, context)) {
-                String[] streamTypes = resolver.getStreamTypes(uri, "*/*");
-                if (streamTypes != null && streamTypes.length > 0) {
-                    AssetFileDescriptor afd =
-                            resolver.openTypedAssetFileDescriptor(uri, streamTypes[0], null);
-                    if (afd.getStartOffset() != 0) {
-                        // Do not use StreamUtil.closeQuietly here, as AssetFileDescriptor
-                        // does not implement Closeable until KitKat.
-                        try {
-                            afd.close();
-                        } catch (IOException e) {
-                            // Closing quietly.
-                        }
-                        throw new SecurityException("Cannot open files with non-zero offset type.");
-                    }
-                    return afd;
-                }
-            } else {
-                ParcelFileDescriptor pfd = resolver.openFileDescriptor(uri, "r");
-                if (pfd != null) {
-                    return new AssetFileDescriptor(pfd, 0, AssetFileDescriptor.UNKNOWN_LENGTH);
-                }
-            }
+            pfd = resolver.openFileDescriptor(uri, "r");
         } catch (FileNotFoundException e) {
             Log.w(TAG, "Cannot find content uri: " + uriString, e);
         } catch (SecurityException e) {
@@ -167,103 +124,37 @@
         } catch (IllegalStateException e) {
             Log.w(TAG, "Unknown content uri: " + uriString, e);
         }
-
-        return null;
+        return pfd;
     }
 
     /**
      * Method to resolve the display name of a content URI.
      *
      * @param uri the content URI to be resolved.
-     * @param context {@link Context} in interest.
+     * @param contentResolver the content resolver to query.
      * @param columnField the column field to query.
      * @return the display name of the @code uri if present in the database
      *  or an empty string otherwise.
      */
-    public static String getDisplayName(Uri uri, Context context, String columnField) {
-        if (uri == null) return "";
-        ContentResolver contentResolver = context.getContentResolver();
+    public static String getDisplayName(
+            Uri uri, ContentResolver contentResolver, String columnField) {
+        if (contentResolver == null || uri == null) return "";
         Cursor cursor = null;
         try {
             cursor = contentResolver.query(uri, null, null, null, null);
 
             if (cursor != null && cursor.getCount() >= 1) {
                 cursor.moveToFirst();
-                int displayNameIndex = cursor.getColumnIndex(columnField);
-                if (displayNameIndex == -1) {
-                    return "";
-                }
-                String displayName = cursor.getString(displayNameIndex);
-                // For Virtual documents, try to modify the file extension so it's compatible
-                // with the alternative MIME type.
-                if (hasVirtualFlag(cursor)) {
-                    String[] mimeTypes = contentResolver.getStreamTypes(uri, "*/*");
-                    if (mimeTypes != null && mimeTypes.length > 0) {
-                        String ext =
-                                MimeTypeMap.getSingleton().getExtensionFromMimeType(mimeTypes[0]);
-                        if (ext != null) {
-                            // Just append, it's simpler and more secure than altering an
-                            // existing extension.
-                            displayName += "." + ext;
-                        }
-                    }
-                }
-                return displayName;
+                int index = cursor.getColumnIndex(columnField);
+                if (index > -1) return cursor.getString(index);
             }
         } catch (NullPointerException e) {
             // Some android models don't handle the provider call correctly.
             // see crbug.com/345393
             return "";
         } finally {
-            StreamUtil.closeQuietly(cursor);
+            if (cursor != null) cursor.close();
         }
         return "";
     }
-
-    /**
-     * Checks whether the passed Uri represents a virtual document.
-     *
-     * @param uri the content URI to be resolved.
-     * @param contentResolver the content resolver to query.
-     * @return True for virtual file, false for any other file.
-     */
-    private static boolean isVirtualDocument(Uri uri, Context context) {
-        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.KITKAT) return false;
-        if (uri == null) return false;
-        if (!DocumentsContract.isDocumentUri(context, uri)) return false;
-        ContentResolver contentResolver = context.getContentResolver();
-        Cursor cursor = null;
-        try {
-            cursor = contentResolver.query(uri, null, null, null, null);
-
-            if (cursor != null && cursor.getCount() >= 1) {
-                cursor.moveToFirst();
-                return hasVirtualFlag(cursor);
-            }
-        } catch (NullPointerException e) {
-            // Some android models don't handle the provider call correctly.
-            // see crbug.com/345393
-            return false;
-        } finally {
-            StreamUtil.closeQuietly(cursor);
-        }
-        return false;
-    }
-
-    /**
-     * Checks whether the passed cursor for a document has a virtual document flag.
-     *
-     * The called must close the passed cursor.
-     *
-     * @param cursor Cursor with COLUMN_FLAGS.
-     * @return True for virtual file, false for any other file.
-     */
-    private static boolean hasVirtualFlag(Cursor cursor) {
-        if (Build.VERSION.SDK_INT < Build.VERSION_CODES.N) return false;
-        int index = cursor.getColumnIndex(DocumentsContract.Document.COLUMN_FLAGS);
-        if (index > -1) {
-            return (cursor.getLong(index) & DocumentsContract.Document.FLAG_VIRTUAL_DOCUMENT) != 0;
-        }
-        return false;
-    }
 }
diff --git a/base/android/java/src/org/chromium/base/ContextUtils.java b/base/android/java/src/org/chromium/base/ContextUtils.java
index 448eff9..4b615cb 100644
--- a/base/android/java/src/org/chromium/base/ContextUtils.java
+++ b/base/android/java/src/org/chromium/base/ContextUtils.java
@@ -9,13 +9,11 @@
 import android.preference.PreferenceManager;
 
 import org.chromium.base.annotations.JNINamespace;
-import org.chromium.base.annotations.MainDex;
 
 /**
  * This class provides Android application context related utility methods.
  */
 @JNINamespace("base::android")
-@MainDex
 public class ContextUtils {
     private static final String TAG = "ContextUtils";
     private static Context sApplicationContext;
diff --git a/base/android/java/src/org/chromium/base/FileUtils.java b/base/android/java/src/org/chromium/base/FileUtils.java
index 2ad70dd..2c0d8f5 100644
--- a/base/android/java/src/org/chromium/base/FileUtils.java
+++ b/base/android/java/src/org/chromium/base/FileUtils.java
@@ -12,7 +12,6 @@
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.OutputStream;
-import java.util.List;
 
 /**
  * Helper methods for dealing with Files.
@@ -38,18 +37,6 @@
     }
 
     /**
-     * Delete the given files or directories by calling {@link #recursivelyDeleteFile(File)}.
-     * @param files The files to delete.
-     */
-    public static void batchDeleteFiles(List<File> files) {
-        assert !ThreadUtils.runningOnUiThread();
-
-        for (File file : files) {
-            if (file.exists()) recursivelyDeleteFile(file);
-        }
-    }
-
-    /**
      * Extracts an asset from the app's APK to a file.
      * @param context
      * @param assetName Name of the asset to extract.
diff --git a/base/android/java/src/org/chromium/base/JNIUtils.java b/base/android/java/src/org/chromium/base/JNIUtils.java
index 3fcec91..f971b5e 100644
--- a/base/android/java/src/org/chromium/base/JNIUtils.java
+++ b/base/android/java/src/org/chromium/base/JNIUtils.java
@@ -12,8 +12,6 @@
  */
 @MainDex
 public class JNIUtils {
-    private static Boolean sSelectiveJniRegistrationEnabled;
-
     /**
      * This returns a ClassLoader that is capable of loading Chromium Java code. Such a ClassLoader
      * is needed for the few cases where the JNI mechanism is unable to automatically determine the
@@ -23,24 +21,4 @@
     public static Object getClassLoader() {
         return JNIUtils.class.getClassLoader();
     }
-
-    /**
-     * @return whether or not the current process supports selective JNI registration.
-     */
-    @CalledByNative
-    public static boolean isSelectiveJniRegistrationEnabled() {
-        if (sSelectiveJniRegistrationEnabled == null) {
-            sSelectiveJniRegistrationEnabled = false;
-        }
-        return sSelectiveJniRegistrationEnabled;
-    }
-
-    /**
-     * Allow this process to selectively perform JNI registration. This must be called before
-     * loading native libraries or it will have no effect.
-     */
-    public static void enableSelectiveJniRegistration() {
-        assert sSelectiveJniRegistrationEnabled == null;
-        sSelectiveJniRegistrationEnabled = true;
-    }
 }
diff --git a/base/android/java/src/org/chromium/base/LocaleUtils.java b/base/android/java/src/org/chromium/base/LocaleUtils.java
index 2f51455..5c26e7a 100644
--- a/base/android/java/src/org/chromium/base/LocaleUtils.java
+++ b/base/android/java/src/org/chromium/base/LocaleUtils.java
@@ -4,18 +4,9 @@
 
 package org.chromium.base;
 
-import android.annotation.TargetApi;
-import android.os.Build;
-import android.os.LocaleList;
-import android.text.TextUtils;
-
 import org.chromium.base.annotations.CalledByNative;
 
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashMap;
 import java.util.Locale;
-import java.util.Map;
 
 /**
  * This class provides the locale related methods.
@@ -27,176 +18,41 @@
     private LocaleUtils() {
     }
 
-    private static final Map<String, String> LANGUAGE_MAP_FOR_CHROMIUM;
-    private static final Map<String, String> LANGUAGE_MAP_FOR_ANDROID;
-
-    static {
-        // A variation of this mapping also exists in:
-        // build/android/gyp/package_resources.py
-        HashMap<String, String> mapForChromium = new HashMap<>();
-        mapForChromium.put("iw", "he"); // Hebrew
-        mapForChromium.put("ji", "yi"); // Yiddish
-        mapForChromium.put("in", "id"); // Indonesian
-        mapForChromium.put("tl", "fil"); // Filipino
-        LANGUAGE_MAP_FOR_CHROMIUM = Collections.unmodifiableMap(mapForChromium);
-    }
-
-    static {
-        HashMap<String, String> mapForAndroid = new HashMap<>();
-        mapForAndroid.put("und", ""); // Undefined
-        mapForAndroid.put("fil", "tl"); // Filipino
-        LANGUAGE_MAP_FOR_ANDROID = Collections.unmodifiableMap(mapForAndroid);
-    }
-
     /**
-     * Java keeps deprecated language codes for Hebrew, Yiddish and Indonesian but Chromium uses
-     * updated ones. Similarly, Android uses "tl" while Chromium uses "fil" for Tagalog/Filipino.
-     * So apply a mapping here.
-     * See http://developer.android.com/reference/java/util/Locale.html
-     * @return a updated language code for Chromium with given language string.
+     * @return the string for the given locale, translating
+     * Android deprecated language codes into the modern ones
+     * used by Chromium.
      */
-    public static String getUpdatedLanguageForChromium(String language) {
-        String updatedLanguageCode = LANGUAGE_MAP_FOR_CHROMIUM.get(language);
-        return updatedLanguageCode == null ? language : updatedLanguageCode;
-    }
-
-    /**
-     * @return a locale with updated language codes for Chromium, with translated modern language
-     *         codes used by Chromium.
-     */
-    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
-    @VisibleForTesting
-    public static Locale getUpdatedLocaleForChromium(Locale locale) {
-        String languageForChrome = LANGUAGE_MAP_FOR_CHROMIUM.get(locale.getLanguage());
-        if (languageForChrome == null) {
-            return locale;
-        }
-        return new Locale.Builder().setLocale(locale).setLanguage(languageForChrome).build();
-    }
-
-    /**
-     * Android uses "tl" while Chromium uses "fil" for Tagalog/Filipino.
-     * So apply a mapping here.
-     * See http://developer.android.com/reference/java/util/Locale.html
-     * @return a updated language code for Android with given language string.
-     */
-    public static String getUpdatedLanguageForAndroid(String language) {
-        String updatedLanguageCode = LANGUAGE_MAP_FOR_ANDROID.get(language);
-        return updatedLanguageCode == null ? language : updatedLanguageCode;
-    }
-
-    /**
-     * @return a locale with updated language codes for Android, from translated modern language
-     *         codes used by Chromium.
-     */
-    @TargetApi(Build.VERSION_CODES.LOLLIPOP)
-    @VisibleForTesting
-    public static Locale getUpdatedLocaleForAndroid(Locale locale) {
-        String languageForAndroid = LANGUAGE_MAP_FOR_ANDROID.get(locale.getLanguage());
-        if (languageForAndroid == null) {
-            return locale;
-        }
-        return new Locale.Builder().setLocale(locale).setLanguage(languageForAndroid).build();
-    }
-
-    /**
-     * This function creates a Locale object from xx-XX style string where xx is language code
-     * and XX is a country code. This works for API level lower than 21.
-     * @return the locale that best represents the language tag.
-     */
-    public static Locale forLanguageTagCompat(String languageTag) {
-        String[] tag = languageTag.split("-");
-        if (tag.length == 0) {
-            return new Locale("");
-        }
-        String language = getUpdatedLanguageForAndroid(tag[0]);
-        if ((language.length() != 2 && language.length() != 3) || language.equals("und")) {
-            return new Locale("");
-        }
-        if (tag.length == 1) {
-            return new Locale(language);
-        }
-        String country = tag[1];
-        if (country.length() != 2 && country.length() != 3) {
-            return new Locale(language);
-        }
-        return new Locale(language, country);
-    }
-
-    /**
-     * This function creates a Locale object from xx-XX style string where xx is language code
-     * and XX is a country code.
-     * @return the locale that best represents the language tag.
-     */
-    public static Locale forLanguageTag(String languageTag) {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            Locale locale = Locale.forLanguageTag(languageTag);
-            return getUpdatedLocaleForAndroid(locale);
-        }
-        return forLanguageTagCompat(languageTag);
-    }
-
-    /**
-     * Converts Locale object to the BCP 47 compliant string format.
-     * This works for API level lower than 24.
-     *
-     * Note that for Android M or before, we cannot use Locale.getLanguage() and
-     * Locale.toLanguageTag() for this purpose. Since Locale.getLanguage() returns deprecated
-     * language code even if the Locale object is constructed with updated language code. As for
-     * Locale.toLanguageTag(), it does a special conversion from deprecated language code to updated
-     * one, but it is only usable for Android N or after.
-     * @return a well-formed IETF BCP 47 language tag with language and country code that
-     *         represents this locale.
-     */
-    public static String toLanguageTag(Locale locale) {
-        String language = getUpdatedLanguageForChromium(locale.getLanguage());
+    public static String getLocale(Locale locale) {
+        String language = locale.getLanguage();
         String country = locale.getCountry();
-        if (language.equals("no") && country.equals("NO") && locale.getVariant().equals("NY")) {
-            return "nn-NO";
+
+        // Android uses deprecated lanuages codes for Hebrew and Indonesian but Chromium uses the
+        // updated codes. Also, Android uses "tl" while Chromium uses "fil" for Tagalog/Filipino.
+        // So apply a mapping.
+        // See http://developer.android.com/reference/java/util/Locale.html
+        if ("iw".equals(language)) {
+            language = "he";
+        } else if ("in".equals(language)) {
+            language = "id";
+        } else if ("tl".equals(language)) {
+            language = "fil";
         }
         return country.isEmpty() ? language : language + "-" + country;
     }
 
     /**
-     * Converts LocaleList object to the comma separated BCP 47 compliant string format.
-     *
-     * @return a well-formed IETF BCP 47 language tag with language and country code that
-     *         represents this locale list.
-     */
-    @TargetApi(Build.VERSION_CODES.N)
-    public static String toLanguageTags(LocaleList localeList) {
-        ArrayList<String> newLocaleList = new ArrayList<>();
-        for (int i = 0; i < localeList.size(); i++) {
-            Locale locale = getUpdatedLocaleForChromium(localeList.get(i));
-            newLocaleList.add(toLanguageTag(locale));
-        }
-        return TextUtils.join(",", newLocaleList);
-    }
-
-    /**
-     * @return a comma separated language tags string that represents a default locale.
-     *         Each language tag is well-formed IETF BCP 47 language tag with language and country
-     *         code.
+     * @return the default locale, translating Android deprecated
+     * language codes into the modern ones used by Chromium.
      */
     @CalledByNative
-    public static String getDefaultLocaleString() {
-        return toLanguageTag(Locale.getDefault());
+    public static String getDefaultLocale() {
+        return getLocale(Locale.getDefault());
     }
 
     /**
-     * @return a comma separated language tags string that represents a default locale or locales.
-     *         Each language tag is well-formed IETF BCP 47 language tag with language and country
-     *         code.
-     */
-    public static String getDefaultLocaleListString() {
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
-            return toLanguageTags(LocaleList.getDefault());
-        }
-        return getDefaultLocaleString();
-    }
-
-    /**
-     * @return The default country code set during install.
+     * Get the default country code set during install.
+     * @return country code.
      */
     @CalledByNative
     private static String getDefaultCountryCode() {
diff --git a/base/android/java/src/org/chromium/base/Log.java b/base/android/java/src/org/chromium/base/Log.java
index 399f16d..8815e63 100644
--- a/base/android/java/src/org/chromium/base/Log.java
+++ b/base/android/java/src/org/chromium/base/Log.java
@@ -347,11 +347,6 @@
         }
     }
 
-    /** Handy function to get a loggable stack trace from a Throwable. */
-    public static String getStackTraceString(Throwable tr) {
-        return android.util.Log.getStackTraceString(tr);
-    }
-
     private static Throwable getThrowableToLog(Object[] args) {
         if (args == null || args.length == 0) return null;
 
diff --git a/base/android/java/src/org/chromium/base/ObserverList.java b/base/android/java/src/org/chromium/base/ObserverList.java
index 59276c6..7a2ab98 100644
--- a/base/android/java/src/org/chromium/base/ObserverList.java
+++ b/base/android/java/src/org/chromium/base/ObserverList.java
@@ -21,7 +21,7 @@
  * The implementation (and the interface) is heavily influenced by the C++ ObserverList.
  * Notable differences:
  *   - The iterator implements NOTIFY_EXISTING_ONLY.
- *   - The range-based for loop is left to the clients to implement in terms of iterator().
+ *   - The FOR_EACH_OBSERVER closure is left to the clients to implement in terms of iterator().
  * <p/>
  * This class is not threadsafe. Observers MUST be added, removed and will be notified on the same
  * thread this is created.
@@ -44,9 +44,9 @@
     }
 
     public final List<E> mObservers = new ArrayList<E>();
-    private int mIterationDepth;
-    private int mCount;
-    private boolean mNeedsCompact;
+    private int mIterationDepth = 0;
+    private int mCount = 0;
+    private boolean mNeedsCompact = false;
 
     public ObserverList() {}
 
@@ -190,8 +190,8 @@
 
     private class ObserverListIterator implements RewindableIterator<E> {
         private int mListEndMarker;
-        private int mIndex;
-        private boolean mIsExhausted;
+        private int mIndex = 0;
+        private boolean mIsExhausted = false;
 
         private ObserverListIterator() {
             ObserverList.this.incrementIterationDepth();
diff --git a/base/android/java/src/org/chromium/base/PathUtils.java b/base/android/java/src/org/chromium/base/PathUtils.java
index 00977d5..c3d3e7e 100644
--- a/base/android/java/src/org/chromium/base/PathUtils.java
+++ b/base/android/java/src/org/chromium/base/PathUtils.java
@@ -34,9 +34,13 @@
     private static final AtomicBoolean sInitializationStarted = new AtomicBoolean();
     private static AsyncTask<Void, Void, String[]> sDirPathFetchTask;
 
-    // If the AsyncTask started in setPrivateDataDirectorySuffix() fails to complete by the time we
-    // need the values, we will need the suffix so that we can restart the task synchronously on
-    // the UI thread.
+    // In setPrivateDataDirectorySuffix(), we store the app's context. If the AsyncTask started in
+    // setPrivateDataDirectorySuffix() fails to complete by the time we need the values, we will
+    // need the context so that we can restart the task synchronously on the UI thread.
+    private static Context sDataDirectoryAppContext;
+
+    // We also store the directory path suffix from setPrivateDataDirectorySuffix() for the same
+    // reason as above.
     private static String sDataDirectorySuffix;
 
     // Prevent instantiation.
@@ -97,14 +101,13 @@
      */
     private static String[] setPrivateDataDirectorySuffixInternal() {
         String[] paths = new String[NUM_DIRECTORIES];
-        Context appContext = ContextUtils.getApplicationContext();
-        paths[DATA_DIRECTORY] = appContext.getDir(
-                sDataDirectorySuffix, Context.MODE_PRIVATE).getPath();
-        paths[THUMBNAIL_DIRECTORY] = appContext.getDir(
+        paths[DATA_DIRECTORY] = sDataDirectoryAppContext.getDir(sDataDirectorySuffix,
+                Context.MODE_PRIVATE).getPath();
+        paths[THUMBNAIL_DIRECTORY] = sDataDirectoryAppContext.getDir(
                 THUMBNAIL_DIRECTORY_NAME, Context.MODE_PRIVATE).getPath();
-        paths[DATABASE_DIRECTORY] = appContext.getDatabasePath("foo").getParent();
-        if (appContext.getCacheDir() != null) {
-            paths[CACHE_DIRECTORY] = appContext.getCacheDir().getPath();
+        paths[DATABASE_DIRECTORY] = sDataDirectoryAppContext.getDatabasePath("foo").getParent();
+        if (sDataDirectoryAppContext.getCacheDir() != null) {
+            paths[CACHE_DIRECTORY] = sDataDirectoryAppContext.getCacheDir().getPath();
         }
         return paths;
     }
@@ -121,12 +124,12 @@
      * @param suffix The private data directory suffix.
      * @see Context#getDir(String, int)
      */
-    public static void setPrivateDataDirectorySuffix(String suffix) {
+    public static void setPrivateDataDirectorySuffix(String suffix, Context context) {
         // This method should only be called once, but many tests end up calling it multiple times,
         // so adding a guard here.
         if (!sInitializationStarted.getAndSet(true)) {
-            assert ContextUtils.getApplicationContext() != null;
             sDataDirectorySuffix = suffix;
+            sDataDirectoryAppContext = context.getApplicationContext();
             sDirPathFetchTask = new AsyncTask<Void, Void, String[]>() {
                 @Override
                 protected String[] doInBackground(Void... unused) {
@@ -148,7 +151,7 @@
      * @return the private directory that is used to store application data.
      */
     @CalledByNative
-    public static String getDataDirectory() {
+    public static String getDataDirectory(Context appContext) {
         assert sDirPathFetchTask != null : "setDataDirectorySuffix must be called first.";
         return getDirectoryPath(DATA_DIRECTORY);
     }
@@ -157,7 +160,7 @@
      * @return the private directory that is used to store application database.
      */
     @CalledByNative
-    public static String getDatabaseDirectory() {
+    public static String getDatabaseDirectory(Context appContext) {
         assert sDirPathFetchTask != null : "setDataDirectorySuffix must be called first.";
         return getDirectoryPath(DATABASE_DIRECTORY);
     }
@@ -165,14 +168,15 @@
     /**
      * @return the cache directory.
      */
+    @SuppressWarnings("unused")
     @CalledByNative
-    public static String getCacheDirectory() {
+    public static String getCacheDirectory(Context appContext) {
         assert sDirPathFetchTask != null : "setDataDirectorySuffix must be called first.";
         return getDirectoryPath(CACHE_DIRECTORY);
     }
 
     @CalledByNative
-    public static String getThumbnailCacheDirectory() {
+    public static String getThumbnailCacheDirectory(Context appContext) {
         assert sDirPathFetchTask != null : "setDataDirectorySuffix must be called first.";
         return getDirectoryPath(THUMBNAIL_DIRECTORY);
     }
@@ -182,7 +186,7 @@
      */
     @SuppressWarnings("unused")
     @CalledByNative
-    private static String getDownloadsDirectory() {
+    private static String getDownloadsDirectory(Context appContext) {
         // Temporarily allowing disk access while fixing. TODO: http://crbug.com/508615
         StrictMode.ThreadPolicy oldPolicy = StrictMode.allowThreadDiskReads();
         String downloadsPath;
@@ -203,8 +207,8 @@
      */
     @SuppressWarnings("unused")
     @CalledByNative
-    private static String getNativeLibraryDirectory() {
-        ApplicationInfo ai = ContextUtils.getApplicationContext().getApplicationInfo();
+    private static String getNativeLibraryDirectory(Context appContext) {
+        ApplicationInfo ai = appContext.getApplicationInfo();
         if ((ai.flags & ApplicationInfo.FLAG_UPDATED_SYSTEM_APP) != 0
                 || (ai.flags & ApplicationInfo.FLAG_SYSTEM) == 0) {
             return ai.nativeLibraryDir;
diff --git a/base/android/java/src/org/chromium/base/PerfTraceEvent.java b/base/android/java/src/org/chromium/base/PerfTraceEvent.java
index 8a87773..c0e4b21 100644
--- a/base/android/java/src/org/chromium/base/PerfTraceEvent.java
+++ b/base/android/java/src/org/chromium/base/PerfTraceEvent.java
@@ -8,12 +8,12 @@
 import android.os.Debug.MemoryInfo;
 import android.util.Log;
 
+import org.chromium.base.annotations.SuppressFBWarnings;
+
 import org.json.JSONArray;
 import org.json.JSONException;
 import org.json.JSONObject;
 
-import org.chromium.base.annotations.SuppressFBWarnings;
-
 import java.io.File;
 import java.io.FileNotFoundException;
 import java.io.FileOutputStream;
@@ -42,7 +42,7 @@
 public class PerfTraceEvent {
     private static final int MAX_NAME_LENGTH = 40;
     private static final String MEMORY_TRACE_NAME_SUFFIX = "_BZR_PSS";
-    private static File sOutputFile;
+    private static File sOutputFile = null;
 
     /** The event types understood by the perf trace scripts. */
     private enum EventType {
@@ -63,9 +63,9 @@
         }
     }
 
-    private static boolean sEnabled;
+    private static boolean sEnabled = false;
     private static boolean sTrackTiming = true;
-    private static boolean sTrackMemory;
+    private static boolean sTrackMemory = false;
 
     // A list of performance trace event strings.
     // Events are stored as a JSON dict much like TraceEvent.
diff --git a/base/android/java/src/org/chromium/base/PowerMonitor.java b/base/android/java/src/org/chromium/base/PowerMonitor.java
index ae36a75..5d8fa0c 100644
--- a/base/android/java/src/org/chromium/base/PowerMonitor.java
+++ b/base/android/java/src/org/chromium/base/PowerMonitor.java
@@ -4,61 +4,74 @@
 
 package org.chromium.base;
 
-import android.content.BroadcastReceiver;
 import android.content.Context;
 import android.content.Intent;
 import android.content.IntentFilter;
 import android.os.BatteryManager;
+import android.os.Handler;
+import android.os.Looper;
 
 import org.chromium.base.annotations.CalledByNative;
 import org.chromium.base.annotations.JNINamespace;
 
+
 /**
  * Integrates native PowerMonitor with the java side.
  */
 @JNINamespace("base::android")
-public class PowerMonitor  {
+public class PowerMonitor implements ApplicationStatus.ApplicationStateListener {
+    private static final long SUSPEND_DELAY_MS = 1 * 60 * 1000;  // 1 minute.
+    private static class LazyHolder {
+        private static final PowerMonitor INSTANCE = new PowerMonitor();
+    }
     private static PowerMonitor sInstance;
 
     private boolean mIsBatteryPower;
+    private final Handler mHandler = new Handler(Looper.getMainLooper());
 
-    public static void createForTests() {
+    // Asynchronous task used to fire the "paused" event to the native side 1 minute after the main
+    // activity transitioned to the "paused" state. This event is not sent immediately because it
+    // would be too aggressive. An Android activity can be in the "paused" state quite often. This
+    // can happen when a dialog window shows up for instance.
+    private static final Runnable sSuspendTask = new Runnable() {
+        @Override
+        public void run() {
+            nativeOnMainActivitySuspended();
+        }
+    };
+
+    public static void createForTests(Context context) {
         // Applications will create this once the JNI side has been fully wired up both sides. For
         // tests, we just need native -> java, that is, we don't need to notify java -> native on
         // creation.
-        sInstance = new PowerMonitor();
+        sInstance = LazyHolder.INSTANCE;
     }
 
     /**
      * Create a PowerMonitor instance if none exists.
+     * @param context The context to register broadcast receivers for.  The application context
+     *                will be used from this parameter.
      */
-    public static void create() {
-        ThreadUtils.assertOnUiThread();
-
-        if (sInstance != null) return;
-
-        Context context = ContextUtils.getApplicationContext();
-        sInstance = new PowerMonitor();
-        IntentFilter ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);
-        Intent batteryStatusIntent = context.registerReceiver(null, ifilter);
-        if (batteryStatusIntent != null) onBatteryChargingChanged(batteryStatusIntent);
-
-        IntentFilter powerConnectedFilter = new IntentFilter();
-        powerConnectedFilter.addAction(Intent.ACTION_POWER_CONNECTED);
-        powerConnectedFilter.addAction(Intent.ACTION_POWER_DISCONNECTED);
-        context.registerReceiver(new BroadcastReceiver() {
-            @Override
-            public void onReceive(Context context, Intent intent) {
-                PowerMonitor.onBatteryChargingChanged(intent);
-            }
-        }, powerConnectedFilter);
+    public static void create(Context context) {
+        context = context.getApplicationContext();
+        if (sInstance == null) {
+            sInstance = LazyHolder.INSTANCE;
+            ApplicationStatus.registerApplicationStateListener(sInstance);
+            IntentFilter ifilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);
+            Intent batteryStatusIntent = context.registerReceiver(null, ifilter);
+            if (batteryStatusIntent != null) onBatteryChargingChanged(batteryStatusIntent);
+        }
     }
 
     private PowerMonitor() {
     }
 
-    private static void onBatteryChargingChanged(Intent intent) {
-        assert sInstance != null;
+    public static void onBatteryChargingChanged(Intent intent) {
+        if (sInstance == null) {
+            // We may be called by the framework intent-filter before being fully initialized. This
+            // is not a problem, since our constructor will check for the state later on.
+            return;
+        }
         int chargePlug = intent.getIntExtra(BatteryManager.EXTRA_PLUGGED, -1);
         // If we're not plugged, assume we're running on battery power.
         sInstance.mIsBatteryPower = chargePlug != BatteryManager.BATTERY_PLUGGED_USB
@@ -66,15 +79,23 @@
         nativeOnBatteryChargingChanged();
     }
 
+    @Override
+    public void onApplicationStateChange(int newState) {
+        if (newState == ApplicationState.HAS_RUNNING_ACTIVITIES) {
+            // Remove the callback from the message loop in case it hasn't been executed yet.
+            mHandler.removeCallbacks(sSuspendTask);
+            nativeOnMainActivityResumed();
+        } else if (newState == ApplicationState.HAS_PAUSED_ACTIVITIES) {
+            mHandler.postDelayed(sSuspendTask, SUSPEND_DELAY_MS);
+        }
+    }
+
     @CalledByNative
     private static boolean isBatteryPower() {
-        // Creation of the PowerMonitor can be deferred based on the browser startup path.  If the
-        // battery power is requested prior to the browser triggering the creation, force it to be
-        // created now.
-        if (sInstance == null) create();
-
         return sInstance.mIsBatteryPower;
     }
 
     private static native void nativeOnBatteryChargingChanged();
+    private static native void nativeOnMainActivitySuspended();
+    private static native void nativeOnMainActivityResumed();
 }
diff --git a/base/android/java/src/org/chromium/base/PowerStatusReceiver.java b/base/android/java/src/org/chromium/base/PowerStatusReceiver.java
new file mode 100644
index 0000000..904a740
--- /dev/null
+++ b/base/android/java/src/org/chromium/base/PowerStatusReceiver.java
@@ -0,0 +1,23 @@
+// Copyright 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+package org.chromium.base;
+
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+
+
+/**
+ * A BroadcastReceiver that listens to changes in power status and notifies
+ * PowerMonitor.
+ * It's instantiated by the framework via the application intent-filter
+ * declared in its manifest.
+ */
+public class PowerStatusReceiver extends BroadcastReceiver {
+    @Override
+    public void onReceive(Context context, Intent intent) {
+        PowerMonitor.onBatteryChargingChanged(intent);
+    }
+}
diff --git a/base/android/java/src/org/chromium/base/ResourceExtractor.java b/base/android/java/src/org/chromium/base/ResourceExtractor.java
index c1d1856..2854b02 100644
--- a/base/android/java/src/org/chromium/base/ResourceExtractor.java
+++ b/base/android/java/src/org/chromium/base/ResourceExtractor.java
@@ -4,12 +4,18 @@
 
 package org.chromium.base;
 
+import android.annotation.TargetApi;
+import android.content.Context;
 import android.content.SharedPreferences;
 import android.content.pm.PackageInfo;
 import android.content.pm.PackageManager;
 import android.os.AsyncTask;
+import android.os.Build;
 import android.os.Handler;
 import android.os.Looper;
+import android.os.Trace;
+
+import org.chromium.base.annotations.SuppressFBWarnings;
 
 import java.io.File;
 import java.io.FileOutputStream;
@@ -17,9 +23,7 @@
 import java.io.InputStream;
 import java.io.OutputStream;
 import java.util.ArrayList;
-import java.util.Arrays;
 import java.util.List;
-import java.util.Locale;
 import java.util.concurrent.CancellationException;
 import java.util.concurrent.ExecutionException;
 
@@ -34,7 +38,23 @@
     private static final String V8_NATIVES_DATA_FILENAME = "natives_blob.bin";
     private static final String V8_SNAPSHOT_DATA_FILENAME = "snapshot_blob.bin";
     private static final String APP_VERSION_PREF = "org.chromium.base.ResourceExtractor.Version";
-    private static final String FALLBACK_LOCALE = "en-US";
+
+    private static ResourceEntry[] sResourcesToExtract = new ResourceEntry[0];
+
+    /**
+     * Holds information about a res/raw file (e.g. locale .pak files).
+     */
+    public static final class ResourceEntry {
+        public final int resourceId;
+        public final String pathWithinApk;
+        public final String extractedFileName;
+
+        public ResourceEntry(int resourceId, String pathWithinApk, String extractedFileName) {
+            this.resourceId = resourceId;
+            this.pathWithinApk = pathWithinApk;
+            this.extractedFileName = extractedFileName;
+        }
+    }
 
     private class ExtractTask extends AsyncTask<Void, Void, Void> {
         private static final int BUFFER_SIZE = 16 * 1024;
@@ -72,12 +92,12 @@
                 return;
             }
 
-            TraceEvent.begin("checkPakTimeStamp");
+            beginTraceSection("checkPakTimeStamp");
             long curAppVersion = getApkVersion();
             SharedPreferences sharedPrefs = ContextUtils.getAppSharedPreferences();
             long prevAppVersion = sharedPrefs.getLong(APP_VERSION_PREF, 0);
             boolean versionChanged = curAppVersion != prevAppVersion;
-            TraceEvent.end("checkPakTimeStamp");
+            endTraceSection();
 
             if (versionChanged) {
                 deleteFiles();
@@ -87,23 +107,23 @@
                 sharedPrefs.edit().putLong(APP_VERSION_PREF, curAppVersion).apply();
             }
 
-            TraceEvent.begin("WalkAssets");
+            beginTraceSection("WalkAssets");
             byte[] buffer = new byte[BUFFER_SIZE];
             try {
-                for (String assetName : mAssetsToExtract) {
-                    File output = new File(outputDir, assetName);
+                for (ResourceEntry entry : sResourcesToExtract) {
+                    File output = new File(outputDir, entry.extractedFileName);
                     // TODO(agrieve): It would be better to check that .length == expectedLength.
                     //     http://crbug.com/606413
                     if (output.length() != 0) {
                         continue;
                     }
-                    TraceEvent.begin("ExtractResource");
-                    InputStream inputStream =
-                            ContextUtils.getApplicationContext().getAssets().open(assetName);
+                    beginTraceSection("ExtractResource");
+                    InputStream inputStream = mContext.getResources().openRawResource(
+                            entry.resourceId);
                     try {
                         extractResourceHelper(inputStream, output, buffer);
                     } finally {
-                        TraceEvent.end("ExtractResource");
+                        endTraceSection(); // ExtractResource
                     }
                 }
             } catch (IOException e) {
@@ -111,21 +131,25 @@
                 // Try to recover here, can we try again after deleting files instead of
                 // returning null? It might be useful to gather UMA here too to track if
                 // this happens with regularity.
-                Log.w(TAG, "Exception unpacking required pak asset: %s", e.getMessage());
+                Log.w(TAG, "Exception unpacking required pak resources: %s", e.getMessage());
                 deleteFiles();
                 return;
             } finally {
-                TraceEvent.end("WalkAssets");
+                endTraceSection(); // WalkAssets
             }
         }
 
         @Override
         protected Void doInBackground(Void... unused) {
-            TraceEvent.begin("ResourceExtractor.ExtractTask.doInBackground");
+            // TODO(lizeb): Use chrome tracing here (and above in
+            // doInBackgroundImpl) when it will be possible. This is currently
+            // not doable since the native library is not loaded yet, and the
+            // TraceEvent calls are dropped before this point.
+            beginTraceSection("ResourceExtractor.ExtractTask.doInBackground");
             try {
                 doInBackgroundImpl();
             } finally {
-                TraceEvent.end("ResourceExtractor.ExtractTask.doInBackground");
+                endTraceSection();
             }
             return null;
         }
@@ -139,60 +163,64 @@
 
         @Override
         protected void onPostExecute(Void result) {
-            TraceEvent.begin("ResourceExtractor.ExtractTask.onPostExecute");
+            beginTraceSection("ResourceExtractor.ExtractTask.onPostExecute");
             try {
                 onPostExecuteImpl();
             } finally {
-                TraceEvent.end("ResourceExtractor.ExtractTask.onPostExecute");
+                endTraceSection();
             }
         }
 
         /** Returns a number that is different each time the apk changes. */
         private long getApkVersion() {
-            PackageManager pm = ContextUtils.getApplicationContext().getPackageManager();
+            PackageManager pm = mContext.getPackageManager();
             try {
-                // Use lastUpdateTime since versionCode does not change when developing locally,
-                // but also use versionCode since it is possible for Chrome to be updated without
-                // the lastUpdateTime being changed (http://crbug.org/673458).
-                PackageInfo pi =
-                        pm.getPackageInfo(ContextUtils.getApplicationContext().getPackageName(), 0);
-                // Xor'ing versionCode into upper half of the long to ensure it doesn't somehow
-                // exactly offset an increase in time.
-                return pi.lastUpdateTime ^ (((long) pi.versionCode) << 32);
+                // More appropriate would be versionCode, but it doesn't change while developing.
+                PackageInfo pi = pm.getPackageInfo(mContext.getPackageName(), 0);
+                return pi.lastUpdateTime;
             } catch (PackageManager.NameNotFoundException e) {
                 throw new RuntimeException(e);
             }
         }
+
+        @TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR2)
+        private void beginTraceSection(String section) {
+            if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR2) return;
+            Trace.beginSection(section);
+        }
+
+        @TargetApi(Build.VERSION_CODES.JELLY_BEAN_MR2)
+        private void endTraceSection() {
+            if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR2) return;
+            Trace.endSection();
+        }
     }
 
+    private final Context mContext;
     private ExtractTask mExtractTask;
-    private final String[] mAssetsToExtract = detectFilesToExtract();
 
     private static ResourceExtractor sInstance;
 
-    public static ResourceExtractor get() {
+    public static ResourceExtractor get(Context context) {
         if (sInstance == null) {
-            sInstance = new ResourceExtractor();
+            sInstance = new ResourceExtractor(context);
         }
         return sInstance;
     }
 
-    private static String[] detectFilesToExtract() {
-        Locale defaultLocale = Locale.getDefault();
-        String language = LocaleUtils.getUpdatedLanguageForChromium(defaultLocale.getLanguage());
-        // Currenty (Oct 2016), this array can be as big as 4 entries, so using a capacity
-        // that allows a bit of growth, but is still in the right ballpark..
-        ArrayList<String> activeLocalePakFiles = new ArrayList<String>(6);
-        for (String locale : BuildConfig.COMPRESSED_LOCALES) {
-            if (locale.startsWith(language)) {
-                activeLocalePakFiles.add(locale + ".pak");
-            }
-        }
-        if (activeLocalePakFiles.isEmpty() && BuildConfig.COMPRESSED_LOCALES.length > 0) {
-            assert Arrays.asList(BuildConfig.COMPRESSED_LOCALES).contains(FALLBACK_LOCALE);
-            activeLocalePakFiles.add(FALLBACK_LOCALE + ".pak");
-        }
-        return activeLocalePakFiles.toArray(new String[activeLocalePakFiles.size()]);
+    /**
+     * Specifies the files that should be extracted from the APK.
+     * and moved to {@link #getOutputDir()}.
+     */
+    @SuppressFBWarnings("EI_EXPOSE_STATIC_REP2")
+    public static void setResourcesToExtract(ResourceEntry[] entries) {
+        assert (sInstance == null || sInstance.mExtractTask == null)
+                : "Must be called before startExtractingResources is called";
+        sResourcesToExtract = entries;
+    }
+
+    private ResourceExtractor(Context context) {
+        mContext = context.getApplicationContext();
     }
 
     /**
@@ -273,7 +301,7 @@
     }
 
     private File getAppDataDir() {
-        return new File(PathUtils.getDataDirectory());
+        return new File(PathUtils.getDataDirectory(mContext));
     }
 
     private File getOutputDir() {
@@ -320,6 +348,6 @@
      * Pak extraction not necessarily required by the embedder.
      */
     private static boolean shouldSkipPakExtraction() {
-        return get().mAssetsToExtract.length == 0;
+        return sResourcesToExtract.length == 0;
     }
 }
diff --git a/base/android/java/src/org/chromium/base/SecureRandomInitializer.java b/base/android/java/src/org/chromium/base/SecureRandomInitializer.java
index 294b1e6..457e2ef 100644
--- a/base/android/java/src/org/chromium/base/SecureRandomInitializer.java
+++ b/base/android/java/src/org/chromium/base/SecureRandomInitializer.java
@@ -4,8 +4,6 @@
 
 package org.chromium.base;
 
-import android.annotation.SuppressLint;
-
 import java.io.FileInputStream;
 import java.io.IOException;
 import java.security.SecureRandom;
@@ -15,25 +13,30 @@
  * <= 4.3. See
  * {@link http://android-developers.blogspot.com/2013/08/some-securerandom-thoughts.html}.
  */
-// TODO(crbug.com/635567): Fix this properly.
-@SuppressLint("SecureRandom")
 public class SecureRandomInitializer {
     private static final int NUM_RANDOM_BYTES = 16;
 
+    private static byte[] sSeedBytes = new byte[NUM_RANDOM_BYTES];
+
     /**
      * Safely initializes the random number generator, by seeding it with data from /dev/urandom.
      */
     public static void initialize(SecureRandom generator) throws IOException {
         FileInputStream fis = null;
         try {
-            byte[] seedBytes = new byte[NUM_RANDOM_BYTES];
             fis = new FileInputStream("/dev/urandom");
-            if (fis.read(seedBytes) != seedBytes.length) {
+            if (fis.read(sSeedBytes) != sSeedBytes.length) {
                 throw new IOException("Failed to get enough random data.");
             }
-            generator.setSeed(seedBytes);
+            generator.setSeed(sSeedBytes);
         } finally {
-            StreamUtil.closeQuietly(fis);
+            try {
+                if (fis != null) {
+                    fis.close();
+                }
+            } catch (IOException e) {
+                // Ignore exception closing the device.
+            }
         }
     }
 }
diff --git a/base/android/java/src/org/chromium/base/SysUtils.java b/base/android/java/src/org/chromium/base/SysUtils.java
index 5ab77df..04a8332 100644
--- a/base/android/java/src/org/chromium/base/SysUtils.java
+++ b/base/android/java/src/org/chromium/base/SysUtils.java
@@ -4,9 +4,6 @@
 
 package org.chromium.base;
 
-import android.content.Context;
-import android.content.pm.PackageManager;
-import android.os.Build;
 import android.os.StrictMode;
 import android.util.Log;
 
@@ -102,24 +99,6 @@
         return sLowEndDevice.booleanValue();
     }
 
-    /**
-     * Resets the cached value, if any.
-     */
-    @VisibleForTesting
-    public static void reset() {
-        sLowEndDevice = null;
-    }
-
-    public static boolean hasCamera(final Context context) {
-        final PackageManager pm = context.getPackageManager();
-        // JellyBean support.
-        boolean hasCamera = pm.hasSystemFeature(PackageManager.FEATURE_CAMERA);
-        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
-            hasCamera |= pm.hasSystemFeature(PackageManager.FEATURE_CAMERA_ANY);
-        }
-        return hasCamera;
-    }
-
     private static boolean detectLowEndDevice() {
         assert CommandLine.isInitialized();
         if (CommandLine.getInstance().hasSwitch(BaseSwitches.ENABLE_LOW_END_DEVICE_MODE)) {
diff --git a/base/android/java/src/org/chromium/base/SystemMessageHandler.java b/base/android/java/src/org/chromium/base/SystemMessageHandler.java
index abfa2d8..ebcc0d9 100644
--- a/base/android/java/src/org/chromium/base/SystemMessageHandler.java
+++ b/base/android/java/src/org/chromium/base/SystemMessageHandler.java
@@ -25,12 +25,10 @@
 
     // Native class pointer set by the constructor of the SharedClient native class.
     private long mMessagePumpDelegateNative = 0;
-    private long mMessagePumpNative = 0;
     private long mDelayedScheduledTimeTicks = 0;
 
-    protected SystemMessageHandler(long messagePumpDelegateNative, long messagePumpNative) {
+    private SystemMessageHandler(long messagePumpDelegateNative) {
         mMessagePumpDelegateNative = messagePumpDelegateNative;
-        mMessagePumpNative = messagePumpNative;
     }
 
     @Override
@@ -38,8 +36,7 @@
         if (msg.what == DELAYED_SCHEDULED_WORK) {
             mDelayedScheduledTimeTicks = 0;
         }
-        nativeDoRunLoopOnce(
-                mMessagePumpDelegateNative, mMessagePumpNative, mDelayedScheduledTimeTicks);
+        nativeDoRunLoopOnce(mMessagePumpDelegateNative, mDelayedScheduledTimeTicks);
     }
 
     @SuppressWarnings("unused")
@@ -156,11 +153,10 @@
     }
 
     @CalledByNative
-    private static SystemMessageHandler create(
-            long messagePumpDelegateNative, long messagePumpNative) {
-        return new SystemMessageHandler(messagePumpDelegateNative, messagePumpNative);
+    private static SystemMessageHandler create(long messagePumpDelegateNative) {
+        return new SystemMessageHandler(messagePumpDelegateNative);
     }
 
     private native void nativeDoRunLoopOnce(
-            long messagePumpDelegateNative, long messagePumpNative, long delayedScheduledTimeTicks);
+            long messagePumpDelegateNative, long delayedScheduledTimeTicks);
 }
diff --git a/base/android/java/src/org/chromium/base/ThreadUtils.java b/base/android/java/src/org/chromium/base/ThreadUtils.java
index 737d7f6..ef2887a 100644
--- a/base/android/java/src/org/chromium/base/ThreadUtils.java
+++ b/base/android/java/src/org/chromium/base/ThreadUtils.java
@@ -34,11 +34,6 @@
     @VisibleForTesting
     public static void setUiThread(Looper looper) {
         synchronized (sLock) {
-            if (looper == null) {
-                // Used to reset the looper after tests.
-                sUiThreadHandler = null;
-                return;
-            }
             if (sUiThreadHandler != null && sUiThreadHandler.getLooper() != looper) {
                 throw new RuntimeException("UI thread looper is already set to "
                         + sUiThreadHandler.getLooper() + " (Main thread looper is "
@@ -194,9 +189,7 @@
      * Asserts that the current thread is running on the main thread.
      */
     public static void assertOnUiThread() {
-        if (BuildConfig.DCHECK_IS_ON && !runningOnUiThread()) {
-            throw new IllegalStateException("Must be called on the Ui thread.");
-        }
+        assert runningOnUiThread();
     }
 
     /**
diff --git a/base/android/java/src/org/chromium/base/TraceEvent.java b/base/android/java/src/org/chromium/base/TraceEvent.java
index 71bfac1..878275c 100644
--- a/base/android/java/src/org/chromium/base/TraceEvent.java
+++ b/base/android/java/src/org/chromium/base/TraceEvent.java
@@ -12,19 +12,18 @@
 
 import org.chromium.base.annotations.CalledByNative;
 import org.chromium.base.annotations.JNINamespace;
-import org.chromium.base.annotations.MainDex;
 /**
  * Java mirror of Chrome trace event API. See base/trace_event/trace_event.h. Unlike the native
  * version, Java does not have stack objects, so a TRACE_EVENT() which does both TRACE_EVENT_BEGIN()
  * and TRACE_EVENT_END() in ctor/dtor is not possible.
- * It is OK to use tracing before the native library has loaded, in a slightly restricted fashion.
- * @see EarlyTraceEvent for details.
+ * It is OK to use tracing before the native library has loaded, but such traces will
+ * be ignored. (Perhaps we could devise to buffer them up in future?).
  */
 @JNINamespace("base::android")
-@MainDex
 public class TraceEvent {
-    private static volatile boolean sEnabled;
-    private static volatile boolean sATraceEnabled; // True when taking an Android systrace.
+
+    private static volatile boolean sEnabled = false;
+    private static volatile boolean sATraceEnabled = false; // True when taking an Android systrace.
 
     private static class BasicLooperMonitor implements Printer {
         @Override
@@ -83,14 +82,14 @@
                 MIN_INTERESTING_DURATION_MILLIS * 3;
 
         // Stats tracking
-        private long mLastIdleStartedAt;
-        private long mLastWorkStartedAt;
-        private int mNumTasksSeen;
-        private int mNumIdlesSeen;
-        private int mNumTasksSinceLastIdle;
+        private long mLastIdleStartedAt = 0L;
+        private long mLastWorkStartedAt = 0L;
+        private int mNumTasksSeen = 0;
+        private int mNumIdlesSeen = 0;
+        private int mNumTasksSinceLastIdle = 0;
 
         // State
-        private boolean mIdleMonitorAttached;
+        private boolean mIdleMonitorAttached = false;
 
         // Called from within the begin/end methods only.
         // This method can only execute on the looper thread, because that is
@@ -180,26 +179,11 @@
      */
     @CalledByNative
     public static void setEnabled(boolean enabled) {
-        if (enabled) EarlyTraceEvent.disable();
-        // Only disable logging if Chromium enabled it originally, so as to not disrupt logging done
-        // by other applications
-        if (sEnabled != enabled) {
-            sEnabled = enabled;
-            // Android M+ systrace logs this on its own. Only log it if not writing to Android
-            // systrace.
-            if (sATraceEnabled) return;
-            ThreadUtils.getUiThreadLooper().setMessageLogging(
-                    enabled ? LooperMonitorHolder.sInstance : null);
-        }
-    }
-
-    /**
-     * May enable early tracing depending on the environment.
-     *
-     * Must be called after the command-line has been read.
-     */
-    public static void maybeEnableEarlyTracing() {
-        EarlyTraceEvent.maybeEnable();
+        sEnabled = enabled;
+        // Android M+ systrace logs this on its own. Only log it if not writing to Android systrace.
+        if (sATraceEnabled) return;
+        ThreadUtils.getUiThreadLooper().setMessageLogging(
+                enabled ? LooperMonitorHolder.sInstance : null);
     }
 
     /**
@@ -270,7 +254,7 @@
      * @param name The name of the event.
      */
     public static void begin(String name) {
-        begin(name, null);
+        if (sEnabled) nativeBegin(name, null);
     }
 
     /**
@@ -279,7 +263,6 @@
      * @param arg  The arguments of the event.
      */
     public static void begin(String name, String arg) {
-        EarlyTraceEvent.begin(name);
         if (sEnabled) nativeBegin(name, arg);
     }
 
@@ -288,7 +271,7 @@
      * @param name The name of the event.
      */
     public static void end(String name) {
-        end(name, null);
+        if (sEnabled) nativeEnd(name, null);
     }
 
     /**
@@ -297,7 +280,6 @@
      * @param arg  The arguments of the event.
      */
     public static void end(String name, String arg) {
-        EarlyTraceEvent.end(name);
         if (sEnabled) nativeEnd(name, arg);
     }
 
diff --git a/base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java b/base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java
index d3e0fb9..f6bf867 100644
--- a/base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java
+++ b/base/android/java/src/org/chromium/base/library_loader/LibraryLoader.java
@@ -4,7 +4,6 @@
 
 package org.chromium.base.library_loader;
 
-import android.annotation.SuppressLint;
 import android.content.Context;
 import android.os.AsyncTask;
 import android.os.SystemClock;
@@ -13,10 +12,8 @@
 import org.chromium.base.ContextUtils;
 import org.chromium.base.Log;
 import org.chromium.base.TraceEvent;
-import org.chromium.base.VisibleForTesting;
 import org.chromium.base.annotations.CalledByNative;
 import org.chromium.base.annotations.JNINamespace;
-import org.chromium.base.annotations.MainDex;
 import org.chromium.base.metrics.RecordHistogram;
 
 import java.util.concurrent.atomic.AtomicBoolean;
@@ -38,7 +35,6 @@
  * the native counterpart to this class.
  */
 @JNINamespace("base::android")
-@MainDex
 public class LibraryLoader {
     private static final String TAG = "LibraryLoader";
 
@@ -133,14 +129,18 @@
 
     /**
      *  This method blocks until the library is fully loaded and initialized.
+     *
+     *  @param context The context in which the method is called.
      */
-    public void ensureInitialized() throws ProcessInitException {
+    public void ensureInitialized(Context context) throws ProcessInitException {
+        // TODO(wnwen): Move this call appropriately down to the tests that need it.
+        ContextUtils.initApplicationContext(context.getApplicationContext());
         synchronized (sLock) {
             if (mInitialized) {
                 // Already initialized, nothing to do.
                 return;
             }
-            loadAlreadyLocked(ContextUtils.getApplicationContext());
+            loadAlreadyLocked(context);
             initializeAlreadyLocked();
         }
     }
@@ -159,26 +159,13 @@
      * this is called on will be the thread that runs the native code's static initializers.
      * See the comment in doInBackground() for more considerations on this.
      *
+     * @param context The context the code is running.
+     *
      * @throws ProcessInitException if the native library failed to load.
      */
-    public void loadNow() throws ProcessInitException {
-        loadNowOverrideApplicationContext(ContextUtils.getApplicationContext());
-    }
-
-    /**
-     * Override kept for callers that need to load from a different app context. Do not use unless
-     * specifically required to load from another context that is not the current process's app
-     * context.
-     *
-     * @param appContext The overriding app context to be used to load libraries.
-     * @throws ProcessInitException if the native library failed to load with this context.
-     */
-    public void loadNowOverrideApplicationContext(Context appContext) throws ProcessInitException {
+    public void loadNow(Context context) throws ProcessInitException {
         synchronized (sLock) {
-            if (mLoaded && appContext != ContextUtils.getApplicationContext()) {
-                throw new IllegalStateException("Attempt to load again from alternate context.");
-            }
-            loadAlreadyLocked(appContext);
+            loadAlreadyLocked(context);
         }
     }
 
@@ -210,10 +197,7 @@
                 TraceEvent.begin("LibraryLoader.asyncPrefetchLibrariesToMemory");
                 int percentage = nativePercentageOfResidentNativeLibraryCode();
                 boolean success = false;
-                // Arbitrary percentage threshold. If most of the native library is already
-                // resident (likely with monochrome), don't bother creating a prefetch process.
-                boolean prefetch = coldStart && percentage < 90;
-                if (prefetch) {
+                if (coldStart) {
                     success = nativeForkAndPrefetchNativeLibrary();
                     if (!success) {
                         Log.w(TAG, "Forking a process to prefetch the native library failed.");
@@ -222,7 +206,7 @@
                 // As this runs in a background thread, it can be called before histograms are
                 // initialized. In this instance, histograms are dropped.
                 RecordHistogram.initialize();
-                if (prefetch) {
+                if (coldStart) {
                     RecordHistogram.recordBooleanHistogram("LibraryLoader.PrefetchStatus", success);
                 }
                 if (percentage != -1) {
@@ -263,9 +247,7 @@
 
     // Invoke either Linker.loadLibrary(...) or System.loadLibrary(...), triggering
     // JNI_OnLoad in native code
-    // TODO(crbug.com/635567): Fix this properly.
-    @SuppressLint("DefaultLocale")
-    private void loadAlreadyLocked(Context appContext) throws ProcessInitException {
+    private void loadAlreadyLocked(Context context) throws ProcessInitException {
         try {
             if (!mLoaded) {
                 assert !mInitialized;
@@ -291,35 +273,25 @@
                         String libFilePath = System.mapLibraryName(library);
                         if (Linker.isInZipFile()) {
                             // Load directly from the APK.
-                            zipFilePath = appContext.getApplicationInfo().sourceDir;
+                            zipFilePath = context.getApplicationInfo().sourceDir;
                             Log.i(TAG, "Loading " + library + " from within " + zipFilePath);
                         } else {
                             // The library is in its own file.
                             Log.i(TAG, "Loading " + library);
                         }
 
-                        try {
-                            // Load the library using this Linker. May throw UnsatisfiedLinkError.
-                            loadLibrary(linker, zipFilePath, libFilePath);
-                        } catch (UnsatisfiedLinkError e) {
-                            Log.e(TAG, "Unable to load library: " + library);
-                            throw(e);
-                        }
+                        // Load the library using this Linker. May throw UnsatisfiedLinkError.
+                        loadLibrary(linker, zipFilePath, libFilePath);
                     }
 
                     linker.finishLibraryLoad();
                 } else {
                     if (sLibraryPreloader != null) {
-                        mLibraryPreloaderStatus = sLibraryPreloader.loadLibrary(appContext);
+                        mLibraryPreloaderStatus = sLibraryPreloader.loadLibrary(context);
                     }
                     // Load libraries using the system linker.
                     for (String library : NativeLibraries.LIBRARIES) {
-                        try {
-                            System.loadLibrary(library);
-                        } catch (UnsatisfiedLinkError e) {
-                            Log.e(TAG, "Unable to load library: " + library);
-                            throw(e);
-                        }
+                        System.loadLibrary(library);
                     }
                 }
 
@@ -335,6 +307,21 @@
         } catch (UnsatisfiedLinkError e) {
             throw new ProcessInitException(LoaderErrors.LOADER_ERROR_NATIVE_LIBRARY_LOAD_FAILED, e);
         }
+        // Check that the version of the library we have loaded matches the version we expect
+        Log.i(TAG, String.format(
+                "Expected native library version number \"%s\", "
+                        + "actual native library version number \"%s\"",
+                NativeLibraries.sVersionNumber,
+                nativeGetVersionNumber()));
+        if (!NativeLibraries.sVersionNumber.equals(nativeGetVersionNumber())) {
+            throw new ProcessInitException(LoaderErrors.LOADER_ERROR_NATIVE_LIBRARY_WRONG_VERSION);
+        }
+    }
+
+    // Returns whether the given split name is that of the ABI split.
+    private static boolean isAbiSplit(String splitName) {
+        // The split name for the ABI split is manually set in the build rules.
+        return splitName.startsWith("abi_");
     }
 
     // The WebView requires the Command Line to be switched over before
@@ -376,14 +363,6 @@
             throw new ProcessInitException(LoaderErrors.LOADER_ERROR_FAILED_TO_REGISTER_JNI);
         }
 
-        // Check that the version of the library we have loaded matches the version we expect
-        Log.i(TAG, String.format("Expected native library version number \"%s\", "
-                                   + "actual native library version number \"%s\"",
-                           NativeLibraries.sVersionNumber, nativeGetVersionNumber()));
-        if (!NativeLibraries.sVersionNumber.equals(nativeGetVersionNumber())) {
-            throw new ProcessInitException(LoaderErrors.LOADER_ERROR_NATIVE_LIBRARY_WRONG_VERSION);
-        }
-
         // From now on, keep tracing in sync with native.
         TraceEvent.registerNativeEnabledObserver();
 
@@ -396,19 +375,18 @@
     }
 
     // Called after all native initializations are complete.
-    public void onNativeInitializationComplete() {
-        recordBrowserProcessHistogram();
+    public void onNativeInitializationComplete(Context context) {
+        recordBrowserProcessHistogram(context);
     }
 
     // Record Chromium linker histogram state for the main browser process. Called from
     // onNativeInitializationComplete().
-    private void recordBrowserProcessHistogram() {
+    private void recordBrowserProcessHistogram(Context context) {
         if (Linker.getInstance().isUsed()) {
-            nativeRecordChromiumAndroidLinkerBrowserHistogram(
-                    mIsUsingBrowserSharedRelros,
-                    mLoadAtFixedAddressFailed,
-                    getLibraryLoadFromApkStatus(),
-                    mLibraryLoadTimeMs);
+            nativeRecordChromiumAndroidLinkerBrowserHistogram(mIsUsingBrowserSharedRelros,
+                                                              mLoadAtFixedAddressFailed,
+                                                              getLibraryLoadFromApkStatus(context),
+                                                              mLibraryLoadTimeMs);
         }
         if (sLibraryPreloader != null) {
             nativeRecordLibraryPreloaderBrowserHistogram(mLibraryPreloaderStatus);
@@ -417,7 +395,7 @@
 
     // Returns the device's status for loading a library directly from the APK file.
     // This method can only be called when the Chromium linker is used.
-    private int getLibraryLoadFromApkStatus() {
+    private int getLibraryLoadFromApkStatus(Context context) {
         assert Linker.getInstance().isUsed();
 
         if (mLibraryWasLoadedFromApk) {
@@ -454,15 +432,6 @@
         return sInstance.mLibraryProcessType;
     }
 
-    /**
-     * Override the library loader (normally with a mock) for testing.
-     * @param loader the mock library loader.
-     */
-    @VisibleForTesting
-    public static void setLibraryLoaderForTesting(LibraryLoader loader) {
-        sInstance = loader;
-    }
-
     private native void nativeInitCommandLine(String[] initCommandLine);
 
     // Only methods needed before or during normal JNI registration are during System.OnLoad.
diff --git a/base/android/java/src/org/chromium/base/library_loader/Linker.java b/base/android/java/src/org/chromium/base/library_loader/Linker.java
index 7d19995..271e6cb 100644
--- a/base/android/java/src/org/chromium/base/library_loader/Linker.java
+++ b/base/android/java/src/org/chromium/base/library_loader/Linker.java
@@ -503,24 +503,32 @@
     }
 
     /**
-     * Determine whether a library is the linker library.
+     * Determine whether a library is the linker library. Also deal with the
+     * component build that adds a .cr suffix to the name.
      *
      * @param library the name of the library.
      * @return true is the library is the Linker's own JNI library.
      */
     public boolean isChromiumLinkerLibrary(String library) {
-        return library.equals(LINKER_JNI_LIBRARY);
+        return library.equals(LINKER_JNI_LIBRARY) || library.equals(LINKER_JNI_LIBRARY + ".cr");
     }
 
     /**
      * Load the Linker JNI library. Throws UnsatisfiedLinkError on error.
+     * In a component build, the suffix ".cr" is added to each library name, so
+     * if the initial load fails we retry with a suffix.
      */
     protected static void loadLinkerJniLibrary() {
         String libName = "lib" + LINKER_JNI_LIBRARY + ".so";
         if (DEBUG) {
             Log.i(TAG, "Loading " + libName);
         }
-        System.loadLibrary(LINKER_JNI_LIBRARY);
+        try {
+            System.loadLibrary(LINKER_JNI_LIBRARY);
+        } catch (UnsatisfiedLinkError e) {
+            Log.w(TAG, "Couldn't load " + libName + ", trying " + libName + ".cr");
+            System.loadLibrary(LINKER_JNI_LIBRARY + ".cr");
+        }
     }
 
     /**
diff --git a/base/android/java/src/org/chromium/base/library_loader/ModernLinker.java b/base/android/java/src/org/chromium/base/library_loader/ModernLinker.java
index 15021c7..7716a8d 100644
--- a/base/android/java/src/org/chromium/base/library_loader/ModernLinker.java
+++ b/base/android/java/src/org/chromium/base/library_loader/ModernLinker.java
@@ -251,6 +251,8 @@
             Log.i(TAG, "disableSharedRelros() called");
         }
         synchronized (mLock) {
+            assert !mPrepareLibraryLoadCalled;
+
             // Mark this as a service process, and disable wait for shared RELRO.
             mInBrowserProcess = false;
             mWaitForSharedRelros = false;
@@ -386,7 +388,7 @@
                 // We are in the browser, and with a current load address that indicates that
                 // there is enough address space for shared RELRO to operate. Create the
                 // shared RELRO, and store it in the map.
-                String relroPath = PathUtils.getDataDirectory() + "/RELRO:" + libFilePath;
+                String relroPath = PathUtils.getDataDirectory(null) + "/RELRO:" + libFilePath;
                 if (nativeCreateSharedRelro(dlopenExtPath,
                                             mCurrentLoadAddress, relroPath, libInfo)) {
                     mSharedRelros.put(dlopenExtPath, libInfo);
diff --git a/base/android/java/src/org/chromium/base/metrics/RecordHistogram.java b/base/android/java/src/org/chromium/base/metrics/RecordHistogram.java
index eaf57b7..56a5803 100644
--- a/base/android/java/src/org/chromium/base/metrics/RecordHistogram.java
+++ b/base/android/java/src/org/chromium/base/metrics/RecordHistogram.java
@@ -25,23 +25,16 @@
  */
 @JNINamespace("base::android")
 public class RecordHistogram {
-    private static Throwable sDisabledBy;
+    private static boolean sIsDisabledForTests = false;
     private static Map<String, Long> sCache =
             Collections.synchronizedMap(new HashMap<String, Long>());
 
     /**
-     * Tests may not have native initialized, so they may need to disable metrics. The value should
-     * be reset after the test done, to avoid carrying over state to unrelated tests.
-     *
-     * In JUnit tests this can be done automatically using
-     * {@link org.chromium.chrome.browser.DisableHistogramsRule}
+     * Tests may not have native initialized, so they may need to disable metrics.
      */
     @VisibleForTesting
-    public static void setDisabledForTests(boolean disabled) {
-        if (disabled && sDisabledBy != null) {
-            throw new IllegalStateException("Histograms are already disabled.", sDisabledBy);
-        }
-        sDisabledBy = disabled ? new Throwable() : null;
+    public static void disableForTests() {
+        sIsDisabledForTests = true;
     }
 
     private static long getCachedHistogramKey(String name) {
@@ -61,7 +54,7 @@
      * @param sample sample to be recorded, either true or false
      */
     public static void recordBooleanHistogram(String name, boolean sample) {
-        if (sDisabledBy != null) return;
+        if (sIsDisabledForTests) return;
         long key = getCachedHistogramKey(name);
         long result = nativeRecordBooleanHistogram(name, key, sample);
         if (result != key) sCache.put(name, result);
@@ -77,7 +70,7 @@
      *        lower than |boundary|
      */
     public static void recordEnumeratedHistogram(String name, int sample, int boundary) {
-        if (sDisabledBy != null) return;
+        if (sIsDisabledForTests) return;
         long key = getCachedHistogramKey(name);
         long result = nativeRecordEnumeratedHistogram(name, key, sample, boundary);
         if (result != key) sCache.put(name, result);
@@ -118,13 +111,13 @@
      * UMA_HISTOGRAM_CUSTOM_COUNTS C++ macro.
      * @param name name of the histogram
      * @param sample sample to be recorded, at least |min| and at most |max| - 1
-     * @param min lower bound for expected sample values. It must be >= 1
+     * @param min lower bound for expected sample values
      * @param max upper bounds for expected sample values
      * @param numBuckets the number of buckets
      */
     public static void recordCustomCountHistogram(
             String name, int sample, int min, int max, int numBuckets) {
-        if (sDisabledBy != null) return;
+        if (sIsDisabledForTests) return;
         long key = getCachedHistogramKey(name);
         long result = nativeRecordCustomCountHistogram(name, key, sample, min, max, numBuckets);
         if (result != key) sCache.put(name, result);
@@ -141,7 +134,7 @@
      */
     public static void recordLinearCountHistogram(
             String name, int sample, int min, int max, int numBuckets) {
-        if (sDisabledBy != null) return;
+        if (sIsDisabledForTests) return;
         long key = getCachedHistogramKey(name);
         long result = nativeRecordLinearCountHistogram(name, key, sample, min, max, numBuckets);
         if (result != key) sCache.put(name, result);
@@ -154,7 +147,7 @@
      * @param sample sample to be recorded, at least 0 and at most 100.
      */
     public static void recordPercentageHistogram(String name, int sample) {
-        if (sDisabledBy != null) return;
+        if (sIsDisabledForTests) return;
         long key = getCachedHistogramKey(name);
         long result = nativeRecordEnumeratedHistogram(name, key, sample, 101);
         if (result != key) sCache.put(name, result);
@@ -167,7 +160,7 @@
     *        values.
     */
     public static void recordSparseSlowlyHistogram(String name, int sample) {
-        if (sDisabledBy != null) return;
+        if (sIsDisabledForTests) return;
         long key = getCachedHistogramKey(name);
         long result = nativeRecordSparseHistogram(name, key, sample);
         if (result != key) sCache.put(name, result);
@@ -225,19 +218,6 @@
                 timeUnit.toMillis(min), timeUnit.toMillis(max), numBuckets);
     }
 
-    /**
-     * Records a sample in a histogram of sizes in KB. This is the Java equivalent of the
-     * UMA_HISTOGRAM_MEMORY_KB C++ macro.
-     *
-     * Good for sizes up to about 500MB.
-     *
-     * @param name name of the histogram.
-     * @param sizeInkB Sample to record in KB.
-     */
-    public static void recordMemoryKBHistogram(String name, int sizeInKB) {
-        recordCustomCountHistogram(name, sizeInKB, 1000, 500000, 50);
-    }
-
     private static int clampToInt(long value) {
         if (value > Integer.MAX_VALUE) return Integer.MAX_VALUE;
         // Note: Clamping to MIN_VALUE rather than 0, to let base/ histograms code
@@ -248,7 +228,7 @@
 
     private static void recordCustomTimesHistogramMilliseconds(
             String name, long duration, long min, long max, int numBuckets) {
-        if (sDisabledBy != null) return;
+        if (sIsDisabledForTests) return;
         long key = getCachedHistogramKey(name);
         // Note: Duration, min and max are clamped to int here because that's what's expected by
         // the native histograms API. Callers of these functions still pass longs because that's
@@ -273,7 +253,7 @@
      * Initializes the metrics system.
      */
     public static void initialize() {
-        if (sDisabledBy != null) return;
+        if (sIsDisabledForTests) return;
         nativeInitialize();
     }
 
diff --git a/base/android/java_handler_thread.cc b/base/android/java_handler_thread.cc
index 76ee301..7527034 100644
--- a/base/android/java_handler_thread.cc
+++ b/base/android/java_handler_thread.cc
@@ -20,8 +20,8 @@
 JavaHandlerThread::JavaHandlerThread(const char* name) {
   JNIEnv* env = base::android::AttachCurrentThread();
 
-  java_thread_.Reset(
-      Java_JavaHandlerThread_create(env, ConvertUTF8ToJavaString(env, name)));
+  java_thread_.Reset(Java_JavaHandlerThread_create(
+      env, ConvertUTF8ToJavaString(env, name).obj()));
 }
 
 JavaHandlerThread::~JavaHandlerThread() {
@@ -35,7 +35,8 @@
   base::WaitableEvent initialize_event(
       WaitableEvent::ResetPolicy::AUTOMATIC,
       WaitableEvent::InitialState::NOT_SIGNALED);
-  Java_JavaHandlerThread_start(env, java_thread_,
+  Java_JavaHandlerThread_start(env,
+                               java_thread_.obj(),
                                reinterpret_cast<intptr_t>(this),
                                reinterpret_cast<intptr_t>(&initialize_event));
   // Wait for thread to be initialized so it is ready to be used when Start
@@ -48,7 +49,8 @@
   JNIEnv* env = base::android::AttachCurrentThread();
   base::WaitableEvent shutdown_event(WaitableEvent::ResetPolicy::AUTOMATIC,
                                      WaitableEvent::InitialState::NOT_SIGNALED);
-  Java_JavaHandlerThread_stop(env, java_thread_,
+  Java_JavaHandlerThread_stop(env,
+                              java_thread_.obj(),
                               reinterpret_cast<intptr_t>(this),
                               reinterpret_cast<intptr_t>(&shutdown_event));
   // Wait for thread to shut down before returning.
@@ -61,23 +63,15 @@
                                          jlong event) {
   // TYPE_JAVA to get the Android java style message loop.
   message_loop_.reset(new base::MessageLoop(base::MessageLoop::TYPE_JAVA));
-  StartMessageLoop();
+  static_cast<MessageLoopForUI*>(message_loop_.get())->Start();
   reinterpret_cast<base::WaitableEvent*>(event)->Signal();
 }
 
 void JavaHandlerThread::StopThread(JNIEnv* env,
                                    const JavaParamRef<jobject>& obj,
                                    jlong event) {
-  StopMessageLoop();
-  reinterpret_cast<base::WaitableEvent*>(event)->Signal();
-}
-
-void JavaHandlerThread::StartMessageLoop() {
-  static_cast<MessageLoopForUI*>(message_loop_.get())->Start();
-}
-
-void JavaHandlerThread::StopMessageLoop() {
   static_cast<MessageLoopForUI*>(message_loop_.get())->QuitWhenIdle();
+  reinterpret_cast<base::WaitableEvent*>(event)->Signal();
 }
 
 // static
diff --git a/base/android/java_handler_thread.h b/base/android/java_handler_thread.h
index 96f2f0a..1709ff4 100644
--- a/base/android/java_handler_thread.h
+++ b/base/android/java_handler_thread.h
@@ -14,6 +14,7 @@
 namespace base {
 
 class MessageLoop;
+class WaitableEvent;
 
 namespace android {
 
@@ -40,15 +41,10 @@
                   const JavaParamRef<jobject>& obj,
                   jlong event);
 
-  virtual void StartMessageLoop();
-  virtual void StopMessageLoop();
-
   static bool RegisterBindings(JNIEnv* env);
 
- protected:
-  std::unique_ptr<base::MessageLoop> message_loop_;
-
  private:
+  std::unique_ptr<base::MessageLoop> message_loop_;
   ScopedJavaGlobalRef<jobject> java_thread_;
 };
 
diff --git a/base/android/java_message_handler_factory.h b/base/android/java_message_handler_factory.h
deleted file mode 100644
index 801617d..0000000
--- a/base/android/java_message_handler_factory.h
+++ /dev/null
@@ -1,33 +0,0 @@
-// Copyright 2016 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_ANDROID_JAVA_MESSAGE_HANDLER_FACTORY_H_
-#define BASE_ANDROID_JAVA_MESSAGE_HANDLER_FACTORY_H_
-
-#include "base/android/scoped_java_ref.h"
-#include "base/message_loop/message_pump.h"
-
-namespace base {
-
-class MessagePumpForUI;
-class WaitableEvent;
-
-namespace android {
-
-// Factory for creating the Java-side system message handler - only used for
-// testing.
-class JavaMessageHandlerFactory {
- public:
-  virtual ~JavaMessageHandlerFactory() {}
-  virtual base::android::ScopedJavaLocalRef<jobject> CreateMessageHandler(
-      JNIEnv* env,
-      base::MessagePump::Delegate* delegate,
-      MessagePumpForUI* message_pump,
-      WaitableEvent* test_done_event) = 0;
-};
-
-}  // namespace android
-}  // namespace base
-
-#endif  // BASE_ANDROID_JAVA_MESSAGE_HANDLER_FACTORY_H_
diff --git a/base/android/java_runtime.cc b/base/android/java_runtime.cc
index 5fae49a..5be9adf 100644
--- a/base/android/java_runtime.cc
+++ b/base/android/java_runtime.cc
@@ -9,12 +9,16 @@
 namespace base {
 namespace android {
 
+bool JavaRuntime::Register(JNIEnv* env) {
+  return JNI_Runtime::RegisterNativesImpl(env);
+}
+
 void JavaRuntime::GetMemoryUsage(long* total_memory, long* free_memory) {
   JNIEnv* env = base::android::AttachCurrentThread();
   base::android::ScopedJavaLocalRef<jobject> runtime =
       JNI_Runtime::Java_Runtime_getRuntime(env);
-  *total_memory = JNI_Runtime::Java_Runtime_totalMemory(env, runtime);
-  *free_memory = JNI_Runtime::Java_Runtime_freeMemory(env, runtime);
+  *total_memory = JNI_Runtime::Java_Runtime_totalMemory(env, runtime.obj());
+  *free_memory = JNI_Runtime::Java_Runtime_freeMemory(env, runtime.obj());
 }
 
 }  // namespace android
diff --git a/base/android/java_runtime.h b/base/android/java_runtime.h
index 2034fb9..4ca889e 100644
--- a/base/android/java_runtime.h
+++ b/base/android/java_runtime.h
@@ -14,6 +14,9 @@
 // Wrapper class for using the java.lang.Runtime object from jni.
 class BASE_EXPORT JavaRuntime {
  public:
+  // Registers the jni class (once per process).
+  static bool Register(JNIEnv* env);
+
   // Fills the total memory used and memory allocated for objects by the java
   // heap in the current process. Returns true on success.
   static void GetMemoryUsage(long* total_memory, long* free_memory);
diff --git a/base/android/javatests/src/org/chromium/base/AdvancedMockContextTest.java b/base/android/javatests/src/org/chromium/base/AdvancedMockContextTest.java
index 20c626d..02dbeb1 100644
--- a/base/android/javatests/src/org/chromium/base/AdvancedMockContextTest.java
+++ b/base/android/javatests/src/org/chromium/base/AdvancedMockContextTest.java
@@ -1,4 +1,4 @@
-// Copyright 2017 The Chromium Authors. All rights reserved.
+// Copyright 2014 The Chromium Authors. All rights reserved.
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
@@ -9,21 +9,15 @@
 import android.content.ComponentCallbacks2;
 import android.content.Context;
 import android.content.res.Configuration;
-import android.support.test.InstrumentationRegistry;
-import android.support.test.filters.SmallTest;
+import android.test.InstrumentationTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
 
-import org.junit.Assert;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-
-import org.chromium.base.test.BaseJUnit4ClassRunner;
 import org.chromium.base.test.util.AdvancedMockContext;
 
 /**
  * Tests for {@link org.chromium.base.test.util.AdvancedMockContext}.
  */
-@RunWith(BaseJUnit4ClassRunner.class)
-public class AdvancedMockContextTest {
+public class AdvancedMockContextTest extends InstrumentationTestCase {
     private static class Callback1 implements ComponentCallbacks {
         protected Configuration mConfiguration;
         protected boolean mOnLowMemoryCalled;
@@ -48,10 +42,9 @@
         }
     }
 
-    @Test
     @SmallTest
     public void testComponentCallbacksForTargetContext() {
-        Context targetContext = InstrumentationRegistry.getInstrumentation().getTargetContext();
+        Context targetContext = getInstrumentation().getTargetContext();
         Application targetApplication = (Application) targetContext.getApplicationContext();
         AdvancedMockContext context = new AdvancedMockContext(targetContext);
         Callback1 callback1 = new Callback1();
@@ -60,18 +53,18 @@
         context.registerComponentCallbacks(callback2);
 
         targetApplication.onLowMemory();
-        Assert.assertTrue("onLowMemory should have been called.", callback1.mOnLowMemoryCalled);
-        Assert.assertTrue("onLowMemory should have been called.", callback2.mOnLowMemoryCalled);
+        assertTrue("onLowMemory should have been called.", callback1.mOnLowMemoryCalled);
+        assertTrue("onLowMemory should have been called.", callback2.mOnLowMemoryCalled);
 
         Configuration configuration = new Configuration();
         targetApplication.onConfigurationChanged(configuration);
-        Assert.assertEquals("onConfigurationChanged should have been called.", configuration,
+        assertEquals("onConfigurationChanged should have been called.", configuration,
                 callback1.mConfiguration);
-        Assert.assertEquals("onConfigurationChanged should have been called.", configuration,
+        assertEquals("onConfigurationChanged should have been called.", configuration,
                 callback2.mConfiguration);
 
         targetApplication.onTrimMemory(ComponentCallbacks2.TRIM_MEMORY_MODERATE);
-        Assert.assertEquals("onTrimMemory should have been called.",
-                ComponentCallbacks2.TRIM_MEMORY_MODERATE, callback2.mLevel);
+        assertEquals("onTrimMemory should have been called.", ComponentCallbacks2
+                .TRIM_MEMORY_MODERATE, callback2.mLevel);
     }
 }
diff --git a/base/android/javatests/src/org/chromium/base/ApiCompatibilityUtilsTest.java b/base/android/javatests/src/org/chromium/base/ApiCompatibilityUtilsTest.java
index de0858a..45b3e21 100644
--- a/base/android/javatests/src/org/chromium/base/ApiCompatibilityUtilsTest.java
+++ b/base/android/javatests/src/org/chromium/base/ApiCompatibilityUtilsTest.java
@@ -1,4 +1,4 @@
-// Copyright 2017 The Chromium Authors. All rights reserved.
+// Copyright 2015 The Chromium Authors. All rights reserved.
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
@@ -8,20 +8,13 @@
 import android.app.Activity;
 import android.os.Build;
 import android.os.SystemClock;
-import android.support.test.InstrumentationRegistry;
-import android.support.test.filters.SmallTest;
-
-import org.junit.Assert;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-
-import org.chromium.base.test.BaseJUnit4ClassRunner;
+import android.test.InstrumentationTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
 
 /**
  * Test of ApiCompatibilityUtils
  */
-@RunWith(BaseJUnit4ClassRunner.class)
-public class ApiCompatibilityUtilsTest {
+public class ApiCompatibilityUtilsTest extends InstrumentationTestCase {
     private static final long WAIT_TIMEOUT_IN_MS = 5000;
     private static final long SLEEP_INTERVAL_IN_MS = 50;
 
@@ -49,40 +42,30 @@
         }
     }
 
-    @Test
     @SmallTest
-    public void testFinishAndRemoveTask() {
-        InstrumentationRegistry.getInstrumentation().runOnMainSync(new Runnable() {
-            @Override
-            public void run() {
-                MockActivity activity = new MockActivity();
-                ApiCompatibilityUtils.finishAndRemoveTask(activity);
+    public void testFinishAndRemoveTask() throws InterruptedException {
+        MockActivity activity = new MockActivity();
+        ApiCompatibilityUtils.finishAndRemoveTask(activity);
 
-                if (Build.VERSION.SDK_INT > Build.VERSION_CODES.LOLLIPOP) {
-                    Assert.assertEquals(1, activity.mFinishAndRemoveTaskCallbackCount);
-                    Assert.assertEquals(0, activity.mFinishCallbackCount);
-                } else if (Build.VERSION.SDK_INT == Build.VERSION_CODES.LOLLIPOP) {
-                    long startTime = SystemClock.uptimeMillis();
-                    while (activity.mFinishCallbackCount == 0
-                            && SystemClock.uptimeMillis() - startTime < WAIT_TIMEOUT_IN_MS) {
-                        try {
-                            Thread.sleep(SLEEP_INTERVAL_IN_MS);
-                        } catch (InterruptedException e) {
-                            throw new RuntimeException("Interrupted thread sleep", e);
-                        }
-                    }
-
-                    // MockActivity#finishAndRemoveTask() never sets isFinishing() to true for
-                    // LOLLIPOP to simulate an exceptional case. In that case, MockActivity#finish()
-                    // should be called after 3 tries.
-                    Assert.assertEquals(3, activity.mFinishAndRemoveTaskCallbackCount);
-                    Assert.assertEquals(1, activity.mFinishCallbackCount);
-                } else {
-                    Assert.assertEquals(0, activity.mFinishAndRemoveTaskCallbackCount);
-                    Assert.assertEquals(1, activity.mFinishCallbackCount);
-                }
-                Assert.assertTrue(activity.mIsFinishing);
+        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.LOLLIPOP) {
+            assertEquals(1, activity.mFinishAndRemoveTaskCallbackCount);
+            assertEquals(0, activity.mFinishCallbackCount);
+        } else if (Build.VERSION.SDK_INT == Build.VERSION_CODES.LOLLIPOP) {
+            long startTime = SystemClock.uptimeMillis();
+            while (activity.mFinishCallbackCount == 0
+                    && SystemClock.uptimeMillis() - startTime < WAIT_TIMEOUT_IN_MS) {
+                Thread.sleep(SLEEP_INTERVAL_IN_MS);
             }
-        });
+
+            // MockActivity#finishAndRemoveTask() never sets isFinishing() to true for LOLLIPOP to
+            // simulate an exceptional case. In that case, MockActivity#finish() should be called
+            // after 3 tries.
+            assertEquals(3, activity.mFinishAndRemoveTaskCallbackCount);
+            assertEquals(1, activity.mFinishCallbackCount);
+        } else {
+            assertEquals(0, activity.mFinishAndRemoveTaskCallbackCount);
+            assertEquals(1, activity.mFinishCallbackCount);
+        }
+        assertTrue(activity.mIsFinishing);
     }
 }
diff --git a/base/android/javatests/src/org/chromium/base/CommandLineTest.java b/base/android/javatests/src/org/chromium/base/CommandLineTest.java
index 47749fb..2b1a967 100644
--- a/base/android/javatests/src/org/chromium/base/CommandLineTest.java
+++ b/base/android/javatests/src/org/chromium/base/CommandLineTest.java
@@ -1,21 +1,15 @@
-// Copyright 2017 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
 package org.chromium.base;
 
-import android.support.test.filters.SmallTest;
+import android.test.InstrumentationTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
 
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-
-import org.chromium.base.test.BaseJUnit4ClassRunner;
 import org.chromium.base.test.util.Feature;
 
-@RunWith(BaseJUnit4ClassRunner.class)
-public class CommandLineTest {
+public class CommandLineTest extends InstrumentationTestCase {
     // A reference command line. Note that switch2 is [brea\d], switch3 is [and "butter"],
     // and switch4 is [a "quoted" 'food'!]
     static final String INIT_SWITCHES[] = { "init_command", "--SWITCH", "Arg",
@@ -33,61 +27,60 @@
     static final String CL_ADDED_SWITCH_2 = "username";
     static final String CL_ADDED_VALUE_2 = "bozo";
 
-    @Before
+    @Override
     public void setUp() throws Exception {
         CommandLine.reset();
     }
 
     void checkInitSwitches() {
         CommandLine cl = CommandLine.getInstance();
-        Assert.assertFalse(cl.hasSwitch("init_command"));
-        Assert.assertFalse(cl.hasSwitch("switch"));
-        Assert.assertTrue(cl.hasSwitch("SWITCH"));
-        Assert.assertFalse(cl.hasSwitch("--SWITCH"));
-        Assert.assertFalse(cl.hasSwitch("Arg"));
-        Assert.assertFalse(cl.hasSwitch("actually_an_arg"));
-        Assert.assertEquals("brea\\d", cl.getSwitchValue("switch2"));
-        Assert.assertEquals("and \"butter\"", cl.getSwitchValue("switch3"));
-        Assert.assertEquals("a \"quoted\" 'food'!", cl.getSwitchValue("switch4"));
-        Assert.assertNull(cl.getSwitchValue("SWITCH"));
-        Assert.assertNull(cl.getSwitchValue("non-existant"));
+        assertFalse(cl.hasSwitch("init_command"));
+        assertFalse(cl.hasSwitch("switch"));
+        assertTrue(cl.hasSwitch("SWITCH"));
+        assertFalse(cl.hasSwitch("--SWITCH"));
+        assertFalse(cl.hasSwitch("Arg"));
+        assertFalse(cl.hasSwitch("actually_an_arg"));
+        assertEquals("brea\\d", cl.getSwitchValue("switch2"));
+        assertEquals("and \"butter\"", cl.getSwitchValue("switch3"));
+        assertEquals("a \"quoted\" 'food'!", cl.getSwitchValue("switch4"));
+        assertNull(cl.getSwitchValue("SWITCH"));
+        assertNull(cl.getSwitchValue("non-existant"));
     }
 
     void checkSettingThenGetting() {
         CommandLine cl = CommandLine.getInstance();
 
         // Add a plain switch.
-        Assert.assertFalse(cl.hasSwitch(CL_ADDED_SWITCH));
+        assertFalse(cl.hasSwitch(CL_ADDED_SWITCH));
         cl.appendSwitch(CL_ADDED_SWITCH);
-        Assert.assertTrue(cl.hasSwitch(CL_ADDED_SWITCH));
+        assertTrue(cl.hasSwitch(CL_ADDED_SWITCH));
 
         // Add a switch paired with a value.
-        Assert.assertFalse(cl.hasSwitch(CL_ADDED_SWITCH_2));
-        Assert.assertNull(cl.getSwitchValue(CL_ADDED_SWITCH_2));
+        assertFalse(cl.hasSwitch(CL_ADDED_SWITCH_2));
+        assertNull(cl.getSwitchValue(CL_ADDED_SWITCH_2));
         cl.appendSwitchWithValue(CL_ADDED_SWITCH_2, CL_ADDED_VALUE_2);
-        Assert.assertTrue(CL_ADDED_VALUE_2.equals(cl.getSwitchValue(CL_ADDED_SWITCH_2)));
+        assertTrue(CL_ADDED_VALUE_2.equals(cl.getSwitchValue(CL_ADDED_SWITCH_2)));
 
         // Append a few new things.
         final String switchesAndArgs[] = { "dummy", "--superfast", "--speed=turbo" };
-        Assert.assertFalse(cl.hasSwitch("dummy"));
-        Assert.assertFalse(cl.hasSwitch("superfast"));
-        Assert.assertNull(cl.getSwitchValue("speed"));
+        assertFalse(cl.hasSwitch("dummy"));
+        assertFalse(cl.hasSwitch("superfast"));
+        assertNull(cl.getSwitchValue("speed"));
         cl.appendSwitchesAndArguments(switchesAndArgs);
-        Assert.assertFalse(cl.hasSwitch("dummy"));
-        Assert.assertFalse(cl.hasSwitch("command"));
-        Assert.assertTrue(cl.hasSwitch("superfast"));
-        Assert.assertTrue("turbo".equals(cl.getSwitchValue("speed")));
+        assertFalse(cl.hasSwitch("dummy"));
+        assertFalse(cl.hasSwitch("command"));
+        assertTrue(cl.hasSwitch("superfast"));
+        assertTrue("turbo".equals(cl.getSwitchValue("speed")));
     }
 
     void checkTokenizer(String[] expected, String toParse) {
         String[] actual = CommandLine.tokenizeQuotedAruments(toParse.toCharArray());
-        Assert.assertEquals(expected.length, actual.length);
+        assertEquals(expected.length, actual.length);
         for (int i = 0; i < expected.length; ++i) {
-            Assert.assertEquals("comparing element " + i, expected[i], actual[i]);
+            assertEquals("comparing element " + i, expected[i], actual[i]);
         }
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testJavaInitialization() {
@@ -96,7 +89,6 @@
         checkSettingThenGetting();
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testBufferInitialization() {
@@ -105,7 +97,6 @@
         checkSettingThenGetting();
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testArgumentTokenizer() {
diff --git a/base/android/javatests/src/org/chromium/base/ObserverListTest.java b/base/android/javatests/src/org/chromium/base/ObserverListTest.java
index 1899f45..94a9c71 100644
--- a/base/android/javatests/src/org/chromium/base/ObserverListTest.java
+++ b/base/android/javatests/src/org/chromium/base/ObserverListTest.java
@@ -1,16 +1,12 @@
-// Copyright 2017 The Chromium Authors. All rights reserved.
+// Copyright 2013 The Chromium Authors. All rights reserved.
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
 package org.chromium.base;
 
-import android.support.test.filters.SmallTest;
+import android.test.InstrumentationTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
 
-import org.junit.Assert;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-
-import org.chromium.base.test.BaseJUnit4ClassRunner;
 import org.chromium.base.test.util.Feature;
 
 import java.util.Collection;
@@ -20,8 +16,7 @@
 /**
  * Tests for (@link ObserverList}.
  */
-@RunWith(BaseJUnit4ClassRunner.class)
-public class ObserverListTest {
+public class ObserverListTest extends InstrumentationTestCase {
     interface Observer {
         void observe(int x);
     }
@@ -84,7 +79,6 @@
         return num;
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testRemoveWhileIteration() {
@@ -111,18 +105,17 @@
         for (Observer obs : observerList) obs.observe(10);
 
         // observe should be called twice on a.
-        Assert.assertEquals(20, a.mTotal);
+        assertEquals(20, a.mTotal);
         // observe should be called twice on b.
-        Assert.assertEquals(-20, b.mTotal);
+        assertEquals(-20, b.mTotal);
         // evil removed c from the observerList before it got any callbacks.
-        Assert.assertEquals(0, c.mTotal);
+        assertEquals(0, c.mTotal);
         // observe should be called once on d.
-        Assert.assertEquals(-10, d.mTotal);
+        assertEquals(-10, d.mTotal);
         // e was never added to the list, observe should not be called.
-        Assert.assertEquals(0, e.mTotal);
+        assertEquals(0, e.mTotal);
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testAddWhileIteration() {
@@ -138,13 +131,12 @@
 
         for (Observer obs : observerList) obs.observe(10);
 
-        Assert.assertTrue(observerList.hasObserver(c));
-        Assert.assertEquals(10, a.mTotal);
-        Assert.assertEquals(-10, b.mTotal);
-        Assert.assertEquals(0, c.mTotal);
+        assertTrue(observerList.hasObserver(c));
+        assertEquals(10, a.mTotal);
+        assertEquals(-10, b.mTotal);
+        assertEquals(0, c.mTotal);
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testIterator() {
@@ -152,39 +144,38 @@
         observerList.addObserver(5);
         observerList.addObserver(10);
         observerList.addObserver(15);
-        Assert.assertEquals(3, getSizeOfIterable(observerList));
+        assertEquals(3, getSizeOfIterable(observerList));
 
         observerList.removeObserver(10);
-        Assert.assertEquals(2, getSizeOfIterable(observerList));
+        assertEquals(2, getSizeOfIterable(observerList));
 
         Iterator<Integer> it = observerList.iterator();
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(5 == it.next());
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(15 == it.next());
-        Assert.assertFalse(it.hasNext());
+        assertTrue(it.hasNext());
+        assertTrue(5 == it.next());
+        assertTrue(it.hasNext());
+        assertTrue(15 == it.next());
+        assertFalse(it.hasNext());
 
         boolean removeExceptionThrown = false;
         try {
             it.remove();
-            Assert.fail("Expecting UnsupportedOperationException to be thrown here.");
+            fail("Expecting UnsupportedOperationException to be thrown here.");
         } catch (UnsupportedOperationException e) {
             removeExceptionThrown = true;
         }
-        Assert.assertTrue(removeExceptionThrown);
-        Assert.assertEquals(2, getSizeOfIterable(observerList));
+        assertTrue(removeExceptionThrown);
+        assertEquals(2, getSizeOfIterable(observerList));
 
         boolean noElementExceptionThrown = false;
         try {
             it.next();
-            Assert.fail("Expecting NoSuchElementException to be thrown here.");
+            fail("Expecting NoSuchElementException to be thrown here.");
         } catch (NoSuchElementException e) {
             noElementExceptionThrown = true;
         }
-        Assert.assertTrue(noElementExceptionThrown);
+        assertTrue(noElementExceptionThrown);
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testRewindableIterator() {
@@ -192,54 +183,52 @@
         observerList.addObserver(5);
         observerList.addObserver(10);
         observerList.addObserver(15);
-        Assert.assertEquals(3, getSizeOfIterable(observerList));
+        assertEquals(3, getSizeOfIterable(observerList));
 
         ObserverList.RewindableIterator<Integer> it = observerList.rewindableIterator();
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(5 == it.next());
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(10 == it.next());
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(15 == it.next());
-        Assert.assertFalse(it.hasNext());
+        assertTrue(it.hasNext());
+        assertTrue(5 == it.next());
+        assertTrue(it.hasNext());
+        assertTrue(10 == it.next());
+        assertTrue(it.hasNext());
+        assertTrue(15 == it.next());
+        assertFalse(it.hasNext());
 
         it.rewind();
 
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(5 == it.next());
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(10 == it.next());
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(15 == it.next());
-        Assert.assertEquals(5, (int) observerList.mObservers.get(0));
+        assertTrue(it.hasNext());
+        assertTrue(5 == it.next());
+        assertTrue(it.hasNext());
+        assertTrue(10 == it.next());
+        assertTrue(it.hasNext());
+        assertTrue(15 == it.next());
+        assertEquals(5, (int) observerList.mObservers.get(0));
         observerList.removeObserver(5);
-        Assert.assertEquals(null, observerList.mObservers.get(0));
+        assertEquals(null, observerList.mObservers.get(0));
 
         it.rewind();
 
-        Assert.assertEquals(10, (int) observerList.mObservers.get(0));
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(10 == it.next());
-        Assert.assertTrue(it.hasNext());
-        Assert.assertTrue(15 == it.next());
+        assertEquals(10, (int) observerList.mObservers.get(0));
+        assertTrue(it.hasNext());
+        assertTrue(10 == it.next());
+        assertTrue(it.hasNext());
+        assertTrue(15 == it.next());
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testAddObserverReturnValue() {
         ObserverList<Object> observerList = new ObserverList<Object>();
 
         Object a = new Object();
-        Assert.assertTrue(observerList.addObserver(a));
-        Assert.assertFalse(observerList.addObserver(a));
+        assertTrue(observerList.addObserver(a));
+        assertFalse(observerList.addObserver(a));
 
         Object b = new Object();
-        Assert.assertTrue(observerList.addObserver(b));
-        Assert.assertFalse(observerList.addObserver(null));
+        assertTrue(observerList.addObserver(b));
+        assertFalse(observerList.addObserver(null));
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testRemoveObserverReturnValue() {
@@ -250,92 +239,91 @@
         observerList.addObserver(a);
         observerList.addObserver(b);
 
-        Assert.assertTrue(observerList.removeObserver(a));
-        Assert.assertFalse(observerList.removeObserver(a));
-        Assert.assertFalse(observerList.removeObserver(new Object()));
-        Assert.assertTrue(observerList.removeObserver(b));
-        Assert.assertFalse(observerList.removeObserver(null));
+        assertTrue(observerList.removeObserver(a));
+        assertFalse(observerList.removeObserver(a));
+        assertFalse(observerList.removeObserver(new Object()));
+        assertTrue(observerList.removeObserver(b));
+        assertFalse(observerList.removeObserver(null));
 
         // If we remove an object while iterating, it will be replaced by 'null'.
         observerList.addObserver(a);
-        Assert.assertTrue(observerList.removeObserver(a));
-        Assert.assertFalse(observerList.removeObserver(null));
+        assertTrue(observerList.removeObserver(a));
+        assertFalse(observerList.removeObserver(null));
     }
 
-    @Test
     @SmallTest
     @Feature({"Android-AppBase"})
     public void testSize() {
         ObserverList<Object> observerList = new ObserverList<Object>();
 
-        Assert.assertEquals(0, observerList.size());
-        Assert.assertTrue(observerList.isEmpty());
+        assertEquals(0, observerList.size());
+        assertTrue(observerList.isEmpty());
 
         observerList.addObserver(null);
-        Assert.assertEquals(0, observerList.size());
-        Assert.assertTrue(observerList.isEmpty());
+        assertEquals(0, observerList.size());
+        assertTrue(observerList.isEmpty());
 
         Object a = new Object();
         observerList.addObserver(a);
-        Assert.assertEquals(1, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(1, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         observerList.addObserver(a);
-        Assert.assertEquals(1, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(1, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         observerList.addObserver(null);
-        Assert.assertEquals(1, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(1, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         Object b = new Object();
         observerList.addObserver(b);
-        Assert.assertEquals(2, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(2, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         observerList.removeObserver(null);
-        Assert.assertEquals(2, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(2, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         observerList.removeObserver(new Object());
-        Assert.assertEquals(2, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(2, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         observerList.removeObserver(b);
-        Assert.assertEquals(1, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(1, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         observerList.removeObserver(b);
-        Assert.assertEquals(1, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(1, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         observerList.removeObserver(a);
-        Assert.assertEquals(0, observerList.size());
-        Assert.assertTrue(observerList.isEmpty());
+        assertEquals(0, observerList.size());
+        assertTrue(observerList.isEmpty());
 
         observerList.removeObserver(a);
         observerList.removeObserver(b);
         observerList.removeObserver(null);
         observerList.removeObserver(new Object());
-        Assert.assertEquals(0, observerList.size());
-        Assert.assertTrue(observerList.isEmpty());
+        assertEquals(0, observerList.size());
+        assertTrue(observerList.isEmpty());
 
         observerList.addObserver(new Object());
         observerList.addObserver(new Object());
         observerList.addObserver(new Object());
         observerList.addObserver(a);
-        Assert.assertEquals(4, observerList.size());
-        Assert.assertFalse(observerList.isEmpty());
+        assertEquals(4, observerList.size());
+        assertFalse(observerList.isEmpty());
 
         observerList.clear();
-        Assert.assertEquals(0, observerList.size());
-        Assert.assertTrue(observerList.isEmpty());
+        assertEquals(0, observerList.size());
+        assertTrue(observerList.isEmpty());
 
         observerList.removeObserver(a);
         observerList.removeObserver(b);
         observerList.removeObserver(null);
         observerList.removeObserver(new Object());
-        Assert.assertEquals(0, observerList.size());
-        Assert.assertTrue(observerList.isEmpty());
+        assertEquals(0, observerList.size());
+        assertTrue(observerList.isEmpty());
     }
 }
diff --git a/base/android/javatests/src/org/chromium/base/metrics/RecordHistogramTest.java b/base/android/javatests/src/org/chromium/base/metrics/RecordHistogramTest.java
index daf639b..6b1888c 100644
--- a/base/android/javatests/src/org/chromium/base/metrics/RecordHistogramTest.java
+++ b/base/android/javatests/src/org/chromium/base/metrics/RecordHistogramTest.java
@@ -1,19 +1,14 @@
-// Copyright 2017 The Chromium Authors. All rights reserved.
+// Copyright 2014 The Chromium Authors. All rights reserved.
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
 package org.chromium.base.metrics;
 
-import android.support.test.filters.SmallTest;
-
-import org.junit.Assert;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
+import android.test.InstrumentationTestCase;
+import android.test.suitebuilder.annotation.SmallTest;
 
 import org.chromium.base.library_loader.LibraryLoader;
 import org.chromium.base.library_loader.LibraryProcessType;
-import org.chromium.base.test.BaseJUnit4ClassRunner;
 import org.chromium.base.test.util.MetricsUtils.HistogramDelta;
 
 import java.util.concurrent.TimeUnit;
@@ -21,43 +16,42 @@
 /**
  * Tests for the Java API for recording UMA histograms.
  */
-@RunWith(BaseJUnit4ClassRunner.class)
-public class RecordHistogramTest {
-    @Before
-    public void setUp() throws Exception {
-        LibraryLoader.get(LibraryProcessType.PROCESS_BROWSER).ensureInitialized();
+public class RecordHistogramTest extends InstrumentationTestCase {
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+        LibraryLoader.get(LibraryProcessType.PROCESS_BROWSER)
+                .ensureInitialized(getInstrumentation().getTargetContext());
         RecordHistogram.initialize();
     }
 
     /**
      * Tests recording of boolean histograms.
      */
-    @Test
     @SmallTest
     public void testRecordBooleanHistogram() {
         String histogram = "HelloWorld.BooleanMetric";
         HistogramDelta falseCount = new HistogramDelta(histogram, 0);
         HistogramDelta trueCount = new HistogramDelta(histogram, 1);
-        Assert.assertEquals(0, trueCount.getDelta());
-        Assert.assertEquals(0, falseCount.getDelta());
+        assertEquals(0, trueCount.getDelta());
+        assertEquals(0, falseCount.getDelta());
 
         RecordHistogram.recordBooleanHistogram(histogram, true);
-        Assert.assertEquals(1, trueCount.getDelta());
-        Assert.assertEquals(0, falseCount.getDelta());
+        assertEquals(1, trueCount.getDelta());
+        assertEquals(0, falseCount.getDelta());
 
         RecordHistogram.recordBooleanHistogram(histogram, true);
-        Assert.assertEquals(2, trueCount.getDelta());
-        Assert.assertEquals(0, falseCount.getDelta());
+        assertEquals(2, trueCount.getDelta());
+        assertEquals(0, falseCount.getDelta());
 
         RecordHistogram.recordBooleanHistogram(histogram, false);
-        Assert.assertEquals(2, trueCount.getDelta());
-        Assert.assertEquals(1, falseCount.getDelta());
+        assertEquals(2, trueCount.getDelta());
+        assertEquals(1, falseCount.getDelta());
     }
 
     /**
      * Tests recording of enumerated histograms.
      */
-    @Test
     @SmallTest
     public void testRecordEnumeratedHistogram() {
         String histogram = "HelloWorld.EnumeratedMetric";
@@ -66,30 +60,29 @@
         HistogramDelta twoCount = new HistogramDelta(histogram, 2);
         final int boundary = 3;
 
-        Assert.assertEquals(0, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(0, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordEnumeratedHistogram(histogram, 0, boundary);
-        Assert.assertEquals(1, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(1, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordEnumeratedHistogram(histogram, 0, boundary);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordEnumeratedHistogram(histogram, 2, boundary);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(1, twoCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(1, twoCount.getDelta());
     }
 
     /**
      * Tests recording of count histograms.
      */
-    @Test
     @SmallTest
     public void testRecordCountHistogram() {
         String histogram = "HelloWorld.CountMetric";
@@ -98,40 +91,39 @@
         HistogramDelta twoCount = new HistogramDelta(histogram, 2);
         HistogramDelta eightThousandCount = new HistogramDelta(histogram, 8000);
 
-        Assert.assertEquals(0, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
-        Assert.assertEquals(0, eightThousandCount.getDelta());
+        assertEquals(0, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
+        assertEquals(0, eightThousandCount.getDelta());
 
         RecordHistogram.recordCountHistogram(histogram, 0);
-        Assert.assertEquals(1, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
-        Assert.assertEquals(0, eightThousandCount.getDelta());
+        assertEquals(1, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
+        assertEquals(0, eightThousandCount.getDelta());
 
         RecordHistogram.recordCountHistogram(histogram, 0);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
-        Assert.assertEquals(0, eightThousandCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
+        assertEquals(0, eightThousandCount.getDelta());
 
         RecordHistogram.recordCountHistogram(histogram, 2);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(1, twoCount.getDelta());
-        Assert.assertEquals(0, eightThousandCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(1, twoCount.getDelta());
+        assertEquals(0, eightThousandCount.getDelta());
 
         RecordHistogram.recordCountHistogram(histogram, 8000);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(1, twoCount.getDelta());
-        Assert.assertEquals(1, eightThousandCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(1, twoCount.getDelta());
+        assertEquals(1, eightThousandCount.getDelta());
     }
 
     /**
      * Tests recording of custom times histograms.
      */
-    @Test
     @SmallTest
     public void testRecordCustomTimesHistogram() {
         String histogram = "HelloWorld.CustomTimesMetric";
@@ -139,37 +131,36 @@
         HistogramDelta oneCount = new HistogramDelta(histogram, 1);
         HistogramDelta twoCount = new HistogramDelta(histogram, 100);
 
-        Assert.assertEquals(0, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(0, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         TimeUnit milli = TimeUnit.MILLISECONDS;
 
         RecordHistogram.recordCustomTimesHistogram(histogram, 0, 1, 100, milli, 3);
-        Assert.assertEquals(1, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(1, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordCustomTimesHistogram(histogram, 0, 1, 100, milli, 3);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordCustomTimesHistogram(histogram, 95, 1, 100, milli, 3);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(1, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(1, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordCustomTimesHistogram(histogram, 200, 1, 100, milli, 3);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(1, oneCount.getDelta());
-        Assert.assertEquals(1, twoCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(1, oneCount.getDelta());
+        assertEquals(1, twoCount.getDelta());
     }
 
     /**
      * Tests recording of linear count histograms.
      */
-    @Test
     @SmallTest
     public void testRecordLinearCountHistogram() {
         String histogram = "HelloWorld.LinearCountMetric";
@@ -180,23 +171,23 @@
         final int max = 3;
         final int numBuckets = 4;
 
-        Assert.assertEquals(0, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(0, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordLinearCountHistogram(histogram, 0, min, max, numBuckets);
-        Assert.assertEquals(1, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(1, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordLinearCountHistogram(histogram, 0, min, max, numBuckets);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(0, twoCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(0, twoCount.getDelta());
 
         RecordHistogram.recordLinearCountHistogram(histogram, 2, min, max, numBuckets);
-        Assert.assertEquals(2, zeroCount.getDelta());
-        Assert.assertEquals(0, oneCount.getDelta());
-        Assert.assertEquals(1, twoCount.getDelta());
+        assertEquals(2, zeroCount.getDelta());
+        assertEquals(0, oneCount.getDelta());
+        assertEquals(1, twoCount.getDelta());
     }
 }
diff --git a/base/android/jni_android.cc b/base/android/jni_android.cc
index 56dc5c2..3b53624 100644
--- a/base/android/jni_android.cc
+++ b/base/android/jni_android.cc
@@ -11,40 +11,33 @@
 #include "base/android/build_info.h"
 #include "base/android/jni_string.h"
 #include "base/android/jni_utils.h"
-#include "base/debug/debugging_flags.h"
 #include "base/lazy_instance.h"
 #include "base/logging.h"
-#include "base/threading/thread_local.h"
 
 namespace {
 using base::android::GetClass;
 using base::android::MethodID;
 using base::android::ScopedJavaLocalRef;
 
-base::android::JniRegistrationType g_jni_registration_type =
-    base::android::ALL_JNI_REGISTRATION;
+bool g_disable_manual_jni_registration = false;
 
 JavaVM* g_jvm = NULL;
-base::LazyInstance<base::android::ScopedJavaGlobalRef<jobject>>::Leaky
+base::LazyInstance<base::android::ScopedJavaGlobalRef<jobject> >::Leaky
     g_class_loader = LAZY_INSTANCE_INITIALIZER;
 jmethodID g_class_loader_load_class_method_id = 0;
 
-#if BUILDFLAG(ENABLE_PROFILING) && HAVE_TRACE_STACK_FRAME_POINTERS
-base::LazyInstance<base::ThreadLocalPointer<void>>::Leaky
-    g_stack_frame_pointer = LAZY_INSTANCE_INITIALIZER;
-#endif
-
 }  // namespace
 
 namespace base {
 namespace android {
 
-JniRegistrationType GetJniRegistrationType() {
-  return g_jni_registration_type;
+bool IsManualJniRegistrationDisabled() {
+  return g_disable_manual_jni_registration;
 }
 
-void SetJniRegistrationType(JniRegistrationType jni_registration_type) {
-  g_jni_registration_type = jni_registration_type;
+void DisableManualJniRegistration() {
+  DCHECK(!g_disable_manual_jni_registration);
+  g_disable_manual_jni_registration = true;
 }
 
 JNIEnv* AttachCurrentThread() {
@@ -240,7 +233,16 @@
   }
 
   // Now, feel good about it and die.
-  LOG(FATAL) << "Please include Java exception stack in crash report";
+  // TODO(lhchavez): Remove this hack. See b/28814913 for details.
+  // We're using BuildInfo's java_exception_info() instead of storing the
+  // exception info a few lines above to avoid extra copies. It will be
+  // truncated to 1024 bytes anyways.
+  const char* exception_string =
+      base::android::BuildInfo::GetInstance()->java_exception_info();
+  if (exception_string)
+    LOG(FATAL) << exception_string;
+  else
+    LOG(FATAL) << "Unhandled exception";
 }
 
 std::string GetJavaExceptionInfo(JNIEnv* env, jthrowable java_throwable) {
@@ -289,22 +291,6 @@
   return ConvertJavaStringToUTF8(exception_string);
 }
 
-#if BUILDFLAG(ENABLE_PROFILING) && HAVE_TRACE_STACK_FRAME_POINTERS
-
-JNIStackFrameSaver::JNIStackFrameSaver(void* current_fp) {
-  previous_fp_ = g_stack_frame_pointer.Pointer()->Get();
-  g_stack_frame_pointer.Pointer()->Set(current_fp);
-}
-
-JNIStackFrameSaver::~JNIStackFrameSaver() {
-  g_stack_frame_pointer.Pointer()->Set(previous_fp_);
-}
-
-void* JNIStackFrameSaver::SavedFrame() {
-  return g_stack_frame_pointer.Pointer()->Get();
-}
-
-#endif  // ENABLE_PROFILING && HAVE_TRACE_STACK_FRAME_POINTERS
 
 }  // namespace android
 }  // namespace base
diff --git a/base/android/jni_android.h b/base/android/jni_android.h
index de53c10..909e3da 100644
--- a/base/android/jni_android.h
+++ b/base/android/jni_android.h
@@ -14,39 +14,6 @@
 #include "base/atomicops.h"
 #include "base/base_export.h"
 #include "base/compiler_specific.h"
-#include "base/debug/stack_trace.h"
-#include "base/macros.h"
-
-#if HAVE_TRACE_STACK_FRAME_POINTERS
-
-// When profiling is enabled (enable_profiling=true) this macro is added to
-// all generated JNI stubs so that it becomes the last thing that runs before
-// control goes into Java.
-//
-// This macro saves stack frame pointer of the current function. Saved value
-// used later by JNI_LINK_SAVED_FRAME_POINTER.
-#define JNI_SAVE_FRAME_POINTER \
-  base::android::JNIStackFrameSaver jni_frame_saver(__builtin_frame_address(0))
-
-// When profiling is enabled (enable_profiling=true) this macro is added to
-// all generated JNI callbacks so that it becomes the first thing that runs
-// after control returns from Java.
-//
-// This macro links stack frame of the current function to the stack frame
-// saved by JNI_SAVE_FRAME_POINTER, allowing frame-based unwinding
-// (used by the heap profiler) to produce complete traces.
-#define JNI_LINK_SAVED_FRAME_POINTER                    \
-  base::debug::ScopedStackFrameLinker jni_frame_linker( \
-      __builtin_frame_address(0),                       \
-      base::android::JNIStackFrameSaver::SavedFrame())
-
-#else
-
-// Frame-based stack unwinding is not supported, do nothing.
-#define JNI_SAVE_FRAME_POINTER
-#define JNI_LINK_SAVED_FRAME_POINTER
-
-#endif  // HAVE_TRACE_STACK_FRAME_POINTERS
 
 namespace base {
 namespace android {
@@ -54,23 +21,12 @@
 // Used to mark symbols to be exported in a shared library's symbol table.
 #define JNI_EXPORT __attribute__ ((visibility("default")))
 
-// The level of JNI registration required for the current process.
-enum JniRegistrationType {
-  // Register all native methods.
-  ALL_JNI_REGISTRATION,
-  // Register some native methods, as controlled by the jni_generator.
-  SELECTIVE_JNI_REGISTRATION,
-  // Do not register any native methods.
-  NO_JNI_REGISTRATION,
-};
-
-BASE_EXPORT JniRegistrationType GetJniRegistrationType();
-
-// Set the JniRegistrationType for this process (defaults to
-// ALL_JNI_REGISTRATION). This should be called in the JNI_OnLoad function
-// which is called when the native library is first loaded.
-BASE_EXPORT void SetJniRegistrationType(
-    JniRegistrationType jni_registration_type);
+// Used to disable manual JNI registration in binaries that prefer to use native
+// JNI exports for startup performance. This is not compatible with the crazy
+// linker and so defaults to off. Call DisableManualJniRegistration at the very
+// beginning of JNI_OnLoad to use this.
+BASE_EXPORT bool IsManualJniRegistrationDisabled();
+BASE_EXPORT void DisableManualJniRegistration();
 
 // Contains the registration method information for initializing JNI bindings.
 struct RegistrationMethod {
@@ -166,24 +122,6 @@
 BASE_EXPORT std::string GetJavaExceptionInfo(JNIEnv* env,
                                              jthrowable java_throwable);
 
-#if HAVE_TRACE_STACK_FRAME_POINTERS
-
-// Saves caller's PC and stack frame in a thread-local variable.
-// Implemented only when profiling is enabled (enable_profiling=true).
-class BASE_EXPORT JNIStackFrameSaver {
- public:
-  JNIStackFrameSaver(void* current_fp);
-  ~JNIStackFrameSaver();
-  static void* SavedFrame();
-
- private:
-  void* previous_fp_;
-
-  DISALLOW_COPY_AND_ASSIGN(JNIStackFrameSaver);
-};
-
-#endif  // HAVE_TRACE_STACK_FRAME_POINTERS
-
 }  // namespace android
 }  // namespace base
 
diff --git a/base/android/jni_generator/golden_sample_for_tests_jni.h b/base/android/jni_generator/golden_sample_for_tests_jni.h
new file mode 100644
index 0000000..e982609
--- /dev/null
+++ b/base/android/jni_generator/golden_sample_for_tests_jni.h
@@ -0,0 +1,481 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This file is autogenerated by
+//     base/android/jni_generator/jni_generator.py
+// For
+//     org/chromium/example/jni_generator/SampleForTests
+
+#ifndef org_chromium_example_jni_generator_SampleForTests_JNI
+#define org_chromium_example_jni_generator_SampleForTests_JNI
+
+#include <jni.h>
+
+#include "base/android/jni_generator/jni_generator_helper.h"
+
+#include "base/android/jni_int_wrapper.h"
+
+// Step 1: forward declarations.
+namespace {
+const char kInnerStructAClassPath[] =
+    "org/chromium/example/jni_generator/SampleForTests$InnerStructA";
+const char kSampleForTestsClassPath[] =
+    "org/chromium/example/jni_generator/SampleForTests";
+const char kInnerStructBClassPath[] =
+    "org/chromium/example/jni_generator/SampleForTests$InnerStructB";
+// Leaking this jclass as we cannot use LazyInstance from some threads.
+jclass g_InnerStructA_clazz = NULL;
+#define InnerStructA_clazz(env) g_InnerStructA_clazz
+// Leaking this jclass as we cannot use LazyInstance from some threads.
+jclass g_SampleForTests_clazz = NULL;
+#define SampleForTests_clazz(env) g_SampleForTests_clazz
+// Leaking this jclass as we cannot use LazyInstance from some threads.
+jclass g_InnerStructB_clazz = NULL;
+#define InnerStructB_clazz(env) g_InnerStructB_clazz
+
+}  // namespace
+
+namespace base {
+namespace android {
+
+// Step 2: method stubs.
+
+static jlong Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller,
+    const JavaParamRef<jstring>& param);
+
+static jlong
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeInit(JNIEnv*
+    env, jobject jcaller,
+    jstring param) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller),
+      JavaParamRef<jstring>(env, param));
+}
+
+static void
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeDestroy(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeCPPClass) {
+  CPPClass* native = reinterpret_cast<CPPClass*>(nativeCPPClass);
+  CHECK_NATIVE_PTR(env, jcaller, native, "Destroy");
+  return native->Destroy(env, JavaParamRef<jobject>(env, jcaller));
+}
+
+static jdouble GetDoubleFunction(JNIEnv* env, const JavaParamRef<jobject>&
+    jcaller);
+
+static jdouble
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeGetDoubleFunction(JNIEnv*
+    env, jobject jcaller) {
+  return GetDoubleFunction(env, JavaParamRef<jobject>(env, jcaller));
+}
+
+static jfloat GetFloatFunction(JNIEnv* env, const JavaParamRef<jclass>&
+    jcaller);
+
+static jfloat
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeGetFloatFunction(JNIEnv*
+    env, jclass jcaller) {
+  return GetFloatFunction(env, JavaParamRef<jclass>(env, jcaller));
+}
+
+static void SetNonPODDatatype(JNIEnv* env, const JavaParamRef<jobject>& jcaller,
+    const JavaParamRef<jobject>& rect);
+
+static void
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeSetNonPODDatatype(JNIEnv*
+    env, jobject jcaller,
+    jobject rect) {
+  return SetNonPODDatatype(env, JavaParamRef<jobject>(env, jcaller),
+      JavaParamRef<jobject>(env, rect));
+}
+
+static ScopedJavaLocalRef<jobject> GetNonPODDatatype(JNIEnv* env, const
+    JavaParamRef<jobject>& jcaller);
+
+static jobject
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeGetNonPODDatatype(JNIEnv*
+    env, jobject jcaller) {
+  return GetNonPODDatatype(env, JavaParamRef<jobject>(env, jcaller)).Release();
+}
+
+static jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeMethod(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeCPPClass) {
+  CPPClass* native = reinterpret_cast<CPPClass*>(nativeCPPClass);
+  CHECK_NATIVE_PTR(env, jcaller, native, "Method", 0);
+  return native->Method(env, JavaParamRef<jobject>(env, jcaller));
+}
+
+static jdouble
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeMethodOtherP0(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativePtr) {
+  CPPClass::InnerClass* native =
+      reinterpret_cast<CPPClass::InnerClass*>(nativePtr);
+  CHECK_NATIVE_PTR(env, jcaller, native, "MethodOtherP0", 0);
+  return native->MethodOtherP0(env, JavaParamRef<jobject>(env, jcaller));
+}
+
+static void
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeAddStructB(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeCPPClass,
+    jobject b) {
+  CPPClass* native = reinterpret_cast<CPPClass*>(nativeCPPClass);
+  CHECK_NATIVE_PTR(env, jcaller, native, "AddStructB");
+  return native->AddStructB(env, JavaParamRef<jobject>(env, jcaller),
+      JavaParamRef<jobject>(env, b));
+}
+
+static void
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeIterateAndDoSomethingWithStructB(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeCPPClass) {
+  CPPClass* native = reinterpret_cast<CPPClass*>(nativeCPPClass);
+  CHECK_NATIVE_PTR(env, jcaller, native, "IterateAndDoSomethingWithStructB");
+  return native->IterateAndDoSomethingWithStructB(env,
+      JavaParamRef<jobject>(env, jcaller));
+}
+
+static jstring
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeReturnAString(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeCPPClass) {
+  CPPClass* native = reinterpret_cast<CPPClass*>(nativeCPPClass);
+  CHECK_NATIVE_PTR(env, jcaller, native, "ReturnAString", NULL);
+  return native->ReturnAString(env, JavaParamRef<jobject>(env,
+      jcaller)).Release();
+}
+
+static base::subtle::AtomicWord g_SampleForTests_javaMethod = 0;
+static jint Java_SampleForTests_javaMethod(JNIEnv* env, jobject obj,
+    JniIntWrapper foo,
+    JniIntWrapper bar) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env), 0);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "javaMethod",
+
+"("
+"I"
+"I"
+")"
+"I",
+      &g_SampleForTests_javaMethod);
+
+  jint ret =
+      env->CallIntMethod(obj,
+          method_id, as_jint(foo), as_jint(bar));
+  jni_generator::CheckException(env);
+  return ret;
+}
+
+static base::subtle::AtomicWord g_SampleForTests_staticJavaMethod = 0;
+static jboolean Java_SampleForTests_staticJavaMethod(JNIEnv* env) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, SampleForTests_clazz(env),
+      SampleForTests_clazz(env), false);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_STATIC>(
+      env, SampleForTests_clazz(env),
+      "staticJavaMethod",
+
+"("
+")"
+"Z",
+      &g_SampleForTests_staticJavaMethod);
+
+  jboolean ret =
+      env->CallStaticBooleanMethod(SampleForTests_clazz(env),
+          method_id);
+  jni_generator::CheckException(env);
+  return ret;
+}
+
+static base::subtle::AtomicWord g_SampleForTests_packagePrivateJavaMethod = 0;
+static void Java_SampleForTests_packagePrivateJavaMethod(JNIEnv* env, jobject
+    obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env));
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "packagePrivateJavaMethod",
+
+"("
+")"
+"V",
+      &g_SampleForTests_packagePrivateJavaMethod);
+
+     env->CallVoidMethod(obj,
+          method_id);
+  jni_generator::CheckException(env);
+
+}
+
+static base::subtle::AtomicWord g_SampleForTests_methodThatThrowsException = 0;
+static void Java_SampleForTests_methodThatThrowsException(JNIEnv* env, jobject
+    obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env));
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "methodThatThrowsException",
+
+"("
+")"
+"V",
+      &g_SampleForTests_methodThatThrowsException);
+
+     env->CallVoidMethod(obj,
+          method_id);
+
+}
+
+static base::subtle::AtomicWord g_InnerStructA_create = 0;
+static ScopedJavaLocalRef<jobject> Java_InnerStructA_create(JNIEnv* env, jlong
+    l,
+    JniIntWrapper i,
+    jstring s) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, InnerStructA_clazz(env),
+      InnerStructA_clazz(env), NULL);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_STATIC>(
+      env, InnerStructA_clazz(env),
+      "create",
+
+"("
+"J"
+"I"
+"Ljava/lang/String;"
+")"
+"Lorg/chromium/example/jni_generator/SampleForTests$InnerStructA;",
+      &g_InnerStructA_create);
+
+  jobject ret =
+      env->CallStaticObjectMethod(InnerStructA_clazz(env),
+          method_id, l, as_jint(i), s);
+  jni_generator::CheckException(env);
+  return ScopedJavaLocalRef<jobject>(env, ret);
+}
+
+static base::subtle::AtomicWord g_SampleForTests_addStructA = 0;
+static void Java_SampleForTests_addStructA(JNIEnv* env, jobject obj, jobject a)
+    {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env));
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "addStructA",
+
+"("
+"Lorg/chromium/example/jni_generator/SampleForTests$InnerStructA;"
+")"
+"V",
+      &g_SampleForTests_addStructA);
+
+     env->CallVoidMethod(obj,
+          method_id, a);
+  jni_generator::CheckException(env);
+
+}
+
+static base::subtle::AtomicWord g_SampleForTests_iterateAndDoSomething = 0;
+static void Java_SampleForTests_iterateAndDoSomething(JNIEnv* env, jobject obj)
+    {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env));
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "iterateAndDoSomething",
+
+"("
+")"
+"V",
+      &g_SampleForTests_iterateAndDoSomething);
+
+     env->CallVoidMethod(obj,
+          method_id);
+  jni_generator::CheckException(env);
+
+}
+
+static base::subtle::AtomicWord g_InnerStructB_getKey = 0;
+static jlong Java_InnerStructB_getKey(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      InnerStructB_clazz(env), 0);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, InnerStructB_clazz(env),
+      "getKey",
+
+"("
+")"
+"J",
+      &g_InnerStructB_getKey);
+
+  jlong ret =
+      env->CallLongMethod(obj,
+          method_id);
+  jni_generator::CheckException(env);
+  return ret;
+}
+
+static base::subtle::AtomicWord g_InnerStructB_getValue = 0;
+static ScopedJavaLocalRef<jstring> Java_InnerStructB_getValue(JNIEnv* env,
+    jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      InnerStructB_clazz(env), NULL);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, InnerStructB_clazz(env),
+      "getValue",
+
+"("
+")"
+"Ljava/lang/String;",
+      &g_InnerStructB_getValue);
+
+  jstring ret =
+      static_cast<jstring>(env->CallObjectMethod(obj,
+          method_id));
+  jni_generator::CheckException(env);
+  return ScopedJavaLocalRef<jstring>(env, ret);
+}
+
+// Step 3: RegisterNatives.
+
+static const JNINativeMethod kMethodsSampleForTests[] = {
+    { "nativeInit",
+"("
+"Ljava/lang/String;"
+")"
+"J",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeInit)
+    },
+    { "nativeDestroy",
+"("
+"J"
+")"
+"V",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeDestroy)
+    },
+    { "nativeGetDoubleFunction",
+"("
+")"
+"D",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeGetDoubleFunction)
+    },
+    { "nativeGetFloatFunction",
+"("
+")"
+"F",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeGetFloatFunction)
+    },
+    { "nativeSetNonPODDatatype",
+"("
+"Landroid/graphics/Rect;"
+")"
+"V",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeSetNonPODDatatype)
+    },
+    { "nativeGetNonPODDatatype",
+"("
+")"
+"Ljava/lang/Object;",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeGetNonPODDatatype)
+    },
+    { "nativeMethod",
+"("
+"J"
+")"
+"I",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeMethod)
+    },
+    { "nativeMethodOtherP0",
+"("
+"J"
+")"
+"D",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeMethodOtherP0)
+    },
+    { "nativeAddStructB",
+"("
+"J"
+"Lorg/chromium/example/jni_generator/SampleForTests$InnerStructB;"
+")"
+"V",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeAddStructB)
+    },
+    { "nativeIterateAndDoSomethingWithStructB",
+"("
+"J"
+")"
+"V",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeIterateAndDoSomethingWithStructB)
+    },
+    { "nativeReturnAString",
+"("
+"J"
+")"
+"Ljava/lang/String;",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeReturnAString)
+    },
+};
+
+static bool RegisterNativesImpl(JNIEnv* env) {
+
+  g_InnerStructA_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kInnerStructAClassPath).obj()));
+  g_SampleForTests_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kSampleForTestsClassPath).obj()));
+  g_InnerStructB_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kInnerStructBClassPath).obj()));
+
+  const int kMethodsSampleForTestsSize = arraysize(kMethodsSampleForTests);
+
+  if (env->RegisterNatives(SampleForTests_clazz(env),
+                           kMethodsSampleForTests,
+                           kMethodsSampleForTestsSize) < 0) {
+    jni_generator::HandleRegistrationError(
+        env, SampleForTests_clazz(env), __FILE__);
+    return false;
+  }
+
+  return true;
+}
+
+}  // namespace android
+}  // namespace base
+
+#endif  // org_chromium_example_jni_generator_SampleForTests_JNI
diff --git a/base/android/jni_generator/java/src/org/chromium/example/jni_generator/SampleForTests.java b/base/android/jni_generator/java/src/org/chromium/example/jni_generator/SampleForTests.java
index 42d8e56..4958f04 100644
--- a/base/android/jni_generator/java/src/org/chromium/example/jni_generator/SampleForTests.java
+++ b/base/android/jni_generator/java/src/org/chromium/example/jni_generator/SampleForTests.java
@@ -10,7 +10,6 @@
 import org.chromium.base.annotations.CalledByNative;
 import org.chromium.base.annotations.CalledByNativeUnchecked;
 import org.chromium.base.annotations.JNINamespace;
-import org.chromium.base.annotations.NativeCall;
 import org.chromium.base.annotations.NativeClassQualifiedName;
 
 import java.util.ArrayList;
@@ -165,13 +164,6 @@
     // String constants that look like comments don't confuse the generator:
     private String mArrgh = "*/*";
 
-    private @interface SomeAnnotation {}
-
-    // The generator is not confused by @Annotated parameters.
-    @CalledByNative
-    void javaMethodWithAnnotatedParam(@SomeAnnotation int foo) {
-    }
-
     // ---------------------------------------------------------------------------------------------
     // Java fields which are accessed from C++ code only must be annotated with @AccessedByNative to
     // prevent them being eliminated when unreferenced code is stripped.
@@ -309,10 +301,4 @@
     native void nativeAddStructB(long nativeCPPClass, InnerStructB b);
     native void nativeIterateAndDoSomethingWithStructB(long nativeCPPClass);
     native String nativeReturnAString(long nativeCPPClass);
-
-    // This inner class shows how to annotate native methods on inner classes.
-    static class InnerClass {
-        @NativeCall("InnerClass")
-        private static native int nativeGetInnerIntFunction();
-    }
 }
diff --git a/base/android/jni_generator/jni_generator.gyp b/base/android/jni_generator/jni_generator.gyp
new file mode 100644
index 0000000..ce936a0
--- /dev/null
+++ b/base/android/jni_generator/jni_generator.gyp
@@ -0,0 +1,72 @@
+# Copyright (c) 2012 The Chromium Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+{
+  'targets': [
+    # GYP: //base/android/jni_generator:jni_generator_tests
+    {
+      'target_name': 'jni_generator_py_tests',
+      'type': 'none',
+      'variables': {
+        'stamp': '<(INTERMEDIATE_DIR)/jni_generator_py_tests.stamp',
+      },
+      'actions': [
+        {
+          'action_name': 'run_jni_generator_py_tests',
+          'inputs': [
+            'jni_generator.py',
+            'jni_generator_tests.py',
+            'java/src/org/chromium/example/jni_generator/SampleForTests.java',
+            'golden_sample_for_tests_jni.h',
+          ],
+          'outputs': [
+            '<(stamp)',
+          ],
+          'action': [
+            'python', 'jni_generator_tests.py',
+            '--stamp=<(stamp)',
+          ],
+        },
+      ],
+    },
+    # GYP: //base/android/jni_generator:jni_sample_header
+    {
+      'target_name': 'jni_sample_header',
+      'type': 'none',
+      'sources': [
+        'java/src/org/chromium/example/jni_generator/SampleForTests.java',
+      ],
+      'variables': {
+        'jni_gen_package': 'example',
+      },
+      'includes': [ '../../../build/jni_generator.gypi' ],
+    },
+    # GYP: //base/android/jni_generator:jni_sample_java
+    {
+      'target_name': 'jni_sample_java',
+      'type': 'none',
+      'variables': {
+        'java_in_dir': '../../../base/android/jni_generator/java',
+      },
+      'dependencies': [
+        '<(DEPTH)/base/base.gyp:base_java',
+      ],
+      'includes': [ '../../../build/java.gypi' ],
+    },
+    # GYP: //base/android/jni_generator:jni_generator_tests
+    {
+      'target_name': 'jni_generator_tests',
+      'type': 'executable',
+      'dependencies': [
+        '../../base.gyp:test_support_base',
+        'jni_generator_py_tests',
+        'jni_sample_header',
+        'jni_sample_java',
+      ],
+      'sources': [
+        'sample_for_tests.cc',
+      ],
+    },
+  ],
+}
diff --git a/base/android/jni_generator/jni_generator.py b/base/android/jni_generator/jni_generator.py
index 99d8b42..b0134d6 100755
--- a/base/android/jni_generator/jni_generator.py
+++ b/base/android/jni_generator/jni_generator.py
@@ -138,7 +138,7 @@
 def WrapCTypeForDeclaration(c_type):
   """Wrap the C datatype in a JavaRef if required."""
   if re.match(RE_SCOPED_JNI_TYPES, c_type):
-    return 'const base::android::JavaParamRef<' + c_type + '>&'
+    return 'const JavaParamRef<' + c_type + '>&'
   else:
     return c_type
 
@@ -153,11 +153,7 @@
   if java_type == 'int':
     return 'JniIntWrapper'
   else:
-    c_type = JavaDataTypeToC(java_type)
-    if re.match(RE_SCOPED_JNI_TYPES, c_type):
-      return 'const base::android::JavaRefOrBare<' + c_type + '>&'
-    else:
-      return c_type
+    return JavaDataTypeToC(java_type)
 
 
 def JavaReturnValueToC(java_type):
@@ -356,14 +352,8 @@
     ret = []
     for p in [p.strip() for p in params.split(',')]:
       items = p.split(' ')
-
-      # Remove @Annotations from parameters.
-      while items[0].startswith('@'):
-        del items[0]
-
       if 'final' in items:
         items.remove('final')
-
       param = Param(
           datatype=items[0],
           name=(items[1] if len(items) > 1 else 'p%s' % len(ret)),
@@ -412,19 +402,6 @@
   return natives
 
 
-def IsMainDexJavaClass(contents):
-  """Returns "true" if the class is annotated with "@MainDex", "false" if not.
-
-  JNI registration doesn't always need to be completed for non-browser processes
-  since most Java code is only used by the browser process. Classes that are
-  needed by non-browser processes must explicitly be annotated with @MainDex
-  to force JNI registration.
-  """
-  re_maindex = re.compile(r'@MainDex[\s\S]*class\s+\w+\s*{')
-  found = re.search(re_maindex, contents)
-  return 'true' if found else 'false'
-
-
 def GetStaticCastForReturnType(return_type):
   type_map = { 'String' : 'jstring',
                'java/lang/String' : 'jstring',
@@ -531,17 +508,11 @@
 RE_CALLED_BY_NATIVE = re.compile(
     '@CalledByNative(?P<Unchecked>(Unchecked)*?)(?:\("(?P<annotation>.*)"\))?'
     '\s+(?P<prefix>[\w ]*?)'
-    '(:?\s*@\w+)?'  # Ignore annotations in return types.
     '\s*(?P<return_type>\S+?)'
     '\s+(?P<name>\w+)'
     '\s*\((?P<params>[^\)]*)\)')
 
 
-# Removes empty lines that are indented (i.e. start with 2x spaces).
-def RemoveIndentedEmptyLines(string):
-  return re.sub('^(?: {2})+$\n', '', string, flags=re.MULTILINE)
-
-
 def ExtractCalledByNatives(contents):
   """Parses all methods annotated with @CalledByNative.
 
@@ -647,8 +618,8 @@
                           value=value.group('value')))
 
     self.inl_header_file_generator = InlHeaderFileGenerator(
-        self.namespace, self.fully_qualified_class, [], self.called_by_natives,
-        self.constant_fields, options)
+        self.namespace, self.fully_qualified_class, [],
+        self.called_by_natives, self.constant_fields, options)
 
   def GetContent(self):
     return self.inl_header_file_generator.GetContent()
@@ -682,13 +653,12 @@
     jni_namespace = ExtractJNINamespace(contents) or options.namespace
     natives = ExtractNatives(contents, options.ptr_type)
     called_by_natives = ExtractCalledByNatives(contents)
-    maindex = IsMainDexJavaClass(contents)
     if len(natives) == 0 and len(called_by_natives) == 0:
       raise SyntaxError('Unable to find any JNI methods for %s.' %
                         fully_qualified_class)
     inl_header_file_generator = InlHeaderFileGenerator(
-        jni_namespace, fully_qualified_class, natives, called_by_natives, [],
-        options, maindex)
+        jni_namespace, fully_qualified_class, natives, called_by_natives,
+        [], options)
     self.content = inl_header_file_generator.GetContent()
 
   @classmethod
@@ -724,7 +694,7 @@
   """Generates an inline header file for JNI integration."""
 
   def __init__(self, namespace, fully_qualified_class, natives,
-               called_by_natives, constant_fields, options, maindex='false'):
+               called_by_natives, constant_fields, options):
     self.namespace = namespace
     self.fully_qualified_class = fully_qualified_class
     self.class_name = self.fully_qualified_class.split('/')[-1]
@@ -732,7 +702,6 @@
     self.called_by_natives = called_by_natives
     self.header_guard = fully_qualified_class.replace('/', '_') + '_JNI'
     self.constant_fields = constant_fields
-    self.maindex = maindex
     self.options = options
 
 
@@ -791,8 +760,6 @@
         'HEADER_GUARD': self.header_guard,
         'INCLUDES': self.GetIncludesString(),
     }
-    assert ((values['JNI_NATIVE_METHODS'] == '') ==
-            (values['REGISTER_NATIVES'] == ''))
     return WrapOutput(template.substitute(values))
 
   def GetClassPathDefinitionsString(self):
@@ -851,7 +818,7 @@
 
   def GetJNINativeMethodsString(self):
     """Returns the implementation of the array of native methods."""
-    if not self.options.native_exports_optional:
+    if self.options.native_exports and not self.options.native_exports_optional:
       return ''
     template = Template("""\
 static const JNINativeMethod kMethods${JAVA_CLASS}[] = {
@@ -862,13 +829,10 @@
 
   def GetRegisterNativesString(self):
     """Returns the code for RegisterNatives."""
-    natives = self.GetRegisterNativesImplString()
-    if not natives:
-      return ''
-
     template = Template("""\
 ${REGISTER_NATIVES_SIGNATURE} {
 ${EARLY_EXIT}
+${CLASSES}
 ${NATIVES}
   return true;
 }
@@ -877,20 +841,20 @@
     early_exit = ''
     if self.options.native_exports_optional:
       early_exit = """\
-  if (jni_generator::ShouldSkipJniRegistration(%s))
-    return true;
-""" % self.maindex
+  if (base::android::IsManualJniRegistrationDisabled()) return true;
+"""
 
+    natives = self.GetRegisterNativesImplString()
     values = {'REGISTER_NATIVES_SIGNATURE': signature,
               'EARLY_EXIT': early_exit,
+              'CLASSES': self.GetFindClasses(),
               'NATIVES': natives,
              }
-
     return template.substitute(values)
 
   def GetRegisterNativesImplString(self):
     """Returns the shared implementation for RegisterNatives."""
-    if not self.options.native_exports_optional:
+    if self.options.native_exports and not self.options.native_exports_optional:
       return ''
 
     template = Template("""\
@@ -990,8 +954,7 @@
     return template.substitute(values)
 
   def GetJavaParamRefForCall(self, c_type, name):
-    return Template(
-        'base::android::JavaParamRef<${TYPE}>(env, ${NAME})').substitute({
+    return Template('JavaParamRef<${TYPE}>(env, ${NAME})').substitute({
         'TYPE': c_type,
         'NAME': name,
     })
@@ -1016,15 +979,15 @@
         params_in_call.append(p.name)
     params_in_call = ', '.join(params_in_call)
 
+    if self.options.native_exports:
+      stub_visibility = 'extern "C" __attribute__((visibility("default")))\n'
+    else:
+      stub_visibility = 'static '
     return_type = return_declaration = JavaDataTypeToC(native.return_type)
     post_call = ''
     if re.match(RE_SCOPED_JNI_TYPES, return_type):
       post_call = '.Release()'
-      return_declaration = ('base::android::ScopedJavaLocalRef<' + return_type +
-                            '>')
-    profiling_entered_native = ''
-    if self.options.enable_profiling:
-      profiling_entered_native = 'JNI_LINK_SAVED_FRAME_POINTER;'
+      return_declaration = 'ScopedJavaLocalRef<' + return_type + '>'
     values = {
         'RETURN': return_type,
         'RETURN_DECLARATION': return_declaration,
@@ -1034,7 +997,7 @@
         'PARAMS_IN_CALL': params_in_call,
         'POST_CALL': post_call,
         'STUB_NAME': self.GetStubName(native),
-        'PROFILING_ENTERED_NATIVE': profiling_entered_native,
+        'STUB_VISIBILITY': stub_visibility,
     }
 
     if is_method:
@@ -1047,8 +1010,8 @@
           'P0_TYPE': native.p0_type,
       })
       template = Template("""\
-JNI_GENERATOR_EXPORT ${RETURN} ${STUB_NAME}(JNIEnv* env, ${PARAMS_IN_STUB}) {
-  ${PROFILING_ENTERED_NATIVE}
+${STUB_VISIBILITY}${RETURN} ${STUB_NAME}(JNIEnv* env,
+    ${PARAMS_IN_STUB}) {
   ${P0_TYPE}* native = reinterpret_cast<${P0_TYPE}*>(${PARAM0_NAME});
   CHECK_NATIVE_PTR(env, jcaller, native, "${NAME}"${OPTIONAL_ERROR_RETURN});
   return native->${NAME}(${PARAMS_IN_CALL})${POST_CALL};
@@ -1058,21 +1021,16 @@
       template = Template("""
 static ${RETURN_DECLARATION} ${NAME}(JNIEnv* env, ${PARAMS});
 
-JNI_GENERATOR_EXPORT ${RETURN} ${STUB_NAME}(JNIEnv* env, ${PARAMS_IN_STUB}) {
-  ${PROFILING_ENTERED_NATIVE}
+${STUB_VISIBILITY}${RETURN} ${STUB_NAME}(JNIEnv* env, ${PARAMS_IN_STUB}) {
   return ${NAME}(${PARAMS_IN_CALL})${POST_CALL};
 }
 """)
 
-    return RemoveIndentedEmptyLines(template.substitute(values))
+    return template.substitute(values)
 
   def GetArgument(self, param):
-    if param.datatype == 'int':
-      return 'as_jint(' + param.name + ')'
-    elif re.match(RE_SCOPED_JNI_TYPES, JavaDataTypeToC(param.datatype)):
-      return param.name + '.obj()'
-    else:
-      return param.name
+    return ('as_jint(' + param.name + ')'
+            if param.datatype == 'int' else param.name)
 
   def GetArgumentsInCall(self, params):
     """Return a string of arguments to call from native into Java"""
@@ -1085,9 +1043,8 @@
       first_param_in_declaration = ''
       first_param_in_call = ('%s_clazz(env)' % java_class)
     else:
-      first_param_in_declaration = (
-          ', const base::android::JavaRefOrBare<jobject>& obj')
-      first_param_in_call = 'obj.obj()'
+      first_param_in_declaration = ', jobject obj'
+      first_param_in_call = 'obj'
     params_in_declaration = self.GetCalledByNativeParamsInDeclaration(
         called_by_native)
     if params_in_declaration:
@@ -1113,13 +1070,10 @@
       pre_call = ' ' + pre_call
       return_declaration = return_type + ' ret ='
       if re.match(RE_SCOPED_JNI_TYPES, return_type):
-        return_type = 'base::android::ScopedJavaLocalRef<' + return_type + '>'
+        return_type = 'ScopedJavaLocalRef<' + return_type + '>'
         return_clause = 'return ' + return_type + '(env, ret);'
       else:
         return_clause = 'return ret;'
-    profiling_leaving_native = ''
-    if self.options.enable_profiling:
-      profiling_leaving_native = 'JNI_SAVE_FRAME_POINTER;'
     return {
         'JAVA_CLASS': java_class,
         'RETURN_TYPE': return_type,
@@ -1135,8 +1089,7 @@
         'PARAMS_IN_CALL': params_in_call,
         'METHOD_ID_VAR_NAME': called_by_native.method_id_var_name,
         'CHECK_EXCEPTION': check_exception,
-        'GET_METHOD_ID_IMPL': self.GetMethodIDImpl(called_by_native),
-        'PROFILING_LEAVING_NATIVE': profiling_leaving_native,
+        'GET_METHOD_ID_IMPL': self.GetMethodIDImpl(called_by_native)
     }
 
 
@@ -1153,11 +1106,11 @@
     template = Template("""
 static base::subtle::AtomicWord g_${JAVA_CLASS}_${METHOD_ID_VAR_NAME} = 0;
 ${FUNCTION_HEADER}
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, ${FIRST_PARAM_IN_CALL},
       ${JAVA_CLASS}_clazz(env)${OPTIONAL_ERROR_RETURN});
   jmethodID method_id =
     ${GET_METHOD_ID_IMPL}
-  ${PROFILING_LEAVING_NATIVE}
   ${RETURN_DECLARATION}
      ${PRE_CALL}env->${ENV_CALL}(${FIRST_PARAM_IN_CALL},
           method_id${PARAMS_IN_CALL})${POST_CALL};
@@ -1172,7 +1125,7 @@
           function_header_with_unused_template.substitute(values))
     else:
       values['FUNCTION_HEADER'] = function_header_template.substitute(values)
-    return RemoveIndentedEmptyLines(template.substitute(values))
+    return template.substitute(values)
 
   def GetKMethodArrayEntry(self, native):
     template = Template('    { "native${NAME}", ${JNI_SIGNATURE}, ' +
@@ -1200,9 +1153,13 @@
     ret = []
     template = Template("""\
 const char k${JAVA_CLASS}ClassPath[] = "${JNI_CLASS_PATH}";""")
-    all_classes = self.GetUniqueClasses(self.called_by_natives)
-    if self.options.native_exports_optional:
-      all_classes.update(self.GetUniqueClasses(self.natives))
+    native_classes = self.GetUniqueClasses(self.natives)
+    called_by_native_classes = self.GetUniqueClasses(self.called_by_natives)
+    if self.options.native_exports:
+      all_classes = called_by_native_classes
+    else:
+      all_classes = native_classes
+      all_classes.update(called_by_native_classes)
 
     for clazz in all_classes:
       values = {
@@ -1212,14 +1169,21 @@
       ret += [template.substitute(values)]
     ret += ''
 
-    template = Template("""\
+    class_getter_methods = []
+    if self.options.native_exports:
+      template = Template("""\
 // Leaking this jclass as we cannot use LazyInstance from some threads.
 base::subtle::AtomicWord g_${JAVA_CLASS}_clazz __attribute__((unused)) = 0;
 #define ${JAVA_CLASS}_clazz(env) \
 base::android::LazyGetClass(env, k${JAVA_CLASS}ClassPath, \
 &g_${JAVA_CLASS}_clazz)""")
+    else:
+      template = Template("""\
+// Leaking this jclass as we cannot use LazyInstance from some threads.
+jclass g_${JAVA_CLASS}_clazz = NULL;
+#define ${JAVA_CLASS}_clazz(env) g_${JAVA_CLASS}_clazz""")
 
-    for clazz in all_classes:
+    for clazz in called_by_native_classes:
       values = {
           'JAVA_CLASS': clazz,
       }
@@ -1227,6 +1191,19 @@
 
     return '\n'.join(ret)
 
+  def GetFindClasses(self):
+    """Returns the imlementation of FindClass for all known classes."""
+    if self.options.native_exports:
+      return '\n'
+    template = Template("""\
+  g_${JAVA_CLASS}_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, k${JAVA_CLASS}ClassPath).obj()));""")
+    ret = []
+    for clazz in self.GetUniqueClasses(self.called_by_natives):
+      values = {'JAVA_CLASS': clazz}
+      ret += [template.substitute(values)]
+    return '\n'.join(ret)
+
   def GetMethodIDImpl(self, called_by_native):
     """Returns the implementation of GetMethodID."""
     template = Template("""\
@@ -1389,12 +1366,15 @@
                            help='The path to cpp command.')
   option_parser.add_option('--javap', default='javap',
                            help='The path to javap command.')
+  option_parser.add_option('--native_exports', action='store_true',
+                           help='Native method registration through .so '
+                           'exports.')
   option_parser.add_option('--native_exports_optional', action='store_true',
                            help='Support both explicit and native method'
                            'registration.')
-  option_parser.add_option('--enable_profiling', action='store_true',
-                           help='Add additional profiling instrumentation.')
   options, args = option_parser.parse_args(argv)
+  if options.native_exports_optional:
+    options.native_exports = True
   if options.jar_file:
     input_file = ExtractJarInputFile(options.jar_file, options.input_file,
                                      options.output_dir)
@@ -1411,7 +1391,9 @@
   GenerateJNIHeader(input_file, output_file, options)
 
   if options.depfile:
-    build_utils.WriteDepfile(options.depfile, output_file)
+    build_utils.WriteDepfile(
+        options.depfile,
+        build_utils.GetPythonDependencies())
 
 
 if __name__ == '__main__':
diff --git a/base/android/jni_generator/jni_generator_helper.h b/base/android/jni_generator/jni_generator_helper.h
index 3062806..9075d3c 100644
--- a/base/android/jni_generator/jni_generator_helper.h
+++ b/base/android/jni_generator/jni_generator_helper.h
@@ -2,6 +2,7 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
+
 #ifndef BASE_ANDROID_JNI_GENERATOR_JNI_GENERATOR_HELPER_H_
 #define BASE_ANDROID_JNI_GENERATOR_JNI_GENERATOR_HELPER_H_
 
@@ -10,53 +11,30 @@
 #include "base/android/jni_android.h"
 #include "base/android/scoped_java_ref.h"
 #include "base/logging.h"
-#include "build/build_config.h"
 
 // Project-specific macros used by the header files generated by
 // jni_generator.py. Different projects can then specify their own
 // implementation for this file.
 #define CHECK_NATIVE_PTR(env, jcaller, native_ptr, method_name, ...) \
-  DCHECK(native_ptr) << method_name;
+    DCHECK(native_ptr) << method_name;
 
-#define CHECK_CLAZZ(env, jcaller, clazz, ...) DCHECK(clazz);
-
-#if defined(ARCH_CPU_X86)
-// Dalvik JIT generated code doesn't guarantee 16-byte stack alignment on
-// x86 - use force_align_arg_pointer to realign the stack at the JNI
-// boundary. crbug.com/655248
-#define JNI_GENERATOR_EXPORT \
-  extern "C" __attribute__((visibility("default"), force_align_arg_pointer))
-#else
-#define JNI_GENERATOR_EXPORT extern "C" __attribute__((visibility("default")))
-#endif
+#define CHECK_CLAZZ(env, jcaller, clazz, ...) \
+    DCHECK(clazz);
 
 namespace jni_generator {
 
-inline void HandleRegistrationError(JNIEnv* env,
-                                    jclass clazz,
-                                    const char* filename) {
-  LOG(ERROR) << "RegisterNatives failed in " << filename;
-}
-
-inline void CheckException(JNIEnv* env) {
-  base::android::CheckException(env);
-}
-
-inline bool ShouldSkipJniRegistration(bool is_maindex_class) {
-  switch (base::android::GetJniRegistrationType()) {
-    case base::android::ALL_JNI_REGISTRATION:
-      return false;
-    case base::android::NO_JNI_REGISTRATION:
-      // TODO(estevenson): Change this to a DCHECK.
-      return true;
-    case base::android::SELECTIVE_JNI_REGISTRATION:
-      return !is_maindex_class;
-    default:
-      NOTREACHED();
-      return false;
+  inline void HandleRegistrationError(JNIEnv* env, jclass clazz,
+                                      const char* filename) {
+    LOG(ERROR) << "RegisterNatives failed in " << filename;
   }
-}
+
+  inline void CheckException(JNIEnv* env) {
+    base::android::CheckException(env);
+  }
 
 }  // namespace jni_generator
 
+using base::android::ScopedJavaLocalRef;
+using base::android::JavaParamRef;
+
 #endif  // BASE_ANDROID_JNI_GENERATOR_JNI_GENERATOR_HELPER_H_
diff --git a/base/android/jni_generator/jni_generator_tests.py b/base/android/jni_generator/jni_generator_tests.py
index c0c8238..5126896 100755
--- a/base/android/jni_generator/jni_generator_tests.py
+++ b/base/android/jni_generator/jni_generator_tests.py
@@ -40,8 +40,8 @@
     self.ptr_type = 'long'
     self.cpp = 'cpp'
     self.javap = 'javap'
-    self.native_exports_optional = True
-    self.enable_profiling = False
+    self.native_exports = False
+    self.native_exports_optional = False
 
 class TestGenerator(unittest.TestCase):
   def assertObjEquals(self, first, second):
@@ -403,10 +403,6 @@
           return
       }
     }
-    @CalledByNative
-    public static @Status int updateStatus(@Status int status) {
-        return getAndUpdateStatus(status);
-    }
     @CalledByNativeUnchecked
     private void uncheckedCall(int iParam);
 
@@ -529,17 +525,6 @@
             unchecked=False,
         ),
         CalledByNative(
-          return_type='int',
-          system_class=False,
-          static=True,
-          name='updateStatus',
-          method_id_var_name='updateStatus',
-          java_class_name='',
-          params=[Param(datatype='int', name='status')],
-          env_call=('Integer', ''),
-          unchecked=False,
-        ),
-        CalledByNative(
             return_type='void',
             system_class=False,
             static=False,
@@ -834,7 +819,7 @@
     content = file(os.path.join(script_dir,
         'java/src/org/chromium/example/jni_generator/SampleForTests.java')
         ).read()
-    golden_file = os.path.join(script_dir, 'SampleForTests_jni.golden')
+    golden_file = os.path.join(script_dir, 'golden_sample_for_tests_jni.h')
     golden_content = file(golden_file).read()
     jni_from_java = jni_generator.JNIFromJavaSource(
         content, 'org/chromium/example/jni_generator/SampleForTests',
@@ -950,34 +935,7 @@
                                              natives, [], [], test_options)
     self.assertGoldenTextEquals(h.GetContent())
 
-  def testMainDexFile(self):
-    test_data = """
-    package org.chromium.example.jni_generator;
-
-    @MainDex
-    class Test {
-        private static native int nativeStaticMethod(long nativeTest, int arg1);
-    }
-    """
-    options = TestOptions()
-    jni_from_java = jni_generator.JNIFromJavaSource(
-      test_data, 'org/chromium/foo/Bar', options)
-    self.assertGoldenTextEquals(jni_from_java.GetContent())
-
-  def testNonMainDexFile(self):
-    test_data = """
-    package org.chromium.example.jni_generator;
-
-    class Test {
-        private static native int nativeStaticMethod(long nativeTest, int arg1);
-    }
-    """
-    options = TestOptions()
-    jni_from_java = jni_generator.JNIFromJavaSource(
-      test_data, 'org/chromium/foo/Bar', options)
-    self.assertGoldenTextEquals(jni_from_java.GetContent())
-
-  def testNativeExportsOnlyOption(self):
+  def runNativeExportsOption(self, optional):
     test_data = """
     package org.chromium.example.jni_generator;
 
@@ -1009,10 +967,19 @@
     }
     """
     options = TestOptions()
-    options.native_exports_optional = False
+    options.native_exports = True
+    options.native_exports_optional = optional
     jni_from_java = jni_generator.JNIFromJavaSource(
         test_data, 'org/chromium/example/jni_generator/SampleForTests', options)
-    self.assertGoldenTextEquals(jni_from_java.GetContent())
+    return jni_from_java.GetContent()
+
+  def testNativeExportsOption(self):
+    content = self.runNativeExportsOption(False)
+    self.assertGoldenTextEquals(content)
+
+  def testNativeExportsOptionalOption(self):
+    content = self.runNativeExportsOption(True)
+    self.assertGoldenTextEquals(content)
 
   def testOuterInnerRaises(self):
     test_data = """
@@ -1074,7 +1041,7 @@
 def TouchStamp(stamp_path):
   dir_name = os.path.dirname(stamp_path)
   if not os.path.isdir(dir_name):
-    os.makedirs(dir_name)
+    os.makedirs()
 
   with open(stamp_path, 'a'):
     os.utime(stamp_path, None)
diff --git a/base/android/jni_generator/sample_for_tests.cc b/base/android/jni_generator/sample_for_tests.cc
index 42b2143..08e5ac9 100644
--- a/base/android/jni_generator/sample_for_tests.cc
+++ b/base/android/jni_generator/sample_for_tests.cc
@@ -51,8 +51,8 @@
                           const JavaParamRef<jobject>& caller,
                           const JavaParamRef<jobject>& structb) {
   long key = Java_InnerStructB_getKey(env, structb);
-  std::string value =
-      ConvertJavaStringToUTF8(env, Java_InnerStructB_getValue(env, structb));
+  std::string value = ConvertJavaStringToUTF8(
+      env, Java_InnerStructB_getValue(env, structb).obj());
   map_[key] = value;
 }
 
@@ -100,10 +100,6 @@
   return ScopedJavaLocalRef<jobject>();
 }
 
-static jint GetInnerIntFunction(JNIEnv*, const JavaParamRef<jclass>&) {
-  return 0;
-}
-
 } // namespace android
 } // namespace base
 
@@ -117,7 +113,7 @@
 
   // This is how you call a java method from C++. Note that you must have
   // obtained the jobject somehow.
-  ScopedJavaLocalRef<jobject> my_java_object;
+  jobject my_java_object = NULL;
   int bar = base::android::Java_SampleForTests_javaMethod(
       env, my_java_object, 1, 2);
 
@@ -127,16 +123,14 @@
     // Creates a "struct" that will then be used by the java side.
     ScopedJavaLocalRef<jobject> struct_a =
         base::android::Java_InnerStructA_create(
-            env, 0, 1, ConvertUTF8ToJavaString(env, "test"));
-    base::android::Java_SampleForTests_addStructA(env, my_java_object,
-                                                  struct_a);
+            env, 0, 1, ConvertUTF8ToJavaString(env, "test").obj());
+    base::android::Java_SampleForTests_addStructA(
+        env, my_java_object, struct_a.obj());
   }
   base::android::Java_SampleForTests_iterateAndDoSomething(env, my_java_object);
   base::android::Java_SampleForTests_packagePrivateJavaMethod(env,
                                                               my_java_object);
   base::android::Java_SampleForTests_methodThatThrowsException(env,
                                                                my_java_object);
-  base::android::Java_SampleForTests_javaMethodWithAnnotatedParam(
-      env, my_java_object, 42);
   return 0;
 }
diff --git a/base/android/jni_generator/testCalledByNatives.golden b/base/android/jni_generator/testCalledByNatives.golden
index ac86b2e..3bc586c 100644
--- a/base/android/jni_generator/testCalledByNatives.golden
+++ b/base/android/jni_generator/testCalledByNatives.golden
@@ -21,31 +21,32 @@
 const char kTestJniClassPath[] = "org/chromium/TestJni";
 const char kInfoBarClassPath[] = "org/chromium/TestJni$InfoBar";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_TestJni_clazz __attribute__((unused)) = 0;
-#define TestJni_clazz(env) base::android::LazyGetClass(env, kTestJniClassPath, &g_TestJni_clazz)
+jclass g_TestJni_clazz = NULL;
+#define TestJni_clazz(env) g_TestJni_clazz
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_InfoBar_clazz __attribute__((unused)) = 0;
-#define InfoBar_clazz(env) base::android::LazyGetClass(env, kInfoBarClassPath, &g_InfoBar_clazz)
+jclass g_InfoBar_clazz = NULL;
+#define InfoBar_clazz(env) g_InfoBar_clazz
 
 }  // namespace
 
 // Step 2: method stubs.
 
 static base::subtle::AtomicWord g_TestJni_showConfirmInfoBar = 0;
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_TestJni_showConfirmInfoBar(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper nativeInfoBar,
-    const base::android::JavaRefOrBare<jstring>& buttonOk,
-    const base::android::JavaRefOrBare<jstring>& buttonCancel,
-    const base::android::JavaRefOrBare<jstring>& title,
-    const base::android::JavaRefOrBare<jobject>& icon) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jobject> Java_TestJni_showConfirmInfoBar(JNIEnv* env,
+    jobject obj, JniIntWrapper nativeInfoBar,
+    jstring buttonOk,
+    jstring buttonCancel,
+    jstring title,
+    jobject icon) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "showConfirmInfoBar",
+
 "("
 "I"
 "Ljava/lang/String;"
@@ -57,27 +58,28 @@
       &g_TestJni_showConfirmInfoBar);
 
   jobject ret =
-      env->CallObjectMethod(obj.obj(),
-          method_id, as_jint(nativeInfoBar), buttonOk.obj(), buttonCancel.obj(),
-              title.obj(), icon.obj());
+      env->CallObjectMethod(obj,
+          method_id, as_jint(nativeInfoBar), buttonOk, buttonCancel, title,
+              icon);
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_showAutoLoginInfoBar = 0;
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_TestJni_showAutoLoginInfoBar(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper nativeInfoBar,
-    const base::android::JavaRefOrBare<jstring>& realm,
-    const base::android::JavaRefOrBare<jstring>& account,
-    const base::android::JavaRefOrBare<jstring>& args) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jobject> Java_TestJni_showAutoLoginInfoBar(JNIEnv*
+    env, jobject obj, JniIntWrapper nativeInfoBar,
+    jstring realm,
+    jstring account,
+    jstring args) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "showAutoLoginInfoBar",
+
 "("
 "I"
 "Ljava/lang/String;"
@@ -88,39 +90,40 @@
       &g_TestJni_showAutoLoginInfoBar);
 
   jobject ret =
-      env->CallObjectMethod(obj.obj(),
-          method_id, as_jint(nativeInfoBar), realm.obj(), account.obj(),
-              args.obj());
+      env->CallObjectMethod(obj,
+          method_id, as_jint(nativeInfoBar), realm, account, args);
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_InfoBar_dismiss = 0;
-static void Java_InfoBar_dismiss(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_InfoBar_dismiss(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InfoBar_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, InfoBar_clazz(env),
       "dismiss",
+
 "("
 ")"
 "V",
       &g_InfoBar_dismiss);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_TestJni_shouldShowAutoLogin = 0;
-static jboolean Java_TestJni_shouldShowAutoLogin(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& view,
-    const base::android::JavaRefOrBare<jstring>& realm,
-    const base::android::JavaRefOrBare<jstring>& account,
-    const base::android::JavaRefOrBare<jstring>& args) {
+static jboolean Java_TestJni_shouldShowAutoLogin(JNIEnv* env, jobject view,
+    jstring realm,
+    jstring account,
+    jstring args) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, TestJni_clazz(env),
       TestJni_clazz(env), false);
   jmethodID method_id =
@@ -128,6 +131,7 @@
       base::android::MethodID::TYPE_STATIC>(
       env, TestJni_clazz(env),
       "shouldShowAutoLogin",
+
 "("
 "Landroid/view/View;"
 "Ljava/lang/String;"
@@ -139,14 +143,15 @@
 
   jboolean ret =
       env->CallStaticBooleanMethod(TestJni_clazz(env),
-          method_id, view.obj(), realm.obj(), account.obj(), args.obj());
+          method_id, view, realm, account, args);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_TestJni_openUrl = 0;
-static base::android::ScopedJavaLocalRef<jobject> Java_TestJni_openUrl(JNIEnv*
-    env, const base::android::JavaRefOrBare<jstring>& url) {
+static ScopedJavaLocalRef<jobject> Java_TestJni_openUrl(JNIEnv* env, jstring
+    url) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, TestJni_clazz(env),
       TestJni_clazz(env), NULL);
   jmethodID method_id =
@@ -154,6 +159,7 @@
       base::android::MethodID::TYPE_STATIC>(
       env, TestJni_clazz(env),
       "openUrl",
+
 "("
 "Ljava/lang/String;"
 ")"
@@ -162,25 +168,27 @@
 
   jobject ret =
       env->CallStaticObjectMethod(TestJni_clazz(env),
-          method_id, url.obj());
+          method_id, url);
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_activateHardwareAcceleration = 0;
-static void Java_TestJni_activateHardwareAcceleration(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jboolean activated,
+static void Java_TestJni_activateHardwareAcceleration(JNIEnv* env, jobject obj,
+    jboolean activated,
     JniIntWrapper iPid,
     JniIntWrapper iType,
     JniIntWrapper iPrimaryID,
     JniIntWrapper iSecondaryID) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "activateHardwareAcceleration",
+
 "("
 "Z"
 "I"
@@ -191,307 +199,310 @@
 "V",
       &g_TestJni_activateHardwareAcceleration);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, activated, as_jint(iPid), as_jint(iType),
               as_jint(iPrimaryID), as_jint(iSecondaryID));
   jni_generator::CheckException(env);
-}
 
-static base::subtle::AtomicWord g_TestJni_updateStatus = 0;
-static jint Java_TestJni_updateStatus(JNIEnv* env, JniIntWrapper status) {
-  CHECK_CLAZZ(env, TestJni_clazz(env),
-      TestJni_clazz(env), 0);
-  jmethodID method_id =
-      base::android::MethodID::LazyGet<
-      base::android::MethodID::TYPE_STATIC>(
-      env, TestJni_clazz(env),
-      "updateStatus",
-"("
-"I"
-")"
-"I",
-      &g_TestJni_updateStatus);
-
-  jint ret =
-      env->CallStaticIntMethod(TestJni_clazz(env),
-          method_id, as_jint(status));
-  jni_generator::CheckException(env);
-  return ret;
 }
 
 static base::subtle::AtomicWord g_TestJni_uncheckedCall = 0;
-static void Java_TestJni_uncheckedCall(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper iParam) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_TestJni_uncheckedCall(JNIEnv* env, jobject obj, JniIntWrapper
+    iParam) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "uncheckedCall",
+
 "("
 "I"
 ")"
 "V",
       &g_TestJni_uncheckedCall);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, as_jint(iParam));
+
 }
 
 static base::subtle::AtomicWord g_TestJni_returnByteArray = 0;
-static base::android::ScopedJavaLocalRef<jbyteArray>
-    Java_TestJni_returnByteArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jbyteArray> Java_TestJni_returnByteArray(JNIEnv* env,
+    jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnByteArray",
+
 "("
 ")"
 "[B",
       &g_TestJni_returnByteArray);
 
   jbyteArray ret =
-      static_cast<jbyteArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jbyteArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jbyteArray>(env, ret);
+  return ScopedJavaLocalRef<jbyteArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_returnBooleanArray = 0;
-static base::android::ScopedJavaLocalRef<jbooleanArray>
-    Java_TestJni_returnBooleanArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jbooleanArray> Java_TestJni_returnBooleanArray(JNIEnv*
+    env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnBooleanArray",
+
 "("
 ")"
 "[Z",
       &g_TestJni_returnBooleanArray);
 
   jbooleanArray ret =
-      static_cast<jbooleanArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jbooleanArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jbooleanArray>(env, ret);
+  return ScopedJavaLocalRef<jbooleanArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_returnCharArray = 0;
-static base::android::ScopedJavaLocalRef<jcharArray>
-    Java_TestJni_returnCharArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jcharArray> Java_TestJni_returnCharArray(JNIEnv* env,
+    jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnCharArray",
+
 "("
 ")"
 "[C",
       &g_TestJni_returnCharArray);
 
   jcharArray ret =
-      static_cast<jcharArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jcharArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jcharArray>(env, ret);
+  return ScopedJavaLocalRef<jcharArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_returnShortArray = 0;
-static base::android::ScopedJavaLocalRef<jshortArray>
-    Java_TestJni_returnShortArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jshortArray> Java_TestJni_returnShortArray(JNIEnv*
+    env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnShortArray",
+
 "("
 ")"
 "[S",
       &g_TestJni_returnShortArray);
 
   jshortArray ret =
-      static_cast<jshortArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jshortArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jshortArray>(env, ret);
+  return ScopedJavaLocalRef<jshortArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_returnIntArray = 0;
-static base::android::ScopedJavaLocalRef<jintArray>
-    Java_TestJni_returnIntArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jintArray> Java_TestJni_returnIntArray(JNIEnv* env,
+    jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnIntArray",
+
 "("
 ")"
 "[I",
       &g_TestJni_returnIntArray);
 
   jintArray ret =
-      static_cast<jintArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jintArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jintArray>(env, ret);
+  return ScopedJavaLocalRef<jintArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_returnLongArray = 0;
-static base::android::ScopedJavaLocalRef<jlongArray>
-    Java_TestJni_returnLongArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jlongArray> Java_TestJni_returnLongArray(JNIEnv* env,
+    jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnLongArray",
+
 "("
 ")"
 "[J",
       &g_TestJni_returnLongArray);
 
   jlongArray ret =
-      static_cast<jlongArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jlongArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jlongArray>(env, ret);
+  return ScopedJavaLocalRef<jlongArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_returnDoubleArray = 0;
-static base::android::ScopedJavaLocalRef<jdoubleArray>
-    Java_TestJni_returnDoubleArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jdoubleArray> Java_TestJni_returnDoubleArray(JNIEnv*
+    env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnDoubleArray",
+
 "("
 ")"
 "[D",
       &g_TestJni_returnDoubleArray);
 
   jdoubleArray ret =
-      static_cast<jdoubleArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jdoubleArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jdoubleArray>(env, ret);
+  return ScopedJavaLocalRef<jdoubleArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_returnObjectArray = 0;
-static base::android::ScopedJavaLocalRef<jobjectArray>
-    Java_TestJni_returnObjectArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jobjectArray> Java_TestJni_returnObjectArray(JNIEnv*
+    env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnObjectArray",
+
 "("
 ")"
 "[Ljava/lang/Object;",
       &g_TestJni_returnObjectArray);
 
   jobjectArray ret =
-      static_cast<jobjectArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jobjectArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobjectArray>(env, ret);
+  return ScopedJavaLocalRef<jobjectArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_returnArrayOfByteArray = 0;
-static base::android::ScopedJavaLocalRef<jobjectArray>
-    Java_TestJni_returnArrayOfByteArray(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jobjectArray>
+    Java_TestJni_returnArrayOfByteArray(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "returnArrayOfByteArray",
+
 "("
 ")"
 "[[B",
       &g_TestJni_returnArrayOfByteArray);
 
   jobjectArray ret =
-      static_cast<jobjectArray>(env->CallObjectMethod(obj.obj(),
+      static_cast<jobjectArray>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobjectArray>(env, ret);
+  return ScopedJavaLocalRef<jobjectArray>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_getCompressFormat = 0;
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_TestJni_getCompressFormat(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jobject> Java_TestJni_getCompressFormat(JNIEnv* env,
+    jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "getCompressFormat",
+
 "("
 ")"
 "Landroid/graphics/Bitmap$CompressFormat;",
       &g_TestJni_getCompressFormat);
 
   jobject ret =
-      env->CallObjectMethod(obj.obj(),
+      env->CallObjectMethod(obj,
           method_id);
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_TestJni_getCompressFormatList = 0;
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_TestJni_getCompressFormatList(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jobject> Java_TestJni_getCompressFormatList(JNIEnv*
+    env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       TestJni_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
       base::android::MethodID::TYPE_INSTANCE>(
       env, TestJni_clazz(env),
       "getCompressFormatList",
+
 "("
 ")"
 "Ljava/util/List;",
       &g_TestJni_getCompressFormatList);
 
   jobject ret =
-      env->CallObjectMethod(obj.obj(),
+      env->CallObjectMethod(obj,
           method_id);
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 // Step 3: RegisterNatives.
 
+static bool RegisterNativesImpl(JNIEnv* env) {
+
+  g_TestJni_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kTestJniClassPath).obj()));
+  g_InfoBar_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kInfoBarClassPath).obj()));
+
+  return true;
+}
+
 #endif  // org_chromium_TestJni_JNI
diff --git a/base/android/jni_generator/testConstantsFromJavaP.golden b/base/android/jni_generator/testConstantsFromJavaP.golden
index b16956f..97c00f9 100644
--- a/base/android/jni_generator/testConstantsFromJavaP.golden
+++ b/base/android/jni_generator/testConstantsFromJavaP.golden
@@ -20,8 +20,8 @@
 namespace {
 const char kMotionEventClassPath[] = "android/view/MotionEvent";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_MotionEvent_clazz __attribute__((unused)) = 0;
-#define MotionEvent_clazz(env) base::android::LazyGetClass(env, kMotionEventClassPath, &g_MotionEvent_clazz)
+jclass g_MotionEvent_clazz = NULL;
+#define MotionEvent_clazz(env) g_MotionEvent_clazz
 
 }  // namespace
 
@@ -113,11 +113,11 @@
 // Step 2: method stubs.
 
 static base::subtle::AtomicWord g_MotionEvent_finalize = 0;
-static void Java_MotionEvent_finalize(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static void Java_MotionEvent_finalize(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_MotionEvent_finalize(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static void Java_MotionEvent_finalize(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -127,21 +127,22 @@
       "()V",
       &g_MotionEvent_finalize);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord
     g_MotionEvent_obtainAVME_J_J_I_I_LAVMEPP_LAVMEPC_I_I_F_F_I_I_I_I = 0;
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_I_LAVMEPP_LAVMEPC_I_I_F_F_I_I_I_I(JNIEnv*
     env, jlong p0,
     jlong p1,
     JniIntWrapper p2,
     JniIntWrapper p3,
-    const base::android::JavaRefOrBare<jobjectArray>& p4,
-    const base::android::JavaRefOrBare<jobjectArray>& p5,
+    jobjectArray p4,
+    jobjectArray p5,
     JniIntWrapper p6,
     JniIntWrapper p7,
     jfloat p8,
@@ -150,14 +151,14 @@
     JniIntWrapper p11,
     JniIntWrapper p12,
     JniIntWrapper p13) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_I_LAVMEPP_LAVMEPC_I_I_F_F_I_I_I_I(JNIEnv*
     env, jlong p0,
     jlong p1,
     JniIntWrapper p2,
     JniIntWrapper p3,
-    const base::android::JavaRefOrBare<jobjectArray>& p4,
-    const base::android::JavaRefOrBare<jobjectArray>& p5,
+    jobjectArray p4,
+    jobjectArray p5,
     JniIntWrapper p6,
     JniIntWrapper p7,
     jfloat p8,
@@ -166,6 +167,7 @@
     JniIntWrapper p11,
     JniIntWrapper p12,
     JniIntWrapper p13) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -178,23 +180,23 @@
 
   jobject ret =
       env->CallStaticObjectMethod(MotionEvent_clazz(env),
-          method_id, p0, p1, as_jint(p2), as_jint(p3), p4.obj(), p5.obj(),
-              as_jint(p6), as_jint(p7), p8, p9, as_jint(p10), as_jint(p11),
-              as_jint(p12), as_jint(p13));
+          method_id, p0, p1, as_jint(p2), as_jint(p3), p4, p5, as_jint(p6),
+              as_jint(p7), p8, p9, as_jint(p10), as_jint(p11), as_jint(p12),
+              as_jint(p13));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord
     g_MotionEvent_obtainAVME_J_J_I_I_AI_LAVMEPC_I_F_F_I_I_I_I = 0;
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_I_AI_LAVMEPC_I_F_F_I_I_I_I(JNIEnv* env,
     jlong p0,
     jlong p1,
     JniIntWrapper p2,
     JniIntWrapper p3,
-    const base::android::JavaRefOrBare<jintArray>& p4,
-    const base::android::JavaRefOrBare<jobjectArray>& p5,
+    jintArray p4,
+    jobjectArray p5,
     JniIntWrapper p6,
     jfloat p7,
     jfloat p8,
@@ -202,14 +204,14 @@
     JniIntWrapper p10,
     JniIntWrapper p11,
     JniIntWrapper p12) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_I_AI_LAVMEPC_I_F_F_I_I_I_I(JNIEnv* env,
     jlong p0,
     jlong p1,
     JniIntWrapper p2,
     JniIntWrapper p3,
-    const base::android::JavaRefOrBare<jintArray>& p4,
-    const base::android::JavaRefOrBare<jobjectArray>& p5,
+    jintArray p4,
+    jobjectArray p5,
     JniIntWrapper p6,
     jfloat p7,
     jfloat p8,
@@ -217,6 +219,7 @@
     JniIntWrapper p10,
     JniIntWrapper p11,
     JniIntWrapper p12) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -229,16 +232,15 @@
 
   jobject ret =
       env->CallStaticObjectMethod(MotionEvent_clazz(env),
-          method_id, p0, p1, as_jint(p2), as_jint(p3), p4.obj(), p5.obj(),
-              as_jint(p6), p7, p8, as_jint(p9), as_jint(p10), as_jint(p11),
-              as_jint(p12));
+          method_id, p0, p1, as_jint(p2), as_jint(p3), p4, p5, as_jint(p6), p7,
+              p8, as_jint(p9), as_jint(p10), as_jint(p11), as_jint(p12));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_MotionEvent_obtainAVME_J_J_I_F_F_F_F_I_F_F_I_I
     = 0;
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_F_F_F_F_I_F_F_I_I(JNIEnv* env, jlong p0,
     jlong p1,
     JniIntWrapper p2,
@@ -251,7 +253,7 @@
     jfloat p9,
     JniIntWrapper p10,
     JniIntWrapper p11) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_F_F_F_F_I_F_F_I_I(JNIEnv* env, jlong p0,
     jlong p1,
     JniIntWrapper p2,
@@ -264,6 +266,7 @@
     jfloat p9,
     JniIntWrapper p10,
     JniIntWrapper p11) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -279,12 +282,12 @@
           method_id, p0, p1, as_jint(p2), p3, p4, p5, p6, as_jint(p7), p8, p9,
               as_jint(p10), as_jint(p11));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord
     g_MotionEvent_obtainAVME_J_J_I_I_F_F_F_F_I_F_F_I_I = 0;
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_I_F_F_F_F_I_F_F_I_I(JNIEnv* env, jlong p0,
     jlong p1,
     JniIntWrapper p2,
@@ -298,7 +301,7 @@
     jfloat p10,
     JniIntWrapper p11,
     JniIntWrapper p12) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_I_F_F_F_F_I_F_F_I_I(JNIEnv* env, jlong p0,
     jlong p1,
     JniIntWrapper p2,
@@ -312,6 +315,7 @@
     jfloat p10,
     JniIntWrapper p11,
     JniIntWrapper p12) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -327,24 +331,25 @@
           method_id, p0, p1, as_jint(p2), as_jint(p3), p4, p5, p6, p7,
               as_jint(p8), p9, p10, as_jint(p11), as_jint(p12));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_MotionEvent_obtainAVME_J_J_I_F_F_I = 0;
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_F_F_I(JNIEnv* env, jlong p0,
     jlong p1,
     JniIntWrapper p2,
     jfloat p3,
     jfloat p4,
     JniIntWrapper p5) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jobject>
+static ScopedJavaLocalRef<jobject>
     Java_MotionEvent_obtainAVME_J_J_I_F_F_I(JNIEnv* env, jlong p0,
     jlong p1,
     JniIntWrapper p2,
     jfloat p3,
     jfloat p4,
     JniIntWrapper p5) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -359,16 +364,15 @@
       env->CallStaticObjectMethod(MotionEvent_clazz(env),
           method_id, p0, p1, as_jint(p2), p3, p4, as_jint(p5));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_MotionEvent_obtainAVME_AVME = 0;
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_MotionEvent_obtainAVME_AVME(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& p0) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_MotionEvent_obtainAVME_AVME(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& p0) {
+static ScopedJavaLocalRef<jobject> Java_MotionEvent_obtainAVME_AVME(JNIEnv* env,
+    jobject p0) __attribute__ ((unused));
+static ScopedJavaLocalRef<jobject> Java_MotionEvent_obtainAVME_AVME(JNIEnv* env,
+    jobject p0) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -381,18 +385,17 @@
 
   jobject ret =
       env->CallStaticObjectMethod(MotionEvent_clazz(env),
-          method_id, p0.obj());
+          method_id, p0);
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_MotionEvent_obtainNoHistory = 0;
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_MotionEvent_obtainNoHistory(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& p0) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_MotionEvent_obtainNoHistory(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& p0) {
+static ScopedJavaLocalRef<jobject> Java_MotionEvent_obtainNoHistory(JNIEnv* env,
+    jobject p0) __attribute__ ((unused));
+static ScopedJavaLocalRef<jobject> Java_MotionEvent_obtainNoHistory(JNIEnv* env,
+    jobject p0) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -405,17 +408,17 @@
 
   jobject ret =
       env->CallStaticObjectMethod(MotionEvent_clazz(env),
-          method_id, p0.obj());
+          method_id, p0);
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 static base::subtle::AtomicWord g_MotionEvent_recycle = 0;
-static void Java_MotionEvent_recycle(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static void Java_MotionEvent_recycle(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_MotionEvent_recycle(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static void Java_MotionEvent_recycle(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -425,17 +428,18 @@
       "()V",
       &g_MotionEvent_recycle);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getDeviceId = 0;
-static jint Java_MotionEvent_getDeviceId(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getDeviceId(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getDeviceId(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jint Java_MotionEvent_getDeviceId(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -446,18 +450,18 @@
       &g_MotionEvent_getDeviceId);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getSource = 0;
-static jint Java_MotionEvent_getSource(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getSource(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getSource(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jint Java_MotionEvent_getSource(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -468,19 +472,19 @@
       &g_MotionEvent_getSource);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_setSource = 0;
-static void Java_MotionEvent_setSource(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static void Java_MotionEvent_setSource(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_MotionEvent_setSource(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) __attribute__ ((unused));
+static void Java_MotionEvent_setSource(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -490,17 +494,18 @@
       "(I)V",
       &g_MotionEvent_setSource);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getAction = 0;
-static jint Java_MotionEvent_getAction(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getAction(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getAction(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jint Java_MotionEvent_getAction(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -511,18 +516,18 @@
       &g_MotionEvent_getAction);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getActionMasked = 0;
-static jint Java_MotionEvent_getActionMasked(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getActionMasked(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getActionMasked(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jint Java_MotionEvent_getActionMasked(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -533,18 +538,18 @@
       &g_MotionEvent_getActionMasked);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getActionIndex = 0;
-static jint Java_MotionEvent_getActionIndex(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getActionIndex(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getActionIndex(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jint Java_MotionEvent_getActionIndex(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -555,18 +560,18 @@
       &g_MotionEvent_getActionIndex);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getFlags = 0;
-static jint Java_MotionEvent_getFlags(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getFlags(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getFlags(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jint Java_MotionEvent_getFlags(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -577,18 +582,18 @@
       &g_MotionEvent_getFlags);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getDownTime = 0;
-static jlong Java_MotionEvent_getDownTime(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jlong Java_MotionEvent_getDownTime(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jlong Java_MotionEvent_getDownTime(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jlong Java_MotionEvent_getDownTime(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -599,18 +604,18 @@
       &g_MotionEvent_getDownTime);
 
   jlong ret =
-      env->CallLongMethod(obj.obj(),
+      env->CallLongMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getEventTime = 0;
-static jlong Java_MotionEvent_getEventTime(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jlong Java_MotionEvent_getEventTime(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jlong Java_MotionEvent_getEventTime(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jlong Java_MotionEvent_getEventTime(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -621,18 +626,18 @@
       &g_MotionEvent_getEventTime);
 
   jlong ret =
-      env->CallLongMethod(obj.obj(),
+      env->CallLongMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getXF = 0;
-static jfloat Java_MotionEvent_getXF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getXF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getXF(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jfloat Java_MotionEvent_getXF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -643,18 +648,18 @@
       &g_MotionEvent_getXF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getYF = 0;
-static jfloat Java_MotionEvent_getYF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getYF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getYF(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jfloat Java_MotionEvent_getYF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -665,18 +670,18 @@
       &g_MotionEvent_getYF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getPressureF = 0;
-static jfloat Java_MotionEvent_getPressureF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getPressureF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getPressureF(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jfloat Java_MotionEvent_getPressureF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -687,18 +692,18 @@
       &g_MotionEvent_getPressureF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getSizeF = 0;
-static jfloat Java_MotionEvent_getSizeF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getSizeF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getSizeF(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jfloat Java_MotionEvent_getSizeF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -709,18 +714,18 @@
       &g_MotionEvent_getSizeF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getTouchMajorF = 0;
-static jfloat Java_MotionEvent_getTouchMajorF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getTouchMajorF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getTouchMajorF(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jfloat Java_MotionEvent_getTouchMajorF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -731,18 +736,18 @@
       &g_MotionEvent_getTouchMajorF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getTouchMinorF = 0;
-static jfloat Java_MotionEvent_getTouchMinorF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getTouchMinorF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getTouchMinorF(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jfloat Java_MotionEvent_getTouchMinorF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -753,18 +758,18 @@
       &g_MotionEvent_getTouchMinorF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getToolMajorF = 0;
-static jfloat Java_MotionEvent_getToolMajorF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getToolMajorF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getToolMajorF(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jfloat Java_MotionEvent_getToolMajorF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -775,18 +780,18 @@
       &g_MotionEvent_getToolMajorF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getToolMinorF = 0;
-static jfloat Java_MotionEvent_getToolMinorF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getToolMinorF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getToolMinorF(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jfloat Java_MotionEvent_getToolMinorF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -797,18 +802,18 @@
       &g_MotionEvent_getToolMinorF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getOrientationF = 0;
-static jfloat Java_MotionEvent_getOrientationF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getOrientationF(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getOrientationF(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jfloat Java_MotionEvent_getOrientationF(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -819,19 +824,19 @@
       &g_MotionEvent_getOrientationF);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getAxisValueF_I = 0;
-static jfloat Java_MotionEvent_getAxisValueF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getAxisValueF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getAxisValueF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getAxisValueF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -842,18 +847,18 @@
       &g_MotionEvent_getAxisValueF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getPointerCount = 0;
-static jint Java_MotionEvent_getPointerCount(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getPointerCount(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getPointerCount(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jint Java_MotionEvent_getPointerCount(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -864,19 +869,19 @@
       &g_MotionEvent_getPointerCount);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getPointerId = 0;
-static jint Java_MotionEvent_getPointerId(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jint Java_MotionEvent_getPointerId(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getPointerId(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jint Java_MotionEvent_getPointerId(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -887,19 +892,19 @@
       &g_MotionEvent_getPointerId);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getToolType = 0;
-static jint Java_MotionEvent_getToolType(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jint Java_MotionEvent_getToolType(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getToolType(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) __attribute__ ((unused));
+static jint Java_MotionEvent_getToolType(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -910,19 +915,19 @@
       &g_MotionEvent_getToolType);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_findPointerIndex = 0;
-static jint Java_MotionEvent_findPointerIndex(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jint Java_MotionEvent_findPointerIndex(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_findPointerIndex(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jint Java_MotionEvent_findPointerIndex(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -933,19 +938,19 @@
       &g_MotionEvent_findPointerIndex);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getXF_I = 0;
-static jfloat Java_MotionEvent_getXF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getXF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getXF_I(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getXF_I(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -956,19 +961,19 @@
       &g_MotionEvent_getXF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getYF_I = 0;
-static jfloat Java_MotionEvent_getYF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getYF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getYF_I(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getYF_I(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -979,19 +984,19 @@
       &g_MotionEvent_getYF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getPressureF_I = 0;
-static jfloat Java_MotionEvent_getPressureF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getPressureF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getPressureF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getPressureF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1002,19 +1007,19 @@
       &g_MotionEvent_getPressureF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getSizeF_I = 0;
-static jfloat Java_MotionEvent_getSizeF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getSizeF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getSizeF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getSizeF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1025,19 +1030,19 @@
       &g_MotionEvent_getSizeF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getTouchMajorF_I = 0;
-static jfloat Java_MotionEvent_getTouchMajorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getTouchMajorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getTouchMajorF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getTouchMajorF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1048,19 +1053,19 @@
       &g_MotionEvent_getTouchMajorF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getTouchMinorF_I = 0;
-static jfloat Java_MotionEvent_getTouchMinorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getTouchMinorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getTouchMinorF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getTouchMinorF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1071,19 +1076,19 @@
       &g_MotionEvent_getTouchMinorF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getToolMajorF_I = 0;
-static jfloat Java_MotionEvent_getToolMajorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getToolMajorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getToolMajorF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getToolMajorF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1094,19 +1099,19 @@
       &g_MotionEvent_getToolMajorF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getToolMinorF_I = 0;
-static jfloat Java_MotionEvent_getToolMinorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getToolMinorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getToolMinorF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getToolMinorF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1117,19 +1122,19 @@
       &g_MotionEvent_getToolMinorF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getOrientationF_I = 0;
-static jfloat Java_MotionEvent_getOrientationF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getOrientationF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getOrientationF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getOrientationF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1140,20 +1145,21 @@
       &g_MotionEvent_getOrientationF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getAxisValueF_I_I = 0;
-static jfloat Java_MotionEvent_getAxisValueF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getAxisValueF_I_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getAxisValueF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getAxisValueF_I_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1164,20 +1170,21 @@
       &g_MotionEvent_getAxisValueF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getPointerCoords = 0;
-static void Java_MotionEvent_getPointerCoords(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
-    const base::android::JavaRefOrBare<jobject>& p1) __attribute__ ((unused));
-static void Java_MotionEvent_getPointerCoords(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
-    const base::android::JavaRefOrBare<jobject>& p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_MotionEvent_getPointerCoords(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
+    jobject p1) __attribute__ ((unused));
+static void Java_MotionEvent_getPointerCoords(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
+    jobject p1) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1187,19 +1194,21 @@
       "(ILandroid/view/MotionEvent$PointerCoords;)V",
       &g_MotionEvent_getPointerCoords);
 
-     env->CallVoidMethod(obj.obj(),
-          method_id, as_jint(p0), p1.obj());
+     env->CallVoidMethod(obj,
+          method_id, as_jint(p0), p1);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getPointerProperties = 0;
-static void Java_MotionEvent_getPointerProperties(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
-    const base::android::JavaRefOrBare<jobject>& p1) __attribute__ ((unused));
-static void Java_MotionEvent_getPointerProperties(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
-    const base::android::JavaRefOrBare<jobject>& p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_MotionEvent_getPointerProperties(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
+    jobject p1) __attribute__ ((unused));
+static void Java_MotionEvent_getPointerProperties(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
+    jobject p1) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1209,17 +1218,18 @@
       "(ILandroid/view/MotionEvent$PointerProperties;)V",
       &g_MotionEvent_getPointerProperties);
 
-     env->CallVoidMethod(obj.obj(),
-          method_id, as_jint(p0), p1.obj());
+     env->CallVoidMethod(obj,
+          method_id, as_jint(p0), p1);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getMetaState = 0;
-static jint Java_MotionEvent_getMetaState(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getMetaState(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getMetaState(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jint Java_MotionEvent_getMetaState(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1230,18 +1240,18 @@
       &g_MotionEvent_getMetaState);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getButtonState = 0;
-static jint Java_MotionEvent_getButtonState(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getButtonState(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getButtonState(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jint Java_MotionEvent_getButtonState(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1252,18 +1262,18 @@
       &g_MotionEvent_getButtonState);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getRawX = 0;
-static jfloat Java_MotionEvent_getRawX(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getRawX(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getRawX(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jfloat Java_MotionEvent_getRawX(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1274,18 +1284,18 @@
       &g_MotionEvent_getRawX);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getRawY = 0;
-static jfloat Java_MotionEvent_getRawY(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getRawY(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getRawY(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jfloat Java_MotionEvent_getRawY(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1296,18 +1306,18 @@
       &g_MotionEvent_getRawY);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getXPrecision = 0;
-static jfloat Java_MotionEvent_getXPrecision(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getXPrecision(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getXPrecision(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jfloat Java_MotionEvent_getXPrecision(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1318,18 +1328,18 @@
       &g_MotionEvent_getXPrecision);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getYPrecision = 0;
-static jfloat Java_MotionEvent_getYPrecision(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getYPrecision(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getYPrecision(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jfloat Java_MotionEvent_getYPrecision(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1340,18 +1350,18 @@
       &g_MotionEvent_getYPrecision);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistorySize = 0;
-static jint Java_MotionEvent_getHistorySize(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getHistorySize(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getHistorySize(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jint Java_MotionEvent_getHistorySize(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1362,19 +1372,19 @@
       &g_MotionEvent_getHistorySize);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalEventTime = 0;
-static jlong Java_MotionEvent_getHistoricalEventTime(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jlong Java_MotionEvent_getHistoricalEventTime(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jlong Java_MotionEvent_getHistoricalEventTime(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jlong Java_MotionEvent_getHistoricalEventTime(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1385,19 +1395,19 @@
       &g_MotionEvent_getHistoricalEventTime);
 
   jlong ret =
-      env->CallLongMethod(obj.obj(),
+      env->CallLongMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalXF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalXF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalXF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalXF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalXF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1408,19 +1418,19 @@
       &g_MotionEvent_getHistoricalXF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalYF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalYF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalYF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalYF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalYF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1431,19 +1441,19 @@
       &g_MotionEvent_getHistoricalYF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalPressureF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalPressureF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalPressureF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalPressureF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalPressureF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1454,19 +1464,19 @@
       &g_MotionEvent_getHistoricalPressureF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalSizeF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalSizeF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalSizeF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalSizeF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalSizeF_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1477,19 +1487,19 @@
       &g_MotionEvent_getHistoricalSizeF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalTouchMajorF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalTouchMajorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalTouchMajorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalTouchMajorF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalTouchMajorF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1500,19 +1510,19 @@
       &g_MotionEvent_getHistoricalTouchMajorF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalTouchMinorF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalTouchMinorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalTouchMinorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalTouchMinorF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalTouchMinorF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1523,19 +1533,19 @@
       &g_MotionEvent_getHistoricalTouchMinorF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalToolMajorF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalToolMajorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalToolMajorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalToolMajorF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalToolMajorF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1546,19 +1556,19 @@
       &g_MotionEvent_getHistoricalToolMajorF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalToolMinorF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalToolMinorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalToolMinorF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalToolMinorF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalToolMinorF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1569,19 +1579,19 @@
       &g_MotionEvent_getHistoricalToolMinorF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalOrientationF_I = 0;
-static jfloat Java_MotionEvent_getHistoricalOrientationF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static jfloat Java_MotionEvent_getHistoricalOrientationF_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jfloat Java_MotionEvent_getHistoricalOrientationF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) __attribute__ ((unused));
+static jfloat Java_MotionEvent_getHistoricalOrientationF_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1592,20 +1602,21 @@
       &g_MotionEvent_getHistoricalOrientationF_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalAxisValueF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalAxisValueF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalAxisValueF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalAxisValueF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalAxisValueF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1616,20 +1627,21 @@
       &g_MotionEvent_getHistoricalAxisValueF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalXF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalXF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalXF_I_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalXF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalXF_I_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1640,20 +1652,21 @@
       &g_MotionEvent_getHistoricalXF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalYF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalYF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalYF_I_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalYF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalYF_I_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1664,20 +1677,21 @@
       &g_MotionEvent_getHistoricalYF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalPressureF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalPressureF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalPressureF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalPressureF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalPressureF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1688,20 +1702,21 @@
       &g_MotionEvent_getHistoricalPressureF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalSizeF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalSizeF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalSizeF_I_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalSizeF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalSizeF_I_I(JNIEnv* env, jobject obj,
+    JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1712,20 +1727,21 @@
       &g_MotionEvent_getHistoricalSizeF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalTouchMajorF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalTouchMajorF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalTouchMajorF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalTouchMajorF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalTouchMajorF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1736,20 +1752,21 @@
       &g_MotionEvent_getHistoricalTouchMajorF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalTouchMinorF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalTouchMinorF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalTouchMinorF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalTouchMinorF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalTouchMinorF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1760,20 +1777,21 @@
       &g_MotionEvent_getHistoricalTouchMinorF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalToolMajorF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalToolMajorF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalToolMajorF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalToolMajorF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalToolMajorF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1784,20 +1802,21 @@
       &g_MotionEvent_getHistoricalToolMajorF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalToolMinorF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalToolMinorF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalToolMinorF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalToolMinorF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalToolMinorF_I_I(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1808,20 +1827,21 @@
       &g_MotionEvent_getHistoricalToolMinorF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalOrientationF_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalOrientationF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalOrientationF_I_I(JNIEnv* env,
+    jobject obj, JniIntWrapper p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalOrientationF_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalOrientationF_I_I(JNIEnv* env,
+    jobject obj, JniIntWrapper p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1832,22 +1852,23 @@
       &g_MotionEvent_getHistoricalOrientationF_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalAxisValueF_I_I_I = 0;
-static jfloat Java_MotionEvent_getHistoricalAxisValueF_I_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalAxisValueF_I_I_I(JNIEnv* env,
+    jobject obj, JniIntWrapper p0,
     JniIntWrapper p1,
     JniIntWrapper p2) __attribute__ ((unused));
-static jfloat Java_MotionEvent_getHistoricalAxisValueF_I_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static jfloat Java_MotionEvent_getHistoricalAxisValueF_I_I_I(JNIEnv* env,
+    jobject obj, JniIntWrapper p0,
     JniIntWrapper p1,
     JniIntWrapper p2) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1858,22 +1879,23 @@
       &g_MotionEvent_getHistoricalAxisValueF_I_I_I);
 
   jfloat ret =
-      env->CallFloatMethod(obj.obj(),
+      env->CallFloatMethod(obj,
           method_id, as_jint(p0), as_jint(p1), as_jint(p2));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getHistoricalPointerCoords = 0;
-static void Java_MotionEvent_getHistoricalPointerCoords(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+static void Java_MotionEvent_getHistoricalPointerCoords(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1,
-    const base::android::JavaRefOrBare<jobject>& p2) __attribute__ ((unused));
-static void Java_MotionEvent_getHistoricalPointerCoords(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0,
+    jobject p2) __attribute__ ((unused));
+static void Java_MotionEvent_getHistoricalPointerCoords(JNIEnv* env, jobject
+    obj, JniIntWrapper p0,
     JniIntWrapper p1,
-    const base::android::JavaRefOrBare<jobject>& p2) {
-  CHECK_CLAZZ(env, obj.obj(),
+    jobject p2) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1883,17 +1905,18 @@
       "(IILandroid/view/MotionEvent$PointerCoords;)V",
       &g_MotionEvent_getHistoricalPointerCoords);
 
-     env->CallVoidMethod(obj.obj(),
-          method_id, as_jint(p0), as_jint(p1), p2.obj());
+     env->CallVoidMethod(obj,
+          method_id, as_jint(p0), as_jint(p1), p2);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_getEdgeFlags = 0;
-static jint Java_MotionEvent_getEdgeFlags(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_MotionEvent_getEdgeFlags(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_MotionEvent_getEdgeFlags(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jint Java_MotionEvent_getEdgeFlags(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1904,19 +1927,19 @@
       &g_MotionEvent_getEdgeFlags);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_setEdgeFlags = 0;
-static void Java_MotionEvent_setEdgeFlags(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static void Java_MotionEvent_setEdgeFlags(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_MotionEvent_setEdgeFlags(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) __attribute__ ((unused));
+static void Java_MotionEvent_setEdgeFlags(JNIEnv* env, jobject obj,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1926,18 +1949,19 @@
       "(I)V",
       &g_MotionEvent_setEdgeFlags);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_setAction = 0;
-static void Java_MotionEvent_setAction(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static void Java_MotionEvent_setAction(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_MotionEvent_setAction(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) __attribute__ ((unused));
+static void Java_MotionEvent_setAction(JNIEnv* env, jobject obj, JniIntWrapper
+    p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1947,19 +1971,19 @@
       "(I)V",
       &g_MotionEvent_setAction);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_offsetLocation = 0;
-static void Java_MotionEvent_offsetLocation(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jfloat p0,
+static void Java_MotionEvent_offsetLocation(JNIEnv* env, jobject obj, jfloat p0,
     jfloat p1) __attribute__ ((unused));
-static void Java_MotionEvent_offsetLocation(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jfloat p0,
+static void Java_MotionEvent_offsetLocation(JNIEnv* env, jobject obj, jfloat p0,
     jfloat p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1969,19 +1993,19 @@
       "(FF)V",
       &g_MotionEvent_offsetLocation);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, p0, p1);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_setLocation = 0;
-static void Java_MotionEvent_setLocation(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jfloat p0,
+static void Java_MotionEvent_setLocation(JNIEnv* env, jobject obj, jfloat p0,
     jfloat p1) __attribute__ ((unused));
-static void Java_MotionEvent_setLocation(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jfloat p0,
+static void Java_MotionEvent_setLocation(JNIEnv* env, jobject obj, jfloat p0,
     jfloat p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -1991,19 +2015,18 @@
       "(FF)V",
       &g_MotionEvent_setLocation);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, p0, p1);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_transform = 0;
-static void Java_MotionEvent_transform(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, const
-    base::android::JavaRefOrBare<jobject>& p0) __attribute__ ((unused));
-static void Java_MotionEvent_transform(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, const
-    base::android::JavaRefOrBare<jobject>& p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_MotionEvent_transform(JNIEnv* env, jobject obj, jobject p0)
+    __attribute__ ((unused));
+static void Java_MotionEvent_transform(JNIEnv* env, jobject obj, jobject p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -2013,27 +2036,29 @@
       "(Landroid/graphics/Matrix;)V",
       &g_MotionEvent_transform);
 
-     env->CallVoidMethod(obj.obj(),
-          method_id, p0.obj());
+     env->CallVoidMethod(obj,
+          method_id, p0);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_addBatchV_J_F_F_F_F_I = 0;
-static void Java_MotionEvent_addBatchV_J_F_F_F_F_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jlong p0,
+static void Java_MotionEvent_addBatchV_J_F_F_F_F_I(JNIEnv* env, jobject obj,
+    jlong p0,
     jfloat p1,
     jfloat p2,
     jfloat p3,
     jfloat p4,
     JniIntWrapper p5) __attribute__ ((unused));
-static void Java_MotionEvent_addBatchV_J_F_F_F_F_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jlong p0,
+static void Java_MotionEvent_addBatchV_J_F_F_F_F_I(JNIEnv* env, jobject obj,
+    jlong p0,
     jfloat p1,
     jfloat p2,
     jfloat p3,
     jfloat p4,
     JniIntWrapper p5) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -2043,21 +2068,23 @@
       "(JFFFFI)V",
       &g_MotionEvent_addBatchV_J_F_F_F_F_I);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, p0, p1, p2, p3, p4, as_jint(p5));
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_addBatchV_J_LAVMEPC_I = 0;
-static void Java_MotionEvent_addBatchV_J_LAVMEPC_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jlong p0,
-    const base::android::JavaRefOrBare<jobjectArray>& p1,
+static void Java_MotionEvent_addBatchV_J_LAVMEPC_I(JNIEnv* env, jobject obj,
+    jlong p0,
+    jobjectArray p1,
     JniIntWrapper p2) __attribute__ ((unused));
-static void Java_MotionEvent_addBatchV_J_LAVMEPC_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jlong p0,
-    const base::android::JavaRefOrBare<jobjectArray>& p1,
+static void Java_MotionEvent_addBatchV_J_LAVMEPC_I(JNIEnv* env, jobject obj,
+    jlong p0,
+    jobjectArray p1,
     JniIntWrapper p2) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -2067,19 +2094,19 @@
       "(J[Landroid/view/MotionEvent$PointerCoords;I)V",
       &g_MotionEvent_addBatchV_J_LAVMEPC_I);
 
-     env->CallVoidMethod(obj.obj(),
-          method_id, p0, p1.obj(), as_jint(p2));
+     env->CallVoidMethod(obj,
+          method_id, p0, p1, as_jint(p2));
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_MotionEvent_toString = 0;
-static base::android::ScopedJavaLocalRef<jstring>
-    Java_MotionEvent_toString(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jstring>
-    Java_MotionEvent_toString(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static ScopedJavaLocalRef<jstring> Java_MotionEvent_toString(JNIEnv* env,
+    jobject obj) __attribute__ ((unused));
+static ScopedJavaLocalRef<jstring> Java_MotionEvent_toString(JNIEnv* env,
+    jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -2090,18 +2117,18 @@
       &g_MotionEvent_toString);
 
   jstring ret =
-      static_cast<jstring>(env->CallObjectMethod(obj.obj(),
+      static_cast<jstring>(env->CallObjectMethod(obj,
           method_id));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jstring>(env, ret);
+  return ScopedJavaLocalRef<jstring>(env, ret);
 }
 
 static base::subtle::AtomicWord g_MotionEvent_actionToString = 0;
-static base::android::ScopedJavaLocalRef<jstring>
-    Java_MotionEvent_actionToString(JNIEnv* env, JniIntWrapper p0) __attribute__
-    ((unused));
-static base::android::ScopedJavaLocalRef<jstring>
-    Java_MotionEvent_actionToString(JNIEnv* env, JniIntWrapper p0) {
+static ScopedJavaLocalRef<jstring> Java_MotionEvent_actionToString(JNIEnv* env,
+    JniIntWrapper p0) __attribute__ ((unused));
+static ScopedJavaLocalRef<jstring> Java_MotionEvent_actionToString(JNIEnv* env,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -2116,15 +2143,15 @@
       static_cast<jstring>(env->CallStaticObjectMethod(MotionEvent_clazz(env),
           method_id, as_jint(p0)));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jstring>(env, ret);
+  return ScopedJavaLocalRef<jstring>(env, ret);
 }
 
 static base::subtle::AtomicWord g_MotionEvent_axisToString = 0;
-static base::android::ScopedJavaLocalRef<jstring>
-    Java_MotionEvent_axisToString(JNIEnv* env, JniIntWrapper p0) __attribute__
-    ((unused));
-static base::android::ScopedJavaLocalRef<jstring>
-    Java_MotionEvent_axisToString(JNIEnv* env, JniIntWrapper p0) {
+static ScopedJavaLocalRef<jstring> Java_MotionEvent_axisToString(JNIEnv* env,
+    JniIntWrapper p0) __attribute__ ((unused));
+static ScopedJavaLocalRef<jstring> Java_MotionEvent_axisToString(JNIEnv* env,
+    JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), NULL);
   jmethodID method_id =
@@ -2139,14 +2166,14 @@
       static_cast<jstring>(env->CallStaticObjectMethod(MotionEvent_clazz(env),
           method_id, as_jint(p0)));
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jstring>(env, ret);
+  return ScopedJavaLocalRef<jstring>(env, ret);
 }
 
 static base::subtle::AtomicWord g_MotionEvent_axisFromString = 0;
-static jint Java_MotionEvent_axisFromString(JNIEnv* env, const
-    base::android::JavaRefOrBare<jstring>& p0) __attribute__ ((unused));
-static jint Java_MotionEvent_axisFromString(JNIEnv* env, const
-    base::android::JavaRefOrBare<jstring>& p0) {
+static jint Java_MotionEvent_axisFromString(JNIEnv* env, jstring p0)
+    __attribute__ ((unused));
+static jint Java_MotionEvent_axisFromString(JNIEnv* env, jstring p0) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, MotionEvent_clazz(env),
       MotionEvent_clazz(env), 0);
   jmethodID method_id =
@@ -2159,21 +2186,18 @@
 
   jint ret =
       env->CallStaticIntMethod(MotionEvent_clazz(env),
-          method_id, p0.obj());
+          method_id, p0);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_MotionEvent_writeToParcel = 0;
-static void Java_MotionEvent_writeToParcel(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, const
-    base::android::JavaRefOrBare<jobject>& p0,
+static void Java_MotionEvent_writeToParcel(JNIEnv* env, jobject obj, jobject p0,
     JniIntWrapper p1) __attribute__ ((unused));
-static void Java_MotionEvent_writeToParcel(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, const
-    base::android::JavaRefOrBare<jobject>& p0,
+static void Java_MotionEvent_writeToParcel(JNIEnv* env, jobject obj, jobject p0,
     JniIntWrapper p1) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       MotionEvent_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -2183,13 +2207,22 @@
       "(Landroid/os/Parcel;I)V",
       &g_MotionEvent_writeToParcel);
 
-     env->CallVoidMethod(obj.obj(),
-          method_id, p0.obj(), as_jint(p1));
+     env->CallVoidMethod(obj,
+          method_id, p0, as_jint(p1));
   jni_generator::CheckException(env);
+
 }
 
 // Step 3: RegisterNatives.
 
+static bool RegisterNativesImpl(JNIEnv* env) {
+
+  g_MotionEvent_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kMotionEventClassPath).obj()));
+
+  return true;
+}
+
 }  // namespace JNI_MotionEvent
 
 #endif  // android_view_MotionEvent_JNI
diff --git a/base/android/jni_generator/testFromJavaP.golden b/base/android/jni_generator/testFromJavaP.golden
index 18a9430..f32666c 100644
--- a/base/android/jni_generator/testFromJavaP.golden
+++ b/base/android/jni_generator/testFromJavaP.golden
@@ -20,8 +20,8 @@
 namespace {
 const char kInputStreamClassPath[] = "java/io/InputStream";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_InputStream_clazz __attribute__((unused)) = 0;
-#define InputStream_clazz(env) base::android::LazyGetClass(env, kInputStreamClassPath, &g_InputStream_clazz)
+jclass g_InputStream_clazz = NULL;
+#define InputStream_clazz(env) g_InputStream_clazz
 
 }  // namespace
 
@@ -30,11 +30,11 @@
 // Step 2: method stubs.
 
 static base::subtle::AtomicWord g_InputStream_available = 0;
-static jint Java_InputStream_available(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_InputStream_available(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_InputStream_available(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jint Java_InputStream_available(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -45,18 +45,18 @@
       &g_InputStream_available);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_InputStream_close = 0;
-static void Java_InputStream_close(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static void Java_InputStream_close(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_InputStream_close(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static void Java_InputStream_close(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -66,18 +66,18 @@
       "()V",
       &g_InputStream_close);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_InputStream_mark = 0;
-static void Java_InputStream_mark(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) __attribute__
-    ((unused));
-static void Java_InputStream_mark(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, JniIntWrapper p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_InputStream_mark(JNIEnv* env, jobject obj, JniIntWrapper p0)
+    __attribute__ ((unused));
+static void Java_InputStream_mark(JNIEnv* env, jobject obj, JniIntWrapper p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -87,17 +87,18 @@
       "(I)V",
       &g_InputStream_mark);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id, as_jint(p0));
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_InputStream_markSupported = 0;
-static jboolean Java_InputStream_markSupported(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jboolean Java_InputStream_markSupported(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jboolean Java_InputStream_markSupported(JNIEnv* env, jobject obj)
+    __attribute__ ((unused));
+static jboolean Java_InputStream_markSupported(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env), false);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -108,18 +109,18 @@
       &g_InputStream_markSupported);
 
   jboolean ret =
-      env->CallBooleanMethod(obj.obj(),
+      env->CallBooleanMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_InputStream_readI = 0;
-static jint Java_InputStream_readI(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static jint Java_InputStream_readI(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_InputStream_readI(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static jint Java_InputStream_readI(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -130,20 +131,18 @@
       &g_InputStream_readI);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
+      env->CallIntMethod(obj,
           method_id);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_InputStream_readI_AB = 0;
-static jint Java_InputStream_readI_AB(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, const
-    base::android::JavaRefOrBare<jbyteArray>& p0) __attribute__ ((unused));
-static jint Java_InputStream_readI_AB(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, const
-    base::android::JavaRefOrBare<jbyteArray>& p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jint Java_InputStream_readI_AB(JNIEnv* env, jobject obj, jbyteArray p0)
+    __attribute__ ((unused));
+static jint Java_InputStream_readI_AB(JNIEnv* env, jobject obj, jbyteArray p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -154,24 +153,23 @@
       &g_InputStream_readI_AB);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
-          method_id, p0.obj());
+      env->CallIntMethod(obj,
+          method_id, p0);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_InputStream_readI_AB_I_I = 0;
-static jint Java_InputStream_readI_AB_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, const
-    base::android::JavaRefOrBare<jbyteArray>& p0,
+static jint Java_InputStream_readI_AB_I_I(JNIEnv* env, jobject obj, jbyteArray
+    p0,
     JniIntWrapper p1,
     JniIntWrapper p2) __attribute__ ((unused));
-static jint Java_InputStream_readI_AB_I_I(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, const
-    base::android::JavaRefOrBare<jbyteArray>& p0,
+static jint Java_InputStream_readI_AB_I_I(JNIEnv* env, jobject obj, jbyteArray
+    p0,
     JniIntWrapper p1,
     JniIntWrapper p2) {
-  CHECK_CLAZZ(env, obj.obj(),
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -182,18 +180,18 @@
       &g_InputStream_readI_AB_I_I);
 
   jint ret =
-      env->CallIntMethod(obj.obj(),
-          method_id, p0.obj(), as_jint(p1), as_jint(p2));
+      env->CallIntMethod(obj,
+          method_id, p0, as_jint(p1), as_jint(p2));
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_InputStream_reset = 0;
-static void Java_InputStream_reset(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static void Java_InputStream_reset(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_InputStream_reset(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static void Java_InputStream_reset(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -203,18 +201,18 @@
       "()V",
       &g_InputStream_reset);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id);
   jni_generator::CheckException(env);
+
 }
 
 static base::subtle::AtomicWord g_InputStream_skip = 0;
-static jlong Java_InputStream_skip(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jlong p0) __attribute__
-    ((unused));
-static jlong Java_InputStream_skip(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj, jlong p0) {
-  CHECK_CLAZZ(env, obj.obj(),
+static jlong Java_InputStream_skip(JNIEnv* env, jobject obj, jlong p0)
+    __attribute__ ((unused));
+static jlong Java_InputStream_skip(JNIEnv* env, jobject obj, jlong p0) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       InputStream_clazz(env), 0);
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -225,17 +223,17 @@
       &g_InputStream_skip);
 
   jlong ret =
-      env->CallLongMethod(obj.obj(),
+      env->CallLongMethod(obj,
           method_id, p0);
   jni_generator::CheckException(env);
   return ret;
 }
 
 static base::subtle::AtomicWord g_InputStream_Constructor = 0;
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_InputStream_Constructor(JNIEnv* env) __attribute__ ((unused));
-static base::android::ScopedJavaLocalRef<jobject>
-    Java_InputStream_Constructor(JNIEnv* env) {
+static ScopedJavaLocalRef<jobject> Java_InputStream_Constructor(JNIEnv* env)
+    __attribute__ ((unused));
+static ScopedJavaLocalRef<jobject> Java_InputStream_Constructor(JNIEnv* env) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, InputStream_clazz(env),
       InputStream_clazz(env), NULL);
   jmethodID method_id =
@@ -250,11 +248,19 @@
       env->NewObject(InputStream_clazz(env),
           method_id);
   jni_generator::CheckException(env);
-  return base::android::ScopedJavaLocalRef<jobject>(env, ret);
+  return ScopedJavaLocalRef<jobject>(env, ret);
 }
 
 // Step 3: RegisterNatives.
 
+static bool RegisterNativesImpl(JNIEnv* env) {
+
+  g_InputStream_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kInputStreamClassPath).obj()));
+
+  return true;
+}
+
 }  // namespace JNI_InputStream
 
 #endif  // java_io_InputStream_JNI
diff --git a/base/android/jni_generator/testFromJavaPGenerics.golden b/base/android/jni_generator/testFromJavaPGenerics.golden
index c076c39..489872c 100644
--- a/base/android/jni_generator/testFromJavaPGenerics.golden
+++ b/base/android/jni_generator/testFromJavaPGenerics.golden
@@ -20,8 +20,8 @@
 namespace {
 const char kHashSetClassPath[] = "java/util/HashSet";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_HashSet_clazz __attribute__((unused)) = 0;
-#define HashSet_clazz(env) base::android::LazyGetClass(env, kHashSetClassPath, &g_HashSet_clazz)
+jclass g_HashSet_clazz = NULL;
+#define HashSet_clazz(env) g_HashSet_clazz
 
 }  // namespace
 
@@ -30,11 +30,11 @@
 // Step 2: method stubs.
 
 static base::subtle::AtomicWord g_HashSet_dummy = 0;
-static void Java_HashSet_dummy(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) __attribute__ ((unused));
-static void Java_HashSet_dummy(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& obj) {
-  CHECK_CLAZZ(env, obj.obj(),
+static void Java_HashSet_dummy(JNIEnv* env, jobject obj) __attribute__
+    ((unused));
+static void Java_HashSet_dummy(JNIEnv* env, jobject obj) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
       HashSet_clazz(env));
   jmethodID method_id =
       base::android::MethodID::LazyGet<
@@ -44,13 +44,22 @@
       "()V",
       &g_HashSet_dummy);
 
-     env->CallVoidMethod(obj.obj(),
+     env->CallVoidMethod(obj,
           method_id);
   jni_generator::CheckException(env);
+
 }
 
 // Step 3: RegisterNatives.
 
+static bool RegisterNativesImpl(JNIEnv* env) {
+
+  g_HashSet_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kHashSetClassPath).obj()));
+
+  return true;
+}
+
 }  // namespace JNI_HashSet
 
 #endif  // java_util_HashSet_JNI
diff --git a/base/android/jni_generator/testInnerClassNatives.golden b/base/android/jni_generator/testInnerClassNatives.golden
index 20b8830..ad140e2 100644
--- a/base/android/jni_generator/testInnerClassNatives.golden
+++ b/base/android/jni_generator/testInnerClassNatives.golden
@@ -21,23 +21,18 @@
 const char kTestJniClassPath[] = "org/chromium/TestJni";
 const char kMyInnerClassClassPath[] = "org/chromium/TestJni$MyInnerClass";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_TestJni_clazz __attribute__((unused)) = 0;
-#define TestJni_clazz(env) base::android::LazyGetClass(env, kTestJniClassPath, &g_TestJni_clazz)
-// Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_MyInnerClass_clazz __attribute__((unused)) = 0;
-#define MyInnerClass_clazz(env) base::android::LazyGetClass(env, kMyInnerClassClassPath, &g_MyInnerClass_clazz)
+jclass g_TestJni_clazz = NULL;
+#define TestJni_clazz(env) g_TestJni_clazz
 
 }  // namespace
 
 // Step 2: method stubs.
 
-static jint Init(JNIEnv* env, const base::android::JavaParamRef<jobject>&
-    jcaller);
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
 
-JNI_GENERATOR_EXPORT jint
-    Java_org_chromium_TestJni_00024MyInnerClass_nativeInit(JNIEnv* env, jobject
-    jcaller) {
-  return Init(env, base::android::JavaParamRef<jobject>(env, jcaller));
+static jint Java_org_chromium_TestJni_00024MyInnerClass_nativeInit(JNIEnv* env,
+    jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
 }
 
 // Step 3: RegisterNatives.
@@ -52,8 +47,9 @@
 };
 
 static bool RegisterNativesImpl(JNIEnv* env) {
-  if (jni_generator::ShouldSkipJniRegistration(false))
-    return true;
+
+  g_TestJni_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kTestJniClassPath).obj()));
 
   const int kMethodsMyInnerClassSize = arraysize(kMethodsMyInnerClass);
 
diff --git a/base/android/jni_generator/testInnerClassNativesBothInnerAndOuter.golden b/base/android/jni_generator/testInnerClassNativesBothInnerAndOuter.golden
index 67352e7..0a890e7 100644
--- a/base/android/jni_generator/testInnerClassNativesBothInnerAndOuter.golden
+++ b/base/android/jni_generator/testInnerClassNativesBothInnerAndOuter.golden
@@ -22,31 +22,24 @@
     "org/chromium/TestJni$MyOtherInnerClass";
 const char kTestJniClassPath[] = "org/chromium/TestJni";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_MyOtherInnerClass_clazz __attribute__((unused)) = 0;
-#define MyOtherInnerClass_clazz(env) base::android::LazyGetClass(env, kMyOtherInnerClassClassPath, &g_MyOtherInnerClass_clazz)
-// Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_TestJni_clazz __attribute__((unused)) = 0;
-#define TestJni_clazz(env) base::android::LazyGetClass(env, kTestJniClassPath, &g_TestJni_clazz)
+jclass g_TestJni_clazz = NULL;
+#define TestJni_clazz(env) g_TestJni_clazz
 
 }  // namespace
 
 // Step 2: method stubs.
 
-static jint Init(JNIEnv* env, const base::android::JavaParamRef<jobject>&
-    jcaller);
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
 
-JNI_GENERATOR_EXPORT jint Java_org_chromium_TestJni_nativeInit(JNIEnv* env,
-    jobject jcaller) {
-  return Init(env, base::android::JavaParamRef<jobject>(env, jcaller));
+static jint Java_org_chromium_TestJni_nativeInit(JNIEnv* env, jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
 }
 
-static jint Init(JNIEnv* env, const base::android::JavaParamRef<jobject>&
-    jcaller);
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
 
-JNI_GENERATOR_EXPORT jint
-    Java_org_chromium_TestJni_00024MyOtherInnerClass_nativeInit(JNIEnv* env,
-    jobject jcaller) {
-  return Init(env, base::android::JavaParamRef<jobject>(env, jcaller));
+static jint Java_org_chromium_TestJni_00024MyOtherInnerClass_nativeInit(JNIEnv*
+    env, jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
 }
 
 // Step 3: RegisterNatives.
@@ -68,8 +61,9 @@
 };
 
 static bool RegisterNativesImpl(JNIEnv* env) {
-  if (jni_generator::ShouldSkipJniRegistration(false))
-    return true;
+
+  g_TestJni_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kTestJniClassPath).obj()));
 
   const int kMethodsMyOtherInnerClassSize =
       arraysize(kMethodsMyOtherInnerClass);
diff --git a/base/android/jni_generator/testInnerClassNativesMultiple.golden b/base/android/jni_generator/testInnerClassNativesMultiple.golden
index 7807efa..268f794 100644
--- a/base/android/jni_generator/testInnerClassNativesMultiple.golden
+++ b/base/android/jni_generator/testInnerClassNativesMultiple.golden
@@ -23,35 +23,25 @@
 const char kTestJniClassPath[] = "org/chromium/TestJni";
 const char kMyInnerClassClassPath[] = "org/chromium/TestJni$MyInnerClass";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_MyOtherInnerClass_clazz __attribute__((unused)) = 0;
-#define MyOtherInnerClass_clazz(env) base::android::LazyGetClass(env, kMyOtherInnerClassClassPath, &g_MyOtherInnerClass_clazz)
-// Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_TestJni_clazz __attribute__((unused)) = 0;
-#define TestJni_clazz(env) base::android::LazyGetClass(env, kTestJniClassPath, &g_TestJni_clazz)
-// Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_MyInnerClass_clazz __attribute__((unused)) = 0;
-#define MyInnerClass_clazz(env) base::android::LazyGetClass(env, kMyInnerClassClassPath, &g_MyInnerClass_clazz)
+jclass g_TestJni_clazz = NULL;
+#define TestJni_clazz(env) g_TestJni_clazz
 
 }  // namespace
 
 // Step 2: method stubs.
 
-static jint Init(JNIEnv* env, const base::android::JavaParamRef<jobject>&
-    jcaller);
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
 
-JNI_GENERATOR_EXPORT jint
-    Java_org_chromium_TestJni_00024MyInnerClass_nativeInit(JNIEnv* env, jobject
-    jcaller) {
-  return Init(env, base::android::JavaParamRef<jobject>(env, jcaller));
+static jint Java_org_chromium_TestJni_00024MyInnerClass_nativeInit(JNIEnv* env,
+    jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
 }
 
-static jint Init(JNIEnv* env, const base::android::JavaParamRef<jobject>&
-    jcaller);
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
 
-JNI_GENERATOR_EXPORT jint
-    Java_org_chromium_TestJni_00024MyOtherInnerClass_nativeInit(JNIEnv* env,
-    jobject jcaller) {
-  return Init(env, base::android::JavaParamRef<jobject>(env, jcaller));
+static jint Java_org_chromium_TestJni_00024MyOtherInnerClass_nativeInit(JNIEnv*
+    env, jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
 }
 
 // Step 3: RegisterNatives.
@@ -75,8 +65,9 @@
 };
 
 static bool RegisterNativesImpl(JNIEnv* env) {
-  if (jni_generator::ShouldSkipJniRegistration(false))
-    return true;
+
+  g_TestJni_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kTestJniClassPath).obj()));
 
   const int kMethodsMyOtherInnerClassSize =
       arraysize(kMethodsMyOtherInnerClass);
diff --git a/base/android/jni_generator/testMultipleJNIAdditionalImport.golden b/base/android/jni_generator/testMultipleJNIAdditionalImport.golden
index 0eecb5a..6de8c21 100644
--- a/base/android/jni_generator/testMultipleJNIAdditionalImport.golden
+++ b/base/android/jni_generator/testMultipleJNIAdditionalImport.golden
@@ -20,31 +20,30 @@
 namespace {
 const char kFooClassPath[] = "org/chromium/foo/Foo";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_Foo_clazz __attribute__((unused)) = 0;
-#define Foo_clazz(env) base::android::LazyGetClass(env, kFooClassPath, &g_Foo_clazz)
+jclass g_Foo_clazz = NULL;
+#define Foo_clazz(env) g_Foo_clazz
 
 }  // namespace
 
 // Step 2: method stubs.
 
-static void DoSomething(JNIEnv* env, const base::android::JavaParamRef<jclass>&
-    jcaller,
-    const base::android::JavaParamRef<jobject>& callback1,
-    const base::android::JavaParamRef<jobject>& callback2);
+static void DoSomething(JNIEnv* env, const JavaParamRef<jclass>& jcaller,
+    const JavaParamRef<jobject>& callback1,
+    const JavaParamRef<jobject>& callback2);
 
-JNI_GENERATOR_EXPORT void Java_org_chromium_foo_Foo_nativeDoSomething(JNIEnv*
-    env, jclass jcaller,
+static void Java_org_chromium_foo_Foo_nativeDoSomething(JNIEnv* env, jclass
+    jcaller,
     jobject callback1,
     jobject callback2) {
-  return DoSomething(env, base::android::JavaParamRef<jclass>(env, jcaller),
-      base::android::JavaParamRef<jobject>(env, callback1),
-      base::android::JavaParamRef<jobject>(env, callback2));
+  return DoSomething(env, JavaParamRef<jclass>(env, jcaller),
+      JavaParamRef<jobject>(env, callback1), JavaParamRef<jobject>(env,
+      callback2));
 }
 
 static base::subtle::AtomicWord g_Foo_calledByNative = 0;
-static void Java_Foo_calledByNative(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& callback1,
-    const base::android::JavaRefOrBare<jobject>& callback2) {
+static void Java_Foo_calledByNative(JNIEnv* env, jobject callback1,
+    jobject callback2) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, Foo_clazz(env),
       Foo_clazz(env));
   jmethodID method_id =
@@ -52,6 +51,7 @@
       base::android::MethodID::TYPE_STATIC>(
       env, Foo_clazz(env),
       "calledByNative",
+
 "("
 "Lorg/chromium/foo/Bar1$Callback;"
 "Lorg/chromium/foo/Bar2$Callback;"
@@ -60,8 +60,9 @@
       &g_Foo_calledByNative);
 
      env->CallStaticVoidMethod(Foo_clazz(env),
-          method_id, callback1.obj(), callback2.obj());
+          method_id, callback1, callback2);
   jni_generator::CheckException(env);
+
 }
 
 // Step 3: RegisterNatives.
@@ -76,8 +77,9 @@
 };
 
 static bool RegisterNativesImpl(JNIEnv* env) {
-  if (jni_generator::ShouldSkipJniRegistration(false))
-    return true;
+
+  g_Foo_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kFooClassPath).obj()));
 
   const int kMethodsFooSize = arraysize(kMethodsFoo);
 
diff --git a/base/android/jni_generator/testNativeExportsOption.golden b/base/android/jni_generator/testNativeExportsOption.golden
new file mode 100644
index 0000000..2c89e3b
--- /dev/null
+++ b/base/android/jni_generator/testNativeExportsOption.golden
@@ -0,0 +1,203 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This file is autogenerated by
+//     base/android/jni_generator/jni_generator.py
+// For
+//     org/chromium/example/jni_generator/SampleForTests
+
+#ifndef org_chromium_example_jni_generator_SampleForTests_JNI
+#define org_chromium_example_jni_generator_SampleForTests_JNI
+
+#include <jni.h>
+
+#include "base/android/jni_generator/jni_generator_helper.h"
+
+#include "base/android/jni_int_wrapper.h"
+
+// Step 1: forward declarations.
+namespace {
+const char kSampleForTestsClassPath[] =
+    "org/chromium/example/jni_generator/SampleForTests";
+// Leaking this jclass as we cannot use LazyInstance from some threads.
+base::subtle::AtomicWord g_SampleForTests_clazz __attribute__((unused)) = 0;
+#define SampleForTests_clazz(env) base::android::LazyGetClass(env, kSampleForTestsClassPath, &g_SampleForTests_clazz)
+
+}  // namespace
+
+// Step 2: method stubs.
+extern "C" __attribute__((visibility("default")))
+jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeStaticMethod(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeTest,
+    jint arg1) {
+  Test* native = reinterpret_cast<Test*>(nativeTest);
+  CHECK_NATIVE_PTR(env, jcaller, native, "StaticMethod", 0);
+  return native->StaticMethod(env, JavaParamRef<jobject>(env, jcaller), arg1);
+}
+
+extern "C" __attribute__((visibility("default")))
+jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeMethod(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeTest,
+    jint arg1) {
+  Test* native = reinterpret_cast<Test*>(nativeTest);
+  CHECK_NATIVE_PTR(env, jcaller, native, "Method", 0);
+  return native->Method(env, JavaParamRef<jobject>(env, jcaller), arg1);
+}
+
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
+
+extern "C" __attribute__((visibility("default")))
+jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_00024MyInnerClass_nativeInit(JNIEnv*
+    env, jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
+}
+
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
+
+extern "C" __attribute__((visibility("default")))
+jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_00024MyOtherInnerClass_nativeInit(JNIEnv*
+    env, jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testMethodWithParam = 0;
+static void Java_SampleForTests_testMethodWithParam(JNIEnv* env, jobject obj,
+    JniIntWrapper iParam) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env));
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "testMethodWithParam",
+
+"("
+"I"
+")"
+"V",
+      &g_SampleForTests_testMethodWithParam);
+
+     env->CallVoidMethod(obj,
+          method_id, as_jint(iParam));
+  jni_generator::CheckException(env);
+
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testMethodWithParamAndReturn =
+    0;
+static ScopedJavaLocalRef<jstring>
+    Java_SampleForTests_testMethodWithParamAndReturn(JNIEnv* env, jobject obj,
+    JniIntWrapper iParam) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env), NULL);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "testMethodWithParamAndReturn",
+
+"("
+"I"
+")"
+"Ljava/lang/String;",
+      &g_SampleForTests_testMethodWithParamAndReturn);
+
+  jstring ret =
+      static_cast<jstring>(env->CallObjectMethod(obj,
+          method_id, as_jint(iParam)));
+  jni_generator::CheckException(env);
+  return ScopedJavaLocalRef<jstring>(env, ret);
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testStaticMethodWithParam = 0;
+static jint Java_SampleForTests_testStaticMethodWithParam(JNIEnv* env,
+    JniIntWrapper iParam) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, SampleForTests_clazz(env),
+      SampleForTests_clazz(env), 0);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_STATIC>(
+      env, SampleForTests_clazz(env),
+      "testStaticMethodWithParam",
+
+"("
+"I"
+")"
+"I",
+      &g_SampleForTests_testStaticMethodWithParam);
+
+  jint ret =
+      env->CallStaticIntMethod(SampleForTests_clazz(env),
+          method_id, as_jint(iParam));
+  jni_generator::CheckException(env);
+  return ret;
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testMethodWithNoParam = 0;
+static jdouble Java_SampleForTests_testMethodWithNoParam(JNIEnv* env) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, SampleForTests_clazz(env),
+      SampleForTests_clazz(env), 0);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_STATIC>(
+      env, SampleForTests_clazz(env),
+      "testMethodWithNoParam",
+
+"("
+")"
+"D",
+      &g_SampleForTests_testMethodWithNoParam);
+
+  jdouble ret =
+      env->CallStaticDoubleMethod(SampleForTests_clazz(env),
+          method_id);
+  jni_generator::CheckException(env);
+  return ret;
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testStaticMethodWithNoParam =
+    0;
+static ScopedJavaLocalRef<jstring>
+    Java_SampleForTests_testStaticMethodWithNoParam(JNIEnv* env) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, SampleForTests_clazz(env),
+      SampleForTests_clazz(env), NULL);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_STATIC>(
+      env, SampleForTests_clazz(env),
+      "testStaticMethodWithNoParam",
+
+"("
+")"
+"Ljava/lang/String;",
+      &g_SampleForTests_testStaticMethodWithNoParam);
+
+  jstring ret =
+static_cast<jstring>(env->CallStaticObjectMethod(SampleForTests_clazz(env),
+          method_id));
+  jni_generator::CheckException(env);
+  return ScopedJavaLocalRef<jstring>(env, ret);
+}
+
+// Step 3: RegisterNatives.
+
+static bool RegisterNativesImpl(JNIEnv* env) {
+
+  return true;
+}
+
+#endif  // org_chromium_example_jni_generator_SampleForTests_JNI
diff --git a/base/android/jni_generator/testNativeExportsOptionalOption.golden b/base/android/jni_generator/testNativeExportsOptionalOption.golden
new file mode 100644
index 0000000..03484c9
--- /dev/null
+++ b/base/android/jni_generator/testNativeExportsOptionalOption.golden
@@ -0,0 +1,272 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This file is autogenerated by
+//     base/android/jni_generator/jni_generator.py
+// For
+//     org/chromium/example/jni_generator/SampleForTests
+
+#ifndef org_chromium_example_jni_generator_SampleForTests_JNI
+#define org_chromium_example_jni_generator_SampleForTests_JNI
+
+#include <jni.h>
+
+#include "base/android/jni_generator/jni_generator_helper.h"
+
+#include "base/android/jni_int_wrapper.h"
+
+// Step 1: forward declarations.
+namespace {
+const char kSampleForTestsClassPath[] =
+    "org/chromium/example/jni_generator/SampleForTests";
+// Leaking this jclass as we cannot use LazyInstance from some threads.
+base::subtle::AtomicWord g_SampleForTests_clazz __attribute__((unused)) = 0;
+#define SampleForTests_clazz(env) base::android::LazyGetClass(env, kSampleForTestsClassPath, &g_SampleForTests_clazz)
+
+}  // namespace
+
+// Step 2: method stubs.
+extern "C" __attribute__((visibility("default")))
+jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeStaticMethod(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeTest,
+    jint arg1) {
+  Test* native = reinterpret_cast<Test*>(nativeTest);
+  CHECK_NATIVE_PTR(env, jcaller, native, "StaticMethod", 0);
+  return native->StaticMethod(env, JavaParamRef<jobject>(env, jcaller), arg1);
+}
+
+extern "C" __attribute__((visibility("default")))
+jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_nativeMethod(JNIEnv*
+    env,
+    jobject jcaller,
+    jlong nativeTest,
+    jint arg1) {
+  Test* native = reinterpret_cast<Test*>(nativeTest);
+  CHECK_NATIVE_PTR(env, jcaller, native, "Method", 0);
+  return native->Method(env, JavaParamRef<jobject>(env, jcaller), arg1);
+}
+
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
+
+extern "C" __attribute__((visibility("default")))
+jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_00024MyInnerClass_nativeInit(JNIEnv*
+    env, jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
+}
+
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
+
+extern "C" __attribute__((visibility("default")))
+jint
+    Java_org_chromium_example_jni_1generator_SampleForTests_00024MyOtherInnerClass_nativeInit(JNIEnv*
+    env, jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testMethodWithParam = 0;
+static void Java_SampleForTests_testMethodWithParam(JNIEnv* env, jobject obj,
+    JniIntWrapper iParam) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env));
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "testMethodWithParam",
+
+"("
+"I"
+")"
+"V",
+      &g_SampleForTests_testMethodWithParam);
+
+     env->CallVoidMethod(obj,
+          method_id, as_jint(iParam));
+  jni_generator::CheckException(env);
+
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testMethodWithParamAndReturn =
+    0;
+static ScopedJavaLocalRef<jstring>
+    Java_SampleForTests_testMethodWithParamAndReturn(JNIEnv* env, jobject obj,
+    JniIntWrapper iParam) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, obj,
+      SampleForTests_clazz(env), NULL);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_INSTANCE>(
+      env, SampleForTests_clazz(env),
+      "testMethodWithParamAndReturn",
+
+"("
+"I"
+")"
+"Ljava/lang/String;",
+      &g_SampleForTests_testMethodWithParamAndReturn);
+
+  jstring ret =
+      static_cast<jstring>(env->CallObjectMethod(obj,
+          method_id, as_jint(iParam)));
+  jni_generator::CheckException(env);
+  return ScopedJavaLocalRef<jstring>(env, ret);
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testStaticMethodWithParam = 0;
+static jint Java_SampleForTests_testStaticMethodWithParam(JNIEnv* env,
+    JniIntWrapper iParam) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, SampleForTests_clazz(env),
+      SampleForTests_clazz(env), 0);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_STATIC>(
+      env, SampleForTests_clazz(env),
+      "testStaticMethodWithParam",
+
+"("
+"I"
+")"
+"I",
+      &g_SampleForTests_testStaticMethodWithParam);
+
+  jint ret =
+      env->CallStaticIntMethod(SampleForTests_clazz(env),
+          method_id, as_jint(iParam));
+  jni_generator::CheckException(env);
+  return ret;
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testMethodWithNoParam = 0;
+static jdouble Java_SampleForTests_testMethodWithNoParam(JNIEnv* env) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, SampleForTests_clazz(env),
+      SampleForTests_clazz(env), 0);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_STATIC>(
+      env, SampleForTests_clazz(env),
+      "testMethodWithNoParam",
+
+"("
+")"
+"D",
+      &g_SampleForTests_testMethodWithNoParam);
+
+  jdouble ret =
+      env->CallStaticDoubleMethod(SampleForTests_clazz(env),
+          method_id);
+  jni_generator::CheckException(env);
+  return ret;
+}
+
+static base::subtle::AtomicWord g_SampleForTests_testStaticMethodWithNoParam =
+    0;
+static ScopedJavaLocalRef<jstring>
+    Java_SampleForTests_testStaticMethodWithNoParam(JNIEnv* env) {
+  /* Must call RegisterNativesImpl()  */
+  CHECK_CLAZZ(env, SampleForTests_clazz(env),
+      SampleForTests_clazz(env), NULL);
+  jmethodID method_id =
+      base::android::MethodID::LazyGet<
+      base::android::MethodID::TYPE_STATIC>(
+      env, SampleForTests_clazz(env),
+      "testStaticMethodWithNoParam",
+
+"("
+")"
+"Ljava/lang/String;",
+      &g_SampleForTests_testStaticMethodWithNoParam);
+
+  jstring ret =
+static_cast<jstring>(env->CallStaticObjectMethod(SampleForTests_clazz(env),
+          method_id));
+  jni_generator::CheckException(env);
+  return ScopedJavaLocalRef<jstring>(env, ret);
+}
+
+// Step 3: RegisterNatives.
+
+static const JNINativeMethod kMethodsMyOtherInnerClass[] = {
+    { "nativeInit",
+"("
+")"
+"I",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_00024MyOtherInnerClass_nativeInit)
+    },
+};
+
+static const JNINativeMethod kMethodsMyInnerClass[] = {
+    { "nativeInit",
+"("
+")"
+"I",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_00024MyInnerClass_nativeInit)
+    },
+};
+
+static const JNINativeMethod kMethodsSampleForTests[] = {
+    { "nativeStaticMethod",
+"("
+"J"
+"I"
+")"
+"I",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeStaticMethod)
+    },
+    { "nativeMethod",
+"("
+"J"
+"I"
+")"
+"I",
+    reinterpret_cast<void*>(Java_org_chromium_example_jni_1generator_SampleForTests_nativeMethod)
+    },
+};
+
+static bool RegisterNativesImpl(JNIEnv* env) {
+  if (base::android::IsManualJniRegistrationDisabled()) return true;
+
+  const int kMethodsMyOtherInnerClassSize =
+      arraysize(kMethodsMyOtherInnerClass);
+
+  if (env->RegisterNatives(MyOtherInnerClass_clazz(env),
+                           kMethodsMyOtherInnerClass,
+                           kMethodsMyOtherInnerClassSize) < 0) {
+    jni_generator::HandleRegistrationError(
+        env, MyOtherInnerClass_clazz(env), __FILE__);
+    return false;
+  }
+
+  const int kMethodsMyInnerClassSize = arraysize(kMethodsMyInnerClass);
+
+  if (env->RegisterNatives(MyInnerClass_clazz(env),
+                           kMethodsMyInnerClass,
+                           kMethodsMyInnerClassSize) < 0) {
+    jni_generator::HandleRegistrationError(
+        env, MyInnerClass_clazz(env), __FILE__);
+    return false;
+  }
+
+  const int kMethodsSampleForTestsSize = arraysize(kMethodsSampleForTests);
+
+  if (env->RegisterNatives(SampleForTests_clazz(env),
+                           kMethodsSampleForTests,
+                           kMethodsSampleForTestsSize) < 0) {
+    jni_generator::HandleRegistrationError(
+        env, SampleForTests_clazz(env), __FILE__);
+    return false;
+  }
+
+  return true;
+}
+
+#endif  // org_chromium_example_jni_generator_SampleForTests_JNI
diff --git a/base/android/jni_generator/testNatives.golden b/base/android/jni_generator/testNatives.golden
index 3362c92..f9538a3 100644
--- a/base/android/jni_generator/testNatives.golden
+++ b/base/android/jni_generator/testNatives.golden
@@ -20,33 +20,30 @@
 namespace {
 const char kTestJniClassPath[] = "org/chromium/TestJni";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_TestJni_clazz __attribute__((unused)) = 0;
-#define TestJni_clazz(env) base::android::LazyGetClass(env, kTestJniClassPath, &g_TestJni_clazz)
+jclass g_TestJni_clazz = NULL;
+#define TestJni_clazz(env) g_TestJni_clazz
 
 }  // namespace
 
 // Step 2: method stubs.
 
-static jint Init(JNIEnv* env, const base::android::JavaParamRef<jobject>&
-    jcaller);
+static jint Init(JNIEnv* env, const JavaParamRef<jobject>& jcaller);
 
-JNI_GENERATOR_EXPORT jint Java_org_chromium_TestJni_nativeInit(JNIEnv* env,
-    jobject jcaller) {
-  return Init(env, base::android::JavaParamRef<jobject>(env, jcaller));
+static jint Java_org_chromium_TestJni_nativeInit(JNIEnv* env, jobject jcaller) {
+  return Init(env, JavaParamRef<jobject>(env, jcaller));
 }
 
-JNI_GENERATOR_EXPORT void Java_org_chromium_TestJni_nativeDestroy(JNIEnv* env,
+static void Java_org_chromium_TestJni_nativeDestroy(JNIEnv* env,
     jobject jcaller,
     jint nativeChromeBrowserProvider) {
   ChromeBrowserProvider* native =
       reinterpret_cast<ChromeBrowserProvider*>(nativeChromeBrowserProvider);
   CHECK_NATIVE_PTR(env, jcaller, native, "Destroy");
-  return native->Destroy(env, base::android::JavaParamRef<jobject>(env,
-      jcaller));
+  return native->Destroy(env, JavaParamRef<jobject>(env, jcaller));
 }
 
-JNI_GENERATOR_EXPORT jlong Java_org_chromium_TestJni_nativeAddBookmark(JNIEnv*
-    env, jobject jcaller,
+static jlong Java_org_chromium_TestJni_nativeAddBookmark(JNIEnv* env,
+    jobject jcaller,
     jint nativeChromeBrowserProvider,
     jstring url,
     jstring title,
@@ -55,79 +52,71 @@
   ChromeBrowserProvider* native =
       reinterpret_cast<ChromeBrowserProvider*>(nativeChromeBrowserProvider);
   CHECK_NATIVE_PTR(env, jcaller, native, "AddBookmark", 0);
-  return native->AddBookmark(env, base::android::JavaParamRef<jobject>(env,
-      jcaller), base::android::JavaParamRef<jstring>(env, url),
-      base::android::JavaParamRef<jstring>(env, title), isFolder, parentId);
+  return native->AddBookmark(env, JavaParamRef<jobject>(env, jcaller),
+      JavaParamRef<jstring>(env, url), JavaParamRef<jstring>(env, title),
+      isFolder, parentId);
 }
 
-static base::android::ScopedJavaLocalRef<jstring> GetDomainAndRegistry(JNIEnv*
-    env, const base::android::JavaParamRef<jclass>& jcaller,
-    const base::android::JavaParamRef<jstring>& url);
+static ScopedJavaLocalRef<jstring> GetDomainAndRegistry(JNIEnv* env, const
+    JavaParamRef<jclass>& jcaller,
+    const JavaParamRef<jstring>& url);
 
-JNI_GENERATOR_EXPORT jstring
-    Java_org_chromium_TestJni_nativeGetDomainAndRegistry(JNIEnv* env, jclass
-    jcaller,
+static jstring Java_org_chromium_TestJni_nativeGetDomainAndRegistry(JNIEnv* env,
+    jclass jcaller,
     jstring url) {
-  return GetDomainAndRegistry(env, base::android::JavaParamRef<jclass>(env,
-      jcaller), base::android::JavaParamRef<jstring>(env, url)).Release();
+  return GetDomainAndRegistry(env, JavaParamRef<jclass>(env, jcaller),
+      JavaParamRef<jstring>(env, url)).Release();
 }
 
 static void CreateHistoricalTabFromState(JNIEnv* env, const
-    base::android::JavaParamRef<jclass>& jcaller,
-    const base::android::JavaParamRef<jbyteArray>& state,
+    JavaParamRef<jclass>& jcaller,
+    const JavaParamRef<jbyteArray>& state,
     jint tab_index);
 
-JNI_GENERATOR_EXPORT void
-    Java_org_chromium_TestJni_nativeCreateHistoricalTabFromState(JNIEnv* env,
-    jclass jcaller,
+static void Java_org_chromium_TestJni_nativeCreateHistoricalTabFromState(JNIEnv*
+    env, jclass jcaller,
     jbyteArray state,
     jint tab_index) {
-  return CreateHistoricalTabFromState(env,
-      base::android::JavaParamRef<jclass>(env, jcaller),
-      base::android::JavaParamRef<jbyteArray>(env, state), tab_index);
+  return CreateHistoricalTabFromState(env, JavaParamRef<jclass>(env, jcaller),
+      JavaParamRef<jbyteArray>(env, state), tab_index);
 }
 
-static base::android::ScopedJavaLocalRef<jbyteArray> GetStateAsByteArray(JNIEnv*
-    env, const base::android::JavaParamRef<jobject>& jcaller,
-    const base::android::JavaParamRef<jobject>& view);
+static ScopedJavaLocalRef<jbyteArray> GetStateAsByteArray(JNIEnv* env, const
+    JavaParamRef<jobject>& jcaller,
+    const JavaParamRef<jobject>& view);
 
-JNI_GENERATOR_EXPORT jbyteArray
-    Java_org_chromium_TestJni_nativeGetStateAsByteArray(JNIEnv* env, jobject
-    jcaller,
+static jbyteArray Java_org_chromium_TestJni_nativeGetStateAsByteArray(JNIEnv*
+    env, jobject jcaller,
     jobject view) {
-  return GetStateAsByteArray(env, base::android::JavaParamRef<jobject>(env,
-      jcaller), base::android::JavaParamRef<jobject>(env, view)).Release();
+  return GetStateAsByteArray(env, JavaParamRef<jobject>(env, jcaller),
+      JavaParamRef<jobject>(env, view)).Release();
 }
 
-static base::android::ScopedJavaLocalRef<jobjectArray>
-    GetAutofillProfileGUIDs(JNIEnv* env, const
-    base::android::JavaParamRef<jclass>& jcaller);
+static ScopedJavaLocalRef<jobjectArray> GetAutofillProfileGUIDs(JNIEnv* env,
+    const JavaParamRef<jclass>& jcaller);
 
-JNI_GENERATOR_EXPORT jobjectArray
+static jobjectArray
     Java_org_chromium_TestJni_nativeGetAutofillProfileGUIDs(JNIEnv* env, jclass
     jcaller) {
-  return GetAutofillProfileGUIDs(env, base::android::JavaParamRef<jclass>(env,
+  return GetAutofillProfileGUIDs(env, JavaParamRef<jclass>(env,
       jcaller)).Release();
 }
 
-static void SetRecognitionResults(JNIEnv* env, const
-    base::android::JavaParamRef<jobject>& jcaller,
-    jint sessionId,
-    const base::android::JavaParamRef<jobjectArray>& results);
-
-JNI_GENERATOR_EXPORT void
-    Java_org_chromium_TestJni_nativeSetRecognitionResults(JNIEnv* env, jobject
+static void SetRecognitionResults(JNIEnv* env, const JavaParamRef<jobject>&
     jcaller,
     jint sessionId,
+    const JavaParamRef<jobjectArray>& results);
+
+static void Java_org_chromium_TestJni_nativeSetRecognitionResults(JNIEnv* env,
+    jobject jcaller,
+    jint sessionId,
     jobjectArray results) {
-  return SetRecognitionResults(env, base::android::JavaParamRef<jobject>(env,
-      jcaller), sessionId, base::android::JavaParamRef<jobjectArray>(env,
-      results));
+  return SetRecognitionResults(env, JavaParamRef<jobject>(env, jcaller),
+      sessionId, JavaParamRef<jobjectArray>(env, results));
 }
 
-JNI_GENERATOR_EXPORT jlong
-    Java_org_chromium_TestJni_nativeAddBookmarkFromAPI(JNIEnv* env, jobject
-    jcaller,
+static jlong Java_org_chromium_TestJni_nativeAddBookmarkFromAPI(JNIEnv* env,
+    jobject jcaller,
     jint nativeChromeBrowserProvider,
     jstring url,
     jobject created,
@@ -139,39 +128,33 @@
   ChromeBrowserProvider* native =
       reinterpret_cast<ChromeBrowserProvider*>(nativeChromeBrowserProvider);
   CHECK_NATIVE_PTR(env, jcaller, native, "AddBookmarkFromAPI", 0);
-  return native->AddBookmarkFromAPI(env,
-      base::android::JavaParamRef<jobject>(env, jcaller),
-      base::android::JavaParamRef<jstring>(env, url),
-      base::android::JavaParamRef<jobject>(env, created),
-      base::android::JavaParamRef<jobject>(env, isBookmark),
-      base::android::JavaParamRef<jobject>(env, date),
-      base::android::JavaParamRef<jbyteArray>(env, favicon),
-      base::android::JavaParamRef<jstring>(env, title),
-      base::android::JavaParamRef<jobject>(env, visits));
+  return native->AddBookmarkFromAPI(env, JavaParamRef<jobject>(env, jcaller),
+      JavaParamRef<jstring>(env, url), JavaParamRef<jobject>(env, created),
+      JavaParamRef<jobject>(env, isBookmark), JavaParamRef<jobject>(env, date),
+      JavaParamRef<jbyteArray>(env, favicon), JavaParamRef<jstring>(env, title),
+      JavaParamRef<jobject>(env, visits));
 }
 
-static jint FindAll(JNIEnv* env, const base::android::JavaParamRef<jobject>&
+static jint FindAll(JNIEnv* env, const JavaParamRef<jobject>& jcaller,
+    const JavaParamRef<jstring>& find);
+
+static jint Java_org_chromium_TestJni_nativeFindAll(JNIEnv* env, jobject
     jcaller,
-    const base::android::JavaParamRef<jstring>& find);
-
-JNI_GENERATOR_EXPORT jint Java_org_chromium_TestJni_nativeFindAll(JNIEnv* env,
-    jobject jcaller,
     jstring find) {
-  return FindAll(env, base::android::JavaParamRef<jobject>(env, jcaller),
-      base::android::JavaParamRef<jstring>(env, find));
+  return FindAll(env, JavaParamRef<jobject>(env, jcaller),
+      JavaParamRef<jstring>(env, find));
 }
 
-static base::android::ScopedJavaLocalRef<jobject> GetInnerClass(JNIEnv* env,
-    const base::android::JavaParamRef<jclass>& jcaller);
+static ScopedJavaLocalRef<jobject> GetInnerClass(JNIEnv* env, const
+    JavaParamRef<jclass>& jcaller);
 
-JNI_GENERATOR_EXPORT jobject
-    Java_org_chromium_TestJni_nativeGetInnerClass(JNIEnv* env, jclass jcaller) {
-  return GetInnerClass(env, base::android::JavaParamRef<jclass>(env,
-      jcaller)).Release();
+static jobject Java_org_chromium_TestJni_nativeGetInnerClass(JNIEnv* env, jclass
+    jcaller) {
+  return GetInnerClass(env, JavaParamRef<jclass>(env, jcaller)).Release();
 }
 
-JNI_GENERATOR_EXPORT jobject Java_org_chromium_TestJni_nativeQueryBitmap(JNIEnv*
-    env, jobject jcaller,
+static jobject Java_org_chromium_TestJni_nativeQueryBitmap(JNIEnv* env,
+    jobject jcaller,
     jint nativeChromeBrowserProvider,
     jobjectArray projection,
     jstring selection,
@@ -180,15 +163,14 @@
   ChromeBrowserProvider* native =
       reinterpret_cast<ChromeBrowserProvider*>(nativeChromeBrowserProvider);
   CHECK_NATIVE_PTR(env, jcaller, native, "QueryBitmap", NULL);
-  return native->QueryBitmap(env, base::android::JavaParamRef<jobject>(env,
-      jcaller), base::android::JavaParamRef<jobjectArray>(env, projection),
-      base::android::JavaParamRef<jstring>(env, selection),
-      base::android::JavaParamRef<jobjectArray>(env, selectionArgs),
-      base::android::JavaParamRef<jstring>(env, sortOrder)).Release();
+  return native->QueryBitmap(env, JavaParamRef<jobject>(env, jcaller),
+      JavaParamRef<jobjectArray>(env, projection), JavaParamRef<jstring>(env,
+      selection), JavaParamRef<jobjectArray>(env, selectionArgs),
+      JavaParamRef<jstring>(env, sortOrder)).Release();
 }
 
-JNI_GENERATOR_EXPORT void Java_org_chromium_TestJni_nativeGotOrientation(JNIEnv*
-    env, jobject jcaller,
+static void Java_org_chromium_TestJni_nativeGotOrientation(JNIEnv* env,
+    jobject jcaller,
     jint nativeDataFetcherImplAndroid,
     jdouble alpha,
     jdouble beta,
@@ -196,21 +178,19 @@
   DataFetcherImplAndroid* native =
       reinterpret_cast<DataFetcherImplAndroid*>(nativeDataFetcherImplAndroid);
   CHECK_NATIVE_PTR(env, jcaller, native, "GotOrientation");
-  return native->GotOrientation(env, base::android::JavaParamRef<jobject>(env,
-      jcaller), alpha, beta, gamma);
+  return native->GotOrientation(env, JavaParamRef<jobject>(env, jcaller), alpha,
+      beta, gamma);
 }
 
-static base::android::ScopedJavaLocalRef<jthrowable>
-    MessWithJavaException(JNIEnv* env, const
-    base::android::JavaParamRef<jclass>& jcaller,
-    const base::android::JavaParamRef<jthrowable>& e);
+static ScopedJavaLocalRef<jthrowable> MessWithJavaException(JNIEnv* env, const
+    JavaParamRef<jclass>& jcaller,
+    const JavaParamRef<jthrowable>& e);
 
-JNI_GENERATOR_EXPORT jthrowable
-    Java_org_chromium_TestJni_nativeMessWithJavaException(JNIEnv* env, jclass
-    jcaller,
+static jthrowable Java_org_chromium_TestJni_nativeMessWithJavaException(JNIEnv*
+    env, jclass jcaller,
     jthrowable e) {
-  return MessWithJavaException(env, base::android::JavaParamRef<jclass>(env,
-      jcaller), base::android::JavaParamRef<jthrowable>(env, e)).Release();
+  return MessWithJavaException(env, JavaParamRef<jclass>(env, jcaller),
+      JavaParamRef<jthrowable>(env, e)).Release();
 }
 
 // Step 3: RegisterNatives.
@@ -321,8 +301,9 @@
 };
 
 static bool RegisterNativesImpl(JNIEnv* env) {
-  if (jni_generator::ShouldSkipJniRegistration(false))
-    return true;
+
+  g_TestJni_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kTestJniClassPath).obj()));
 
   const int kMethodsTestJniSize = arraysize(kMethodsTestJni);
 
diff --git a/base/android/jni_generator/testNativesLong.golden b/base/android/jni_generator/testNativesLong.golden
index ec029ce..d5b67ba 100644
--- a/base/android/jni_generator/testNativesLong.golden
+++ b/base/android/jni_generator/testNativesLong.golden
@@ -20,20 +20,19 @@
 namespace {
 const char kTestJniClassPath[] = "org/chromium/TestJni";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_TestJni_clazz __attribute__((unused)) = 0;
-#define TestJni_clazz(env) base::android::LazyGetClass(env, kTestJniClassPath, &g_TestJni_clazz)
+jclass g_TestJni_clazz = NULL;
+#define TestJni_clazz(env) g_TestJni_clazz
 
 }  // namespace
 
 // Step 2: method stubs.
-JNI_GENERATOR_EXPORT void Java_org_chromium_TestJni_nativeDestroy(JNIEnv* env,
+static void Java_org_chromium_TestJni_nativeDestroy(JNIEnv* env,
     jobject jcaller,
     jlong nativeChromeBrowserProvider) {
   ChromeBrowserProvider* native =
       reinterpret_cast<ChromeBrowserProvider*>(nativeChromeBrowserProvider);
   CHECK_NATIVE_PTR(env, jcaller, native, "Destroy");
-  return native->Destroy(env, base::android::JavaParamRef<jobject>(env,
-      jcaller));
+  return native->Destroy(env, JavaParamRef<jobject>(env, jcaller));
 }
 
 // Step 3: RegisterNatives.
@@ -47,8 +46,9 @@
 };
 
 static bool RegisterNativesImpl(JNIEnv* env) {
-  if (jni_generator::ShouldSkipJniRegistration(false))
-    return true;
+
+  g_TestJni_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kTestJniClassPath).obj()));
 
   const int kMethodsTestJniSize = arraysize(kMethodsTestJni);
 
diff --git a/base/android/jni_generator/testSingleJNIAdditionalImport.golden b/base/android/jni_generator/testSingleJNIAdditionalImport.golden
index ef618da..1b2895e 100644
--- a/base/android/jni_generator/testSingleJNIAdditionalImport.golden
+++ b/base/android/jni_generator/testSingleJNIAdditionalImport.golden
@@ -20,27 +20,26 @@
 namespace {
 const char kFooClassPath[] = "org/chromium/foo/Foo";
 // Leaking this jclass as we cannot use LazyInstance from some threads.
-base::subtle::AtomicWord g_Foo_clazz __attribute__((unused)) = 0;
-#define Foo_clazz(env) base::android::LazyGetClass(env, kFooClassPath, &g_Foo_clazz)
+jclass g_Foo_clazz = NULL;
+#define Foo_clazz(env) g_Foo_clazz
 
 }  // namespace
 
 // Step 2: method stubs.
 
-static void DoSomething(JNIEnv* env, const base::android::JavaParamRef<jclass>&
-    jcaller,
-    const base::android::JavaParamRef<jobject>& callback);
+static void DoSomething(JNIEnv* env, const JavaParamRef<jclass>& jcaller,
+    const JavaParamRef<jobject>& callback);
 
-JNI_GENERATOR_EXPORT void Java_org_chromium_foo_Foo_nativeDoSomething(JNIEnv*
-    env, jclass jcaller,
+static void Java_org_chromium_foo_Foo_nativeDoSomething(JNIEnv* env, jclass
+    jcaller,
     jobject callback) {
-  return DoSomething(env, base::android::JavaParamRef<jclass>(env, jcaller),
-      base::android::JavaParamRef<jobject>(env, callback));
+  return DoSomething(env, JavaParamRef<jclass>(env, jcaller),
+      JavaParamRef<jobject>(env, callback));
 }
 
 static base::subtle::AtomicWord g_Foo_calledByNative = 0;
-static void Java_Foo_calledByNative(JNIEnv* env, const
-    base::android::JavaRefOrBare<jobject>& callback) {
+static void Java_Foo_calledByNative(JNIEnv* env, jobject callback) {
+  /* Must call RegisterNativesImpl()  */
   CHECK_CLAZZ(env, Foo_clazz(env),
       Foo_clazz(env));
   jmethodID method_id =
@@ -48,6 +47,7 @@
       base::android::MethodID::TYPE_STATIC>(
       env, Foo_clazz(env),
       "calledByNative",
+
 "("
 "Lorg/chromium/foo/Bar$Callback;"
 ")"
@@ -55,8 +55,9 @@
       &g_Foo_calledByNative);
 
      env->CallStaticVoidMethod(Foo_clazz(env),
-          method_id, callback.obj());
+          method_id, callback);
   jni_generator::CheckException(env);
+
 }
 
 // Step 3: RegisterNatives.
@@ -70,8 +71,9 @@
 };
 
 static bool RegisterNativesImpl(JNIEnv* env) {
-  if (jni_generator::ShouldSkipJniRegistration(false))
-    return true;
+
+  g_Foo_clazz = reinterpret_cast<jclass>(env->NewGlobalRef(
+      base::android::GetClass(env, kFooClassPath).obj()));
 
   const int kMethodsFooSize = arraysize(kMethodsFoo);
 
diff --git a/base/android/jni_utils.cc b/base/android/jni_utils.cc
index 848dfd7..b4d682b 100644
--- a/base/android/jni_utils.cc
+++ b/base/android/jni_utils.cc
@@ -4,6 +4,7 @@
 
 #include "base/android/jni_utils.h"
 
+#include "base/android/jni_android.h"
 #include "base/android/scoped_java_ref.h"
 
 #include "jni/JNIUtils_jni.h"
@@ -15,8 +16,8 @@
   return Java_JNIUtils_getClassLoader(env);
 }
 
-bool isSelectiveJniRegistrationEnabled(JNIEnv* env) {
-  return Java_JNIUtils_isSelectiveJniRegistrationEnabled(env);
+bool RegisterJNIUtils(JNIEnv* env) {
+  return RegisterNativesImpl(env);
 }
 
 }  // namespace android
diff --git a/base/android/jni_utils.h b/base/android/jni_utils.h
index ef645c2..b793aed 100644
--- a/base/android/jni_utils.h
+++ b/base/android/jni_utils.h
@@ -18,8 +18,7 @@
 // via JNI from Java.
 BASE_EXPORT ScopedJavaLocalRef<jobject> GetClassLoader(JNIEnv* env);
 
-// Returns true if the current process permits selective JNI registration.
-BASE_EXPORT bool isSelectiveJniRegistrationEnabled(JNIEnv* env);
+bool RegisterJNIUtils(JNIEnv* env);
 
 }  // namespace android
 }  // namespace base
diff --git a/base/android/jni_weak_ref.cc b/base/android/jni_weak_ref.cc
index fe7ea2e..55244f2 100644
--- a/base/android/jni_weak_ref.cc
+++ b/base/android/jni_weak_ref.cc
@@ -4,34 +4,24 @@
 
 #include "base/android/jni_weak_ref.h"
 
-#include <utility>
-
 #include "base/android/jni_android.h"
 #include "base/logging.h"
 
 using base::android::AttachCurrentThread;
 
-JavaObjectWeakGlobalRef::JavaObjectWeakGlobalRef() : obj_(nullptr) {}
+JavaObjectWeakGlobalRef::JavaObjectWeakGlobalRef()
+  : obj_(NULL) {
+}
 
 JavaObjectWeakGlobalRef::JavaObjectWeakGlobalRef(
     const JavaObjectWeakGlobalRef& orig)
-    : obj_(nullptr) {
+    : obj_(NULL) {
   Assign(orig);
 }
 
-JavaObjectWeakGlobalRef::JavaObjectWeakGlobalRef(JavaObjectWeakGlobalRef&& orig)
-    : obj_(orig.obj_) {
-  orig.obj_ = nullptr;
-}
-
 JavaObjectWeakGlobalRef::JavaObjectWeakGlobalRef(JNIEnv* env, jobject obj)
     : obj_(env->NewWeakGlobalRef(obj)) {
-}
-
-JavaObjectWeakGlobalRef::JavaObjectWeakGlobalRef(
-    JNIEnv* env,
-    const base::android::JavaRef<jobject>& obj)
-    : obj_(env->NewWeakGlobalRef(obj.obj())) {
+  DCHECK(obj_);
 }
 
 JavaObjectWeakGlobalRef::~JavaObjectWeakGlobalRef() {
@@ -42,14 +32,10 @@
   Assign(rhs);
 }
 
-void JavaObjectWeakGlobalRef::operator=(JavaObjectWeakGlobalRef&& rhs) {
-  std::swap(obj_, rhs.obj_);
-}
-
 void JavaObjectWeakGlobalRef::reset() {
   if (obj_) {
     AttachCurrentThread()->DeleteWeakGlobalRef(obj_);
-    obj_ = nullptr;
+    obj_ = NULL;
   }
 }
 
@@ -60,7 +46,7 @@
 
 base::android::ScopedJavaLocalRef<jobject> GetRealObject(
     JNIEnv* env, jweak obj) {
-  jobject real = nullptr;
+  jobject real = NULL;
   if (obj)
     real = env->NewLocalRef(obj);
   return base::android::ScopedJavaLocalRef<jobject>(env, real);
@@ -74,5 +60,5 @@
   if (obj_)
     env->DeleteWeakGlobalRef(obj_);
 
-  obj_ = other.obj_ ? env->NewWeakGlobalRef(other.obj_) : nullptr;
+  obj_ = other.obj_ ? env->NewWeakGlobalRef(other.obj_) : NULL;
 }
diff --git a/base/android/jni_weak_ref.h b/base/android/jni_weak_ref.h
index 223c47b..c851046 100644
--- a/base/android/jni_weak_ref.h
+++ b/base/android/jni_weak_ref.h
@@ -18,22 +18,14 @@
  public:
   JavaObjectWeakGlobalRef();
   JavaObjectWeakGlobalRef(const JavaObjectWeakGlobalRef& orig);
-  JavaObjectWeakGlobalRef(JavaObjectWeakGlobalRef&& orig);
   JavaObjectWeakGlobalRef(JNIEnv* env, jobject obj);
-  JavaObjectWeakGlobalRef(JNIEnv* env,
-                          const base::android::JavaRef<jobject>& obj);
   virtual ~JavaObjectWeakGlobalRef();
 
   void operator=(const JavaObjectWeakGlobalRef& rhs);
-  void operator=(JavaObjectWeakGlobalRef&& rhs);
 
   base::android::ScopedJavaLocalRef<jobject> get(JNIEnv* env) const;
 
-  // Returns true if the weak reference has not been initialized to point at
-  // an object (or ḣas had reset() called).
-  // Do not call this to test if the object referred to still exists! The weak
-  // reference remains initialized even if the target object has been collected.
-  bool is_uninitialized() const { return obj_ == nullptr; }
+  bool is_empty() const { return obj_ == NULL; }
 
   void reset();
 
diff --git a/base/android/junit/src/org/chromium/base/BaseChromiumApplicationTest.java b/base/android/junit/src/org/chromium/base/BaseChromiumApplicationTest.java
index 269f84b..bfcd7aa 100644
--- a/base/android/junit/src/org/chromium/base/BaseChromiumApplicationTest.java
+++ b/base/android/junit/src/org/chromium/base/BaseChromiumApplicationTest.java
@@ -10,19 +10,18 @@
 import android.app.Activity;
 import android.view.KeyEvent;
 
+import junit.framework.Assert;
+
 import org.chromium.base.BaseChromiumApplication.WindowFocusChangedListener;
+import org.chromium.base.test.shadows.ShadowMultiDex;
 import org.chromium.testing.local.LocalRobolectricTestRunner;
-import org.junit.Assert;
 import org.junit.Test;
 import org.junit.runner.RunWith;
 import org.robolectric.Robolectric;
-import org.robolectric.RuntimeEnvironment;
-import org.robolectric.Shadows;
 import org.robolectric.annotation.Config;
 import org.robolectric.annotation.Implementation;
 import org.robolectric.annotation.Implements;
 import org.robolectric.shadows.ShadowActivity;
-import org.robolectric.shadows.multidex.ShadowMultiDex;
 import org.robolectric.util.ActivityController;
 
 /** Unit tests for {@link BaseChromiumApplication}. */
@@ -53,7 +52,7 @@
 
     @Test
     public void testWindowsFocusChanged() throws Exception {
-        BaseChromiumApplication app = (BaseChromiumApplication) RuntimeEnvironment.application;
+        BaseChromiumApplication app = (BaseChromiumApplication) Robolectric.application;
 
         WindowFocusChangedListener mock = mock(WindowFocusChangedListener.class);
         app.registerWindowFocusChangedListener(mock);
@@ -61,7 +60,7 @@
         ActivityController<Activity> controller =
                 Robolectric.buildActivity(Activity.class).create().start().visible();
         TrackingShadowActivity shadow =
-                (TrackingShadowActivity) Shadows.shadowOf(controller.get());
+                (TrackingShadowActivity) Robolectric.shadowOf(controller.get());
 
         controller.get().getWindow().getCallback().onWindowFocusChanged(true);
         // Assert that listeners were notified.
diff --git a/base/android/library_loader/library_loader_hooks.cc b/base/android/library_loader/library_loader_hooks.cc
index 621575c..025075e 100644
--- a/base/android/library_loader/library_loader_hooks.cc
+++ b/base/android/library_loader/library_loader_hooks.cc
@@ -10,7 +10,7 @@
 #include "base/android/library_loader/library_prefetcher.h"
 #include "base/at_exit.h"
 #include "base/metrics/histogram.h"
-#include "base/metrics/histogram_macros.h"
+#include "base/metrics/sparse_histogram.h"
 #include "jni/LibraryLoader_jni.h"
 
 namespace base {
@@ -21,7 +21,6 @@
 base::AtExitManager* g_at_exit_manager = NULL;
 const char* g_library_version_number = "";
 LibraryLoadedHook* g_registration_callback = NULL;
-NativeInitializationHook* g_native_initialization_hook = NULL;
 
 enum RendererHistogramCode {
   // Renderer load at fixed address success, fail, or not attempted.
@@ -150,11 +149,6 @@
   g_library_preloader_renderer_histogram_code_registered = true;
 }
 
-void SetNativeInitializationHook(
-    NativeInitializationHook native_initialization_hook) {
-  g_native_initialization_hook = native_initialization_hook;
-}
-
 void RecordLibraryLoaderRendererHistograms() {
   RecordChromiumAndroidLinkerRendererHistogram();
   RecordLibraryPreloaderRendereHistogram();
@@ -173,9 +167,6 @@
 
 static jboolean LibraryLoaded(JNIEnv* env,
                               const JavaParamRef<jobject>& jcaller) {
-  if (g_native_initialization_hook && !g_native_initialization_hook()) {
-    return false;
-  }
   if (g_registration_callback == NULL) {
     return true;
   }
diff --git a/base/android/library_loader/library_loader_hooks.h b/base/android/library_loader/library_loader_hooks.h
index 5c37e6e..3e8969b 100644
--- a/base/android/library_loader/library_loader_hooks.h
+++ b/base/android/library_loader/library_loader_hooks.h
@@ -8,7 +8,6 @@
 #include <jni.h>
 
 #include "base/base_export.h"
-#include "base/callback.h"
 
 namespace base {
 namespace android {
@@ -28,11 +27,6 @@
   PROCESS_WEBVIEW_CHILD = 4,
 };
 
-typedef bool NativeInitializationHook();
-
-BASE_EXPORT void SetNativeInitializationHook(
-    NativeInitializationHook native_initialization_hook);
-
 // Record any pending renderer histogram value as histograms.  Pending values
 // are set by RegisterChromiumAndroidLinkerRendererHistogram and
 // RegisterLibraryPreloaderRendererHistogram.
diff --git a/base/android/library_loader/library_prefetcher.cc b/base/android/library_loader/library_prefetcher.cc
index a946c82..c7ec990 100644
--- a/base/android/library_loader/library_prefetcher.cc
+++ b/base/android/library_loader/library_prefetcher.cc
@@ -16,7 +16,6 @@
 #include "base/macros.h"
 #include "base/posix/eintr_wrapper.h"
 #include "base/strings/string_util.h"
-#include "build/build_config.h"
 
 namespace base {
 namespace android {
@@ -51,13 +50,6 @@
 // Heap allocations, syscalls and library functions are not allowed in this
 // function.
 // Returns true for success.
-#if defined(ADDRESS_SANITIZER)
-// Disable AddressSanitizer instrumentation for this function. It is touching
-// memory that hasn't been allocated by the app, though the addresses are
-// valid. Furthermore, this takes place in a child process. See crbug.com/653372
-// for the context.
-__attribute__((no_sanitize_address))
-#endif
 bool Prefetch(const std::vector<std::pair<uintptr_t, uintptr_t>>& ranges) {
   for (const auto& range : ranges) {
     const uintptr_t page_mask = kPageSize - 1;
diff --git a/base/android/linker/BUILD.gn b/base/android/linker/BUILD.gn
index c2bfb11..3724b88 100644
--- a/base/android/linker/BUILD.gn
+++ b/base/android/linker/BUILD.gn
@@ -6,6 +6,7 @@
 
 assert(is_android)
 
+# GYP: //base/base.gyp:chromium_android_linker
 shared_library("chromium_android_linker") {
   sources = [
     "android_dlext.h",
diff --git a/base/android/linker/config.gni b/base/android/linker/config.gni
index 27793ff..174c1ab 100644
--- a/base/android/linker/config.gni
+++ b/base/android/linker/config.gni
@@ -6,8 +6,7 @@
 import("//build/config/compiler/compiler.gni")
 import("//build/config/sanitizers/sanitizers.gni")
 
-# Chromium linker doesn't reliably support loading multiple libraries;
-# disable for component builds, see crbug.com/657093.
+# Chromium linker crashes on component builds on Android 4.4. See b/11379966
 # Chromium linker causes instrumentation to return incorrect results.
 chromium_linker_supported =
     !is_component_build && !enable_profiling && !use_order_profiling && !is_asan
diff --git a/base/android/locale_utils.cc b/base/android/locale_utils.cc
index b3a2346..af46f89 100644
--- a/base/android/locale_utils.cc
+++ b/base/android/locale_utils.cc
@@ -16,12 +16,16 @@
   return ConvertJavaStringToUTF8(Java_LocaleUtils_getDefaultCountryCode(env));
 }
 
-std::string GetDefaultLocaleString() {
+std::string GetDefaultLocale() {
   JNIEnv* env = base::android::AttachCurrentThread();
-  ScopedJavaLocalRef<jstring> locale =
-      Java_LocaleUtils_getDefaultLocaleString(env);
+  ScopedJavaLocalRef<jstring> locale = Java_LocaleUtils_getDefaultLocale(
+      env);
   return ConvertJavaStringToUTF8(locale);
 }
 
+bool RegisterLocaleUtils(JNIEnv* env) {
+  return RegisterNativesImpl(env);
+}
+
 }  // namespace android
 }  // namespace base
diff --git a/base/android/locale_utils.h b/base/android/locale_utils.h
index be68890..9e03b83 100644
--- a/base/android/locale_utils.h
+++ b/base/android/locale_utils.h
@@ -16,8 +16,10 @@
 
 BASE_EXPORT std::string GetDefaultCountryCode();
 
-// Return the current default locale of the device as string.
-BASE_EXPORT std::string GetDefaultLocaleString();
+// Return the current default locale of the device.
+BASE_EXPORT std::string GetDefaultLocale();
+
+BASE_EXPORT bool RegisterLocaleUtils(JNIEnv* env);
 
 }  // namespace android
 }  // namespace base
diff --git a/base/android/memory_pressure_listener_android.cc b/base/android/memory_pressure_listener_android.cc
index 32e0871..5975b94 100644
--- a/base/android/memory_pressure_listener_android.cc
+++ b/base/android/memory_pressure_listener_android.cc
@@ -8,8 +8,6 @@
 #include "base/memory/memory_pressure_listener.h"
 #include "jni/MemoryPressureListener_jni.h"
 
-using base::android::JavaParamRef;
-
 // Defined and called by JNI.
 static void OnMemoryPressure(JNIEnv* env,
                              const JavaParamRef<jclass>& clazz,
diff --git a/base/android/path_utils.cc b/base/android/path_utils.cc
index 89ab833..b765449 100644
--- a/base/android/path_utils.cc
+++ b/base/android/path_utils.cc
@@ -17,7 +17,8 @@
 
 bool GetDataDirectory(FilePath* result) {
   JNIEnv* env = AttachCurrentThread();
-  ScopedJavaLocalRef<jstring> path = Java_PathUtils_getDataDirectory(env);
+  ScopedJavaLocalRef<jstring> path =
+      Java_PathUtils_getDataDirectory(env, GetApplicationContext());
   FilePath data_path(ConvertJavaStringToUTF8(path));
   *result = data_path;
   return true;
@@ -25,7 +26,8 @@
 
 bool GetDatabaseDirectory(FilePath* result) {
   JNIEnv* env = AttachCurrentThread();
-  ScopedJavaLocalRef<jstring> path = Java_PathUtils_getDatabaseDirectory(env);
+  ScopedJavaLocalRef<jstring> path =
+      Java_PathUtils_getDatabaseDirectory(env, GetApplicationContext());
   FilePath data_path(ConvertJavaStringToUTF8(path));
   *result = data_path;
   return true;
@@ -33,7 +35,8 @@
 
 bool GetCacheDirectory(FilePath* result) {
   JNIEnv* env = AttachCurrentThread();
-  ScopedJavaLocalRef<jstring> path = Java_PathUtils_getCacheDirectory(env);
+  ScopedJavaLocalRef<jstring> path =
+      Java_PathUtils_getCacheDirectory(env, GetApplicationContext());
   FilePath cache_path(ConvertJavaStringToUTF8(path));
   *result = cache_path;
   return true;
@@ -42,7 +45,7 @@
 bool GetThumbnailCacheDirectory(FilePath* result) {
   JNIEnv* env = AttachCurrentThread();
   ScopedJavaLocalRef<jstring> path =
-      Java_PathUtils_getThumbnailCacheDirectory(env);
+      Java_PathUtils_getThumbnailCacheDirectory(env, GetApplicationContext());
   FilePath thumbnail_cache_path(ConvertJavaStringToUTF8(path));
   *result = thumbnail_cache_path;
   return true;
@@ -50,7 +53,8 @@
 
 bool GetDownloadsDirectory(FilePath* result) {
   JNIEnv* env = AttachCurrentThread();
-  ScopedJavaLocalRef<jstring> path = Java_PathUtils_getDownloadsDirectory(env);
+  ScopedJavaLocalRef<jstring> path =
+      Java_PathUtils_getDownloadsDirectory(env, GetApplicationContext());
   FilePath downloads_path(ConvertJavaStringToUTF8(path));
   *result = downloads_path;
   return true;
@@ -59,7 +63,7 @@
 bool GetNativeLibraryDirectory(FilePath* result) {
   JNIEnv* env = AttachCurrentThread();
   ScopedJavaLocalRef<jstring> path =
-      Java_PathUtils_getNativeLibraryDirectory(env);
+      Java_PathUtils_getNativeLibraryDirectory(env, GetApplicationContext());
   FilePath library_path(ConvertJavaStringToUTF8(path));
   *result = library_path;
   return true;
@@ -74,5 +78,9 @@
   return true;
 }
 
+bool RegisterPathUtils(JNIEnv* env) {
+  return RegisterNativesImpl(env);
+}
+
 }  // namespace android
 }  // namespace base
diff --git a/base/android/path_utils.h b/base/android/path_utils.h
index 7402644..6501f1b 100644
--- a/base/android/path_utils.h
+++ b/base/android/path_utils.h
@@ -48,6 +48,8 @@
 // is placed in the FilePath pointed to by 'result'.
 BASE_EXPORT bool GetExternalStorageDirectory(FilePath* result);
 
+bool RegisterPathUtils(JNIEnv* env);
+
 }  // namespace android
 }  // namespace base
 
diff --git a/base/android/record_histogram.cc b/base/android/record_histogram.cc
index 1a207a1..3c51fe2 100644
--- a/base/android/record_histogram.cc
+++ b/base/android/record_histogram.cc
@@ -53,16 +53,12 @@
                           jstring j_histogram_name,
                           int32_t expected_min,
                           int32_t expected_max,
-                          uint32_t expected_bucket_count,
+                          int32_t expected_bucket_count,
                           HistogramBase* histogram) {
-    std::string histogram_name = ConvertJavaStringToUTF8(env, j_histogram_name);
-    bool valid_arguments = Histogram::InspectConstructionArguments(
-        histogram_name, &expected_min, &expected_max, &expected_bucket_count);
-    DCHECK(valid_arguments);
     DCHECK(histogram->HasConstructionArguments(expected_min, expected_max,
                                                expected_bucket_count))
-        << histogram_name << "/" << expected_min << "/" << expected_max << "/"
-        << expected_bucket_count << " vs. "
+        << ConvertJavaStringToUTF8(env, j_histogram_name) << "/" << expected_min
+        << "/" << expected_max << "/" << expected_bucket_count << " vs. "
         << HistogramConstructionParamsToString(histogram);
   }
 
@@ -117,8 +113,6 @@
       return histogram;
     }
 
-    DCHECK_GE(min, 1) << "The min expected sample must be >= 1";
-
     std::string histogram_name = ConvertJavaStringToUTF8(env, j_histogram_name);
     histogram =
         Histogram::FactoryGet(histogram_name, min, max, num_buckets,
diff --git a/base/android/scoped_java_ref.cc b/base/android/scoped_java_ref.cc
index 2876ba4..4d4ef6d 100644
--- a/base/android/scoped_java_ref.cc
+++ b/base/android/scoped_java_ref.cc
@@ -26,9 +26,7 @@
   DCHECK(!failed);
 }
 
-ScopedJavaLocalFrame::~ScopedJavaLocalFrame() {
-  env_->PopLocalFrame(nullptr);
-}
+ScopedJavaLocalFrame::~ScopedJavaLocalFrame() { env_->PopLocalFrame(NULL); }
 
 #if DCHECK_IS_ON()
 // This constructor is inlined when DCHECKs are disabled; don't add anything
@@ -71,14 +69,14 @@
   if (obj_) {
     DCHECK_EQ(env, AttachCurrentThread());  // Is |env| on correct thread.
     env->DeleteLocalRef(obj_);
-    obj_ = nullptr;
+    obj_ = NULL;
   }
 }
 
 void JavaRef<jobject>::ResetGlobalRef() {
   if (obj_) {
     AttachCurrentThread()->DeleteGlobalRef(obj_);
-    obj_ = nullptr;
+    obj_ = NULL;
   }
 }
 
diff --git a/base/android/scoped_java_ref.h b/base/android/scoped_java_ref.h
index 6d728e9..a1b4b13 100644
--- a/base/android/scoped_java_ref.h
+++ b/base/android/scoped_java_ref.h
@@ -9,7 +9,6 @@
 #include <stddef.h>
 
 #include <type_traits>
-#include <utility>
 
 #include "base/base_export.h"
 #include "base/logging.h"
@@ -44,23 +43,23 @@
 template<>
 class BASE_EXPORT JavaRef<jobject> {
  public:
-  // Initializes a null reference. Don't add anything else here; it's inlined.
-  JavaRef() : obj_(nullptr) {}
-
   // Allow nullptr to be converted to JavaRef. This avoids having to declare an
-  // empty JavaRef just to pass null to a function, and makes C++ "nullptr" and
-  // Java "null" equivalent.
+  // empty ScopedJavaLocalRef just to pass null to a function with a JavaRef
+  // parameter, and makes C++ "nullptr" and Java "null" equivalent.
   JavaRef(std::nullptr_t) : JavaRef() {}
 
-  // Public to allow destruction of null JavaRef objects.
-  // Don't add anything else here; it's inlined.
+  // Public to allow destruction of temporary JavaRef objects created by the
+  // nullptr conversion. Don't add anything else here; it's inlined.
   ~JavaRef() {}
 
   jobject obj() const { return obj_; }
 
-  bool is_null() const { return obj_ == nullptr; }
+  bool is_null() const { return obj_ == NULL; }
 
  protected:
+  // Initializes a NULL reference. Don't add anything else here; it's inlined.
+  JavaRef() : obj_(NULL) {}
+
   // Takes ownership of the |obj| reference passed; requires it to be a local
   // reference type.
 #if DCHECK_IS_ON()
@@ -71,8 +70,6 @@
   JavaRef(JNIEnv* env, jobject obj) : obj_(obj) {}
 #endif
 
-  void swap(JavaRef& other) { std::swap(obj_, other.obj_); }
-
   // The following are implementation detail convenience methods, for
   // use by the sub-classes.
   JNIEnv* SetNewLocalRef(JNIEnv* env, jobject obj);
@@ -93,13 +90,14 @@
 template<typename T>
 class JavaRef : public JavaRef<jobject> {
  public:
-  JavaRef() {}
   JavaRef(std::nullptr_t) : JavaRef<jobject>(nullptr) {}
   ~JavaRef() {}
 
   T obj() const { return static_cast<T>(JavaRef<jobject>::obj()); }
 
  protected:
+  JavaRef() {}
+
   JavaRef(JNIEnv* env, T obj) : JavaRef<jobject>(env, obj) {}
 
  private:
@@ -146,8 +144,7 @@
 template<typename T>
 class ScopedJavaLocalRef : public JavaRef<T> {
  public:
-  ScopedJavaLocalRef() : env_(nullptr) {}
-  ScopedJavaLocalRef(std::nullptr_t) : env_(nullptr) {}
+  ScopedJavaLocalRef() : env_(NULL) {}
 
   // Non-explicit copy constructor, to allow ScopedJavaLocalRef to be returned
   // by value as this is the normal usage pattern.
@@ -156,18 +153,14 @@
     this->SetNewLocalRef(env_, other.obj());
   }
 
-  ScopedJavaLocalRef(ScopedJavaLocalRef<T>&& other) : env_(other.env_) {
-    this->swap(other);
-  }
-
-  explicit ScopedJavaLocalRef(const JavaRef<T>& other) : env_(nullptr) {
+  template<typename U>
+  explicit ScopedJavaLocalRef(const U& other)
+      : env_(NULL) {
     this->Reset(other);
   }
 
   // Assumes that |obj| is a local reference to a Java object and takes
   // ownership  of this local reference.
-  // TODO(torne): this shouldn't be used outside of JNI helper functions but
-  // there are currently some cases where there aren't helpers for things.
   ScopedJavaLocalRef(JNIEnv* env, T obj) : JavaRef<T>(env, obj), env_(env) {}
 
   ~ScopedJavaLocalRef() {
@@ -180,32 +173,31 @@
     this->Reset(other);
   }
 
-  void operator=(ScopedJavaLocalRef<T>&& other) {
-    env_ = other.env_;
-    this->swap(other);
-  }
-
   void Reset() {
     this->ResetLocalRef(env_);
   }
 
-  void Reset(const ScopedJavaLocalRef<T>& other) {
+  template<typename U>
+  void Reset(const ScopedJavaLocalRef<U>& other) {
     // We can copy over env_ here as |other| instance must be from the same
     // thread as |this| local ref. (See class comment for multi-threading
     // limitations, and alternatives).
     this->Reset(other.env_, other.obj());
   }
 
-  void Reset(const JavaRef<T>& other) {
-    // If |env_| was not yet set (is still null) it will be attached to the
+  template<typename U>
+  void Reset(const U& other) {
+    // If |env_| was not yet set (is still NULL) it will be attached to the
     // current thread in SetNewLocalRef().
     this->Reset(env_, other.obj());
   }
 
-  // Creates a new local reference to the Java object, unlike the constructor
-  // with the same parameters that takes ownership of the existing reference.
-  // TODO(torne): these should match as this is confusing.
-  void Reset(JNIEnv* env, T obj) { env_ = this->SetNewLocalRef(env, obj); }
+  template<typename U>
+  void Reset(JNIEnv* env, U obj) {
+    static_assert(std::is_convertible<U, T>::value,
+                  "U must be convertible to T");
+    env_ = this->SetNewLocalRef(env, obj);
+  }
 
   // Releases the local reference to the caller. The caller *must* delete the
   // local reference when it is done with it. Note that calling a Java method
@@ -235,17 +227,17 @@
 class ScopedJavaGlobalRef : public JavaRef<T> {
  public:
   ScopedJavaGlobalRef() {}
-  ScopedJavaGlobalRef(std::nullptr_t) {}
 
   ScopedJavaGlobalRef(const ScopedJavaGlobalRef<T>& other) {
     this->Reset(other);
   }
 
-  ScopedJavaGlobalRef(ScopedJavaGlobalRef<T>&& other) { this->swap(other); }
-
   ScopedJavaGlobalRef(JNIEnv* env, T obj) { this->Reset(env, obj); }
 
-  explicit ScopedJavaGlobalRef(const JavaRef<T>& other) { this->Reset(other); }
+  template<typename U>
+  explicit ScopedJavaGlobalRef(const U& other) {
+    this->Reset(other);
+  }
 
   ~ScopedJavaGlobalRef() {
     this->Reset();
@@ -257,19 +249,26 @@
     this->Reset(other);
   }
 
-  void operator=(ScopedJavaGlobalRef<T>&& other) { this->swap(other); }
-
   void Reset() {
     this->ResetGlobalRef();
   }
 
-  void Reset(const JavaRef<T>& other) { this->Reset(nullptr, other.obj()); }
+  template<typename U>
+  void Reset(const U& other) {
+    this->Reset(NULL, other.obj());
+  }
 
-  void Reset(JNIEnv* env, const JavaParamRef<T>& other) {
+  template<typename U>
+  void Reset(JNIEnv* env, const JavaParamRef<U>& other) {
     this->Reset(env, other.obj());
   }
 
-  void Reset(JNIEnv* env, T obj) { this->SetNewGlobalRef(env, obj); }
+  template<typename U>
+  void Reset(JNIEnv* env, U obj) {
+    static_assert(std::is_convertible<U, T>::value,
+                  "U must be convertible to T");
+    this->SetNewGlobalRef(env, obj);
+  }
 
   // Releases the global reference to the caller. The caller *must* delete the
   // global reference when it is done with it. Note that calling a Java method
@@ -279,22 +278,6 @@
   }
 };
 
-// Temporary type for parameters to Java functions, to allow incremental
-// migration from bare jobject to JavaRef. Don't use outside JNI generator.
-template <typename T>
-class JavaRefOrBare {
- public:
-  JavaRefOrBare(std::nullptr_t) : obj_(nullptr) {}
-  JavaRefOrBare(const JavaRef<T>& ref) : obj_(ref.obj()) {}
-  JavaRefOrBare(T obj) : obj_(obj) {}
-  T obj() const { return obj_; }
-
- private:
-  T obj_;
-
-  DISALLOW_COPY_AND_ASSIGN(JavaRefOrBare);
-};
-
 }  // namespace android
 }  // namespace base
 
diff --git a/base/android/scoped_java_ref_unittest.cc b/base/android/scoped_java_ref_unittest.cc
index 99d035b..3f4419a 100644
--- a/base/android/scoped_java_ref_unittest.cc
+++ b/base/android/scoped_java_ref_unittest.cc
@@ -106,17 +106,6 @@
       EXPECT_EQ(2, g_local_refs);
     }
     EXPECT_EQ(1, g_local_refs);
-    {
-      ScopedJavaLocalRef<jstring> str4((ScopedJavaLocalRef<jstring>(str2)));
-      EXPECT_EQ(2, g_local_refs);
-    }
-    EXPECT_EQ(1, g_local_refs);
-    {
-      ScopedJavaLocalRef<jstring> str5;
-      str5 = ScopedJavaLocalRef<jstring>(str2);
-      EXPECT_EQ(2, g_local_refs);
-    }
-    EXPECT_EQ(1, g_local_refs);
     str2.Reset();
     EXPECT_EQ(0, g_local_refs);
     global_str.Reset();
diff --git a/base/android/sys_utils.cc b/base/android/sys_utils.cc
index a576644..e89c1b3 100644
--- a/base/android/sys_utils.cc
+++ b/base/android/sys_utils.cc
@@ -11,6 +11,10 @@
 namespace base {
 namespace android {
 
+bool SysUtils::Register(JNIEnv* env) {
+  return RegisterNativesImpl(env);
+}
+
 bool SysUtils::IsLowEndDeviceFromJni() {
   JNIEnv* env = AttachCurrentThread();
   return Java_SysUtils_isLowEndDevice(env);
@@ -18,4 +22,4 @@
 
 }  // namespace android
 
-}  // namespace base
+}  // namespace base
\ No newline at end of file
diff --git a/base/android/sys_utils.h b/base/android/sys_utils.h
index 2edbdd5..85dc035 100644
--- a/base/android/sys_utils.h
+++ b/base/android/sys_utils.h
@@ -12,6 +12,8 @@
 
 class BASE_EXPORT SysUtils {
  public:
+  static bool Register(JNIEnv* env);
+
   // Returns true iff this is a low-end device.
   static bool IsLowEndDeviceFromJni();
 };
diff --git a/base/android/thread_utils.h b/base/android/thread_utils.h
new file mode 100644
index 0000000..cbe65f0
--- /dev/null
+++ b/base/android/thread_utils.h
@@ -0,0 +1,16 @@
+// Copyright (c) 2012 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef BASE_ANDROID_THREAD_UTILS_H_
+#define BASE_ANDROID_THREAD_UTILS_H_
+
+#include "base/android/jni_android.h"
+
+namespace base {
+
+bool RegisterThreadUtils(JNIEnv* env);
+
+}  // namespace base
+
+#endif  // BASE_ANDROID_THREAD_UTILS_H_
diff --git a/base/debug/stack_trace_android.cc b/base/debug/stack_trace_android.cc
index 329204c..1e80385 100644
--- a/base/debug/stack_trace_android.cc
+++ b/base/debug/stack_trace_android.cc
@@ -7,8 +7,6 @@
 #include <android/log.h>
 #include <stddef.h>
 #include <unwind.h>
-
-#include <algorithm>
 #include <ostream>
 
 #include "base/debug/proc_maps_linux.h"
@@ -69,10 +67,8 @@
   return (sigaction(SIGPIPE, &action, NULL) == 0);
 }
 
-StackTrace::StackTrace(size_t count) {
-  count = std::min(arraysize(trace_), count);
-
-  StackCrawlState state(reinterpret_cast<uintptr_t*>(trace_), count);
+StackTrace::StackTrace() {
+  StackCrawlState state(reinterpret_cast<uintptr_t*>(trace_), kMaxTraces);
   _Unwind_Backtrace(&TraceStackFrame, &state);
   count_ = state.frame_count;
 }
diff --git a/base/i18n/base_i18n_export.h b/base/i18n/base_i18n_export.h
deleted file mode 100644
index e8a2add..0000000
--- a/base/i18n/base_i18n_export.h
+++ /dev/null
@@ -1,29 +0,0 @@
-// Copyright (c) 2011 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_I18N_BASE_I18N_EXPORT_H_
-#define BASE_I18N_BASE_I18N_EXPORT_H_
-
-#if defined(COMPONENT_BUILD)
-#if defined(WIN32)
-
-#if defined(BASE_I18N_IMPLEMENTATION)
-#define BASE_I18N_EXPORT __declspec(dllexport)
-#else
-#define BASE_I18N_EXPORT __declspec(dllimport)
-#endif  // defined(BASE_I18N_IMPLEMENTATION)
-
-#else  // defined(WIN32)
-#if defined(BASE_I18N_IMPLEMENTATION)
-#define BASE_I18N_EXPORT __attribute__((visibility("default")))
-#else
-#define BASE_I18N_EXPORT
-#endif
-#endif
-
-#else  // defined(COMPONENT_BUILD)
-#define BASE_I18N_EXPORT
-#endif
-
-#endif  // BASE_I18N_BASE_I18N_EXPORT_H_
diff --git a/base/i18n/rtl.h b/base/i18n/rtl.h
deleted file mode 100644
index df15cd0..0000000
--- a/base/i18n/rtl.h
+++ /dev/null
@@ -1,155 +0,0 @@
-// Copyright (c) 2011 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_I18N_RTL_H_
-#define BASE_I18N_RTL_H_
-
-#include <string>
-
-#include "base/compiler_specific.h"
-#include "base/i18n/base_i18n_export.h"
-#include "base/strings/string16.h"
-#include "build/build_config.h"
-
-namespace base {
-
-class FilePath;
-
-namespace i18n {
-
-const char16 kRightToLeftMark = 0x200F;
-const char16 kLeftToRightMark = 0x200E;
-const char16 kLeftToRightEmbeddingMark = 0x202A;
-const char16 kRightToLeftEmbeddingMark = 0x202B;
-const char16 kPopDirectionalFormatting = 0x202C;
-const char16 kLeftToRightOverride = 0x202D;
-const char16 kRightToLeftOverride = 0x202E;
-
-// Locale.java mirrored this enum TextDirection. Please keep in sync.
-enum TextDirection {
-  UNKNOWN_DIRECTION = 0,
-  RIGHT_TO_LEFT = 1,
-  LEFT_TO_RIGHT = 2,
-  TEXT_DIRECTION_MAX = LEFT_TO_RIGHT,
-};
-
-// Get the locale that the currently running process has been configured to use.
-// The return value is of the form language[-country] (e.g., en-US) where the
-// language is the 2 or 3 letter code from ISO-639.
-BASE_I18N_EXPORT std::string GetConfiguredLocale();
-
-// Canonicalize a string (eg. a POSIX locale string) to a Chrome locale name.
-BASE_I18N_EXPORT std::string GetCanonicalLocale(const std::string& locale);
-
-// Sets the default locale of ICU.
-// Once the application locale of Chrome in GetApplicationLocale is determined,
-// the default locale of ICU need to be changed to match the application locale
-// so that ICU functions work correctly in a locale-dependent manner.
-// This is handy in that we don't have to call GetApplicationLocale()
-// everytime we call locale-dependent ICU APIs as long as we make sure
-// that this is called before any locale-dependent API is called.
-BASE_I18N_EXPORT void SetICUDefaultLocale(const std::string& locale_string);
-
-// Returns true if the application text direction is right-to-left.
-BASE_I18N_EXPORT bool IsRTL();
-
-// Returns whether the text direction for the default ICU locale is RTL.  This
-// assumes that SetICUDefaultLocale has been called to set the default locale to
-// the UI locale of Chrome.
-// NOTE: Generally, you should call IsRTL() instead of this.
-BASE_I18N_EXPORT bool ICUIsRTL();
-
-// Returns the text direction for |locale_name|.
-// As a startup optimization, this method checks the locale against a list of
-// Chrome-supported RTL locales.
-BASE_I18N_EXPORT TextDirection
-GetTextDirectionForLocaleInStartUp(const char* locale_name);
-
-// Returns the text direction for |locale_name|.
-BASE_I18N_EXPORT TextDirection GetTextDirectionForLocale(
-    const char* locale_name);
-
-// Given the string in |text|, returns the directionality of the first or last
-// character with strong directionality in the string. If no character in the
-// text has strong directionality, LEFT_TO_RIGHT is returned. The Bidi
-// character types L, LRE, LRO, R, AL, RLE, and RLO are considered as strong
-// directionality characters. Please refer to http://unicode.org/reports/tr9/
-// for more information.
-BASE_I18N_EXPORT TextDirection GetFirstStrongCharacterDirection(
-    const string16& text);
-BASE_I18N_EXPORT TextDirection GetLastStrongCharacterDirection(
-    const string16& text);
-
-// Given the string in |text|, returns LEFT_TO_RIGHT or RIGHT_TO_LEFT if all the
-// strong directionality characters in the string are of the same
-// directionality. It returns UNKNOWN_DIRECTION if the string contains a mix of
-// LTR and RTL strong directionality characters. Defaults to LEFT_TO_RIGHT if
-// the string does not contain directionality characters. Please refer to
-// http://unicode.org/reports/tr9/ for more information.
-BASE_I18N_EXPORT TextDirection GetStringDirection(const string16& text);
-
-// Given the string in |text|, this function modifies the string in place with
-// the appropriate Unicode formatting marks that mark the string direction
-// (either left-to-right or right-to-left). The function checks both the current
-// locale and the contents of the string in order to determine the direction of
-// the returned string. The function returns true if the string in |text| was
-// properly adjusted.
-//
-// Certain LTR strings are not rendered correctly when the context is RTL. For
-// example, the string "Foo!" will appear as "!Foo" if it is rendered as is in
-// an RTL context. Calling this function will make sure the returned localized
-// string is always treated as a right-to-left string. This is done by
-// inserting certain Unicode formatting marks into the returned string.
-//
-// ** Notes about the Windows version of this function:
-// TODO(idana) bug 6806: this function adjusts the string in question only
-// if the current locale is right-to-left. The function does not take care of
-// the opposite case (an RTL string displayed in an LTR context) since
-// adjusting the string involves inserting Unicode formatting characters that
-// Windows does not handle well unless right-to-left language support is
-// installed. Since the English version of Windows doesn't have right-to-left
-// language support installed by default, inserting the direction Unicode mark
-// results in Windows displaying squares.
-BASE_I18N_EXPORT bool AdjustStringForLocaleDirection(string16* text);
-
-// Undoes the actions of the above function (AdjustStringForLocaleDirection).
-BASE_I18N_EXPORT bool UnadjustStringForLocaleDirection(string16* text);
-
-// Returns true if the string contains at least one character with strong right
-// to left directionality; that is, a character with either R or AL Unicode
-// BiDi character type.
-BASE_I18N_EXPORT bool StringContainsStrongRTLChars(const string16& text);
-
-// Wraps a string with an LRE-PDF pair which essentialy marks the string as a
-// Left-To-Right string. Doing this is useful in order to make sure LTR
-// strings are rendered properly in an RTL context.
-BASE_I18N_EXPORT void WrapStringWithLTRFormatting(string16* text);
-
-// Wraps a string with an RLE-PDF pair which essentialy marks the string as a
-// Right-To-Left string. Doing this is useful in order to make sure RTL
-// strings are rendered properly in an LTR context.
-BASE_I18N_EXPORT void WrapStringWithRTLFormatting(string16* text);
-
-// Wraps file path to get it to display correctly in RTL UI. All filepaths
-// should be passed through this function before display in UI for RTL locales.
-BASE_I18N_EXPORT void WrapPathWithLTRFormatting(const FilePath& path,
-                                                string16* rtl_safe_path);
-
-// Return the string in |text| wrapped with LRE (Left-To-Right Embedding) and
-// PDF (Pop Directional Formatting) marks, if needed for UI display purposes.
-BASE_I18N_EXPORT string16 GetDisplayStringInLTRDirectionality(
-    const string16& text) WARN_UNUSED_RESULT;
-
-// Strip the beginning (U+202A..U+202B, U+202D..U+202E) and/or ending (U+202C)
-// explicit bidi control characters from |text|, if there are any. Otherwise,
-// return the text itself. Explicit bidi control characters display and have
-// semantic effect. They can be deleted so they might not always appear in a
-// pair.
-BASE_I18N_EXPORT string16 StripWrappingBidiControlCharacters(
-    const string16& text) WARN_UNUSED_RESULT;
-
-}  // namespace i18n
-}  // namespace base
-
-#endif  // BASE_I18N_RTL_H_
diff --git a/base/message_loop/message_pump_android.cc b/base/message_loop/message_pump_android.cc
index bedb205..a0eee12 100644
--- a/base/message_loop/message_pump_android.cc
+++ b/base/message_loop/message_pump_android.cc
@@ -6,17 +6,14 @@
 
 #include <jni.h>
 
-#include "base/android/java_message_handler_factory.h"
 #include "base/android/jni_android.h"
 #include "base/android/scoped_java_ref.h"
 #include "base/lazy_instance.h"
 #include "base/logging.h"
-#include "base/message_loop/message_loop.h"
 #include "base/run_loop.h"
 #include "base/time/time.h"
 #include "jni/SystemMessageHandler_jni.h"
 
-using base::android::JavaParamRef;
 using base::android::ScopedJavaLocalRef;
 
 // ----------------------------------------------------------------------------
@@ -27,14 +24,10 @@
 static void DoRunLoopOnce(JNIEnv* env,
                           const JavaParamRef<jobject>& obj,
                           jlong native_delegate,
-                          jlong native_message_pump,
                           jlong delayed_scheduled_time_ticks) {
   base::MessagePump::Delegate* delegate =
       reinterpret_cast<base::MessagePump::Delegate*>(native_delegate);
   DCHECK(delegate);
-  base::MessagePumpForUI* pump =
-      reinterpret_cast<base::MessagePumpForUI*>(native_message_pump);
-  DCHECK(pump);
   // This is based on MessagePumpForUI::DoRunLoop() from desktop.
   // Note however that our system queue is handled in the java side.
   // In desktop we inspect and process a single system message and then
@@ -42,11 +35,6 @@
   // On Android, the java message queue may contain messages for other handlers
   // that will be processed before calling here again.
   bool did_work = delegate->DoWork();
-  if (pump->ShouldAbort()) {
-    // There is a pending JNI exception, return to Java so that the exception is
-    // thrown correctly.
-    return;
-  }
 
   // In the java side, |SystemMessageHandler| keeps a single "delayed" message.
   // It's an expensive operation to |removeMessage| there, so this is optimized
@@ -72,11 +60,6 @@
   // avoid comparisons with TimeDelta / Now() (expensive).
   base::TimeTicks next_delayed_work_time;
   did_work |= delegate->DoDelayedWork(&next_delayed_work_time);
-  if (pump->ShouldAbort()) {
-    // There is a pending JNI exception, return to Java so that the exception is
-    // thrown correctly
-    return;
-  }
 
   if (!next_delayed_work_time.is_null()) {
     // Schedule a new message if there's nothing already scheduled or there's a
@@ -98,16 +81,13 @@
     return;
 
   delegate->DoIdleWork();
-  // Note that we do not check whether we should abort here since we are
-  // returning to the JVM anyway. If, in the future, we add any more code after
-  // the call to DoIdleWork() here, we should add an abort-check and return
-  // immediately if the check passes.
 }
 
 namespace base {
 
 MessagePumpForUI::MessagePumpForUI()
-    : run_loop_(nullptr), should_abort_(false) {}
+    : run_loop_(NULL) {
+}
 
 MessagePumpForUI::~MessagePumpForUI() {
 }
@@ -117,7 +97,7 @@
       " test_stub_android.h";
 }
 
-JNIEnv* MessagePumpForUI::StartInternal() {
+void MessagePumpForUI::Start(Delegate* delegate) {
   run_loop_ = new RunLoop();
   // Since the RunLoop was just created above, BeforeRun should be guaranteed to
   // return true (it only returns false if the RunLoop has been Quit already).
@@ -128,23 +108,10 @@
 
   JNIEnv* env = base::android::AttachCurrentThread();
   DCHECK(env);
-  return env;
-}
 
-void MessagePumpForUI::Start(Delegate* delegate) {
-  JNIEnv* env = StartInternal();
-  system_message_handler_obj_.Reset(Java_SystemMessageHandler_create(
-      env, reinterpret_cast<intptr_t>(delegate),
-      reinterpret_cast<intptr_t>(this)));
-}
-
-void MessagePumpForUI::StartForUnitTest(
-    Delegate* delegate,
-    base::android::JavaMessageHandlerFactory* factory,
-    WaitableEvent* test_done_event) {
-  JNIEnv* env = StartInternal();
   system_message_handler_obj_.Reset(
-      factory->CreateMessageHandler(env, delegate, this, test_done_event));
+      Java_SystemMessageHandler_create(
+          env, reinterpret_cast<intptr_t>(delegate)));
 }
 
 void MessagePumpForUI::Quit() {
@@ -152,8 +119,8 @@
     JNIEnv* env = base::android::AttachCurrentThread();
     DCHECK(env);
 
-    Java_SystemMessageHandler_removeAllPendingMessages(
-        env, system_message_handler_obj_);
+    Java_SystemMessageHandler_removeAllPendingMessages(env,
+        system_message_handler_obj_.obj());
     system_message_handler_obj_.Reset();
   }
 
@@ -170,7 +137,8 @@
   JNIEnv* env = base::android::AttachCurrentThread();
   DCHECK(env);
 
-  Java_SystemMessageHandler_scheduleWork(env, system_message_handler_obj_);
+  Java_SystemMessageHandler_scheduleWork(env,
+      system_message_handler_obj_.obj());
 }
 
 void MessagePumpForUI::ScheduleDelayedWork(const TimeTicks& delayed_work_time) {
@@ -183,9 +151,9 @@
       (delayed_work_time - TimeTicks::Now()).InMillisecondsRoundedUp();
   // Note that we're truncating to milliseconds as required by the java side,
   // even though delayed_work_time is microseconds resolution.
-  Java_SystemMessageHandler_scheduleDelayedWork(
-      env, system_message_handler_obj_, delayed_work_time.ToInternalValue(),
-      millis);
+  Java_SystemMessageHandler_scheduleDelayedWork(env,
+      system_message_handler_obj_.obj(),
+      delayed_work_time.ToInternalValue(), millis);
 }
 
 // static
diff --git a/base/message_loop/message_pump_android.h b/base/message_loop/message_pump_android.h
index e4adaf6..795bd5e 100644
--- a/base/message_loop/message_pump_android.h
+++ b/base/message_loop/message_pump_android.h
@@ -15,13 +15,8 @@
 
 namespace base {
 
-namespace android {
-class JavaMessageHandlerFactory;
-}
-
 class RunLoop;
 class TimeTicks;
-class WaitableEvent;
 
 // This class implements a MessagePump needed for TYPE_UI MessageLoops on
 // OS_ANDROID platform.
@@ -36,25 +31,12 @@
   void ScheduleDelayedWork(const TimeTicks& delayed_work_time) override;
 
   virtual void Start(Delegate* delegate);
-  void StartForUnitTest(Delegate* delegate,
-                        base::android::JavaMessageHandlerFactory* factory,
-                        WaitableEvent* test_done_event);
-
-  // We call Abort when there is a pending JNI exception, meaning that the
-  // current thread will crash when we return to Java.
-  // We can't call any JNI-methods before returning to Java as we would then
-  // cause a native crash (instead of the original Java crash).
-  void Abort() { should_abort_ = true; }
-  bool ShouldAbort() const { return should_abort_; }
 
   static bool RegisterBindings(JNIEnv* env);
 
  private:
-  JNIEnv* StartInternal();
-
   RunLoop* run_loop_;
   base::android::ScopedJavaGlobalRef<jobject> system_message_handler_obj_;
-  bool should_abort_;
 
   DISALLOW_COPY_AND_ASSIGN(MessagePumpForUI);
 };
diff --git a/base/path_service.cc b/base/path_service.cc
index 1b9d394..3f954d7 100644
--- a/base/path_service.cc
+++ b/base/path_service.cc
@@ -13,6 +13,7 @@
 #include "base/containers/hash_tables.h"
 #include "base/files/file_path.h"
 #include "base/files/file_util.h"
+#include "base/lazy_instance.h"
 #include "base/logging.h"
 #include "base/synchronization/lock.h"
 #include "build/build_config.h"
@@ -128,9 +129,10 @@
   }
 };
 
+static LazyInstance<PathData>::Leaky g_path_data = LAZY_INSTANCE_INITIALIZER;
+
 static PathData* GetPathData() {
-  static auto* path_data = new PathData();
-  return path_data;
+  return g_path_data.Pointer();
 }
 
 // Tries to find |key| in the cache. |path_data| should be locked by the caller!
diff --git a/base/threading/thread_local_android.cc b/base/threading/thread_local_android.cc
new file mode 100644
index 0000000..813dd78
--- /dev/null
+++ b/base/threading/thread_local_android.cc
@@ -0,0 +1,31 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "base/threading/thread_local.h"
+
+namespace base {
+namespace internal {
+
+// static
+void ThreadLocalPlatform::AllocateSlot(SlotType* slot) {
+  slot->Initialize(nullptr);
+}
+
+// static
+void ThreadLocalPlatform::FreeSlot(SlotType slot) {
+  slot.Free();
+}
+
+// static
+void* ThreadLocalPlatform::GetValueFromSlot(SlotType slot) {
+  return slot.Get();
+}
+
+// static
+void ThreadLocalPlatform::SetValueInSlot(SlotType slot, void* value) {
+  slot.Set(value);
+}
+
+}  // namespace internal
+}  // namespace base
diff --git a/base/trace_event/trace_event_android.cc b/base/trace_event/trace_event_android.cc
index 0a4e6ea..a28c54a 100644
--- a/base/trace_event/trace_event_android.cc
+++ b/base/trace_event/trace_event_android.cc
@@ -13,7 +13,6 @@
 #include "base/posix/eintr_wrapper.h"
 #include "base/strings/stringprintf.h"
 #include "base/synchronization/waitable_event.h"
-#include "base/threading/thread.h"
 #include "base/trace_event/trace_event.h"
 
 namespace base {
diff --git a/base/unguessable_token.cc b/base/unguessable_token.cc
deleted file mode 100644
index cd9830e..0000000
--- a/base/unguessable_token.cc
+++ /dev/null
@@ -1,41 +0,0 @@
-// Copyright 2016 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/unguessable_token.h"
-
-#include "base/format_macros.h"
-#include "base/rand_util.h"
-#include "base/strings/stringprintf.h"
-
-namespace base {
-
-UnguessableToken::UnguessableToken(uint64_t high, uint64_t low)
-    : high_(high), low_(low) {}
-
-std::string UnguessableToken::ToString() const {
-  return base::StringPrintf("(%08" PRIX64 "%08" PRIX64 ")", high_, low_);
-}
-
-// static
-UnguessableToken UnguessableToken::Create() {
-  UnguessableToken token;
-  // Use base::RandBytes instead of crypto::RandBytes, because crypto calls the
-  // base version directly, and to prevent the dependency from base/ to crypto/.
-  base::RandBytes(&token, sizeof(token));
-  return token;
-}
-
-// static
-UnguessableToken UnguessableToken::Deserialize(uint64_t high, uint64_t low) {
-  // Receiving a zeroed out UnguessableToken from another process means that it
-  // was never initialized via Create(). Treat this case as a security issue.
-  DCHECK(!(high == 0 && low == 0));
-  return UnguessableToken(high, low);
-}
-
-std::ostream& operator<<(std::ostream& out, const UnguessableToken& token) {
-  return out << token.ToString();
-}
-
-}  // namespace base
diff --git a/base/unguessable_token.h b/base/unguessable_token.h
deleted file mode 100644
index 9f38783..0000000
--- a/base/unguessable_token.h
+++ /dev/null
@@ -1,103 +0,0 @@
-// Copyright 2016 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_UNGUESSABLE_TOKEN_H_
-#define BASE_UNGUESSABLE_TOKEN_H_
-
-#include <stdint.h>
-#include <string.h>
-#include <iosfwd>
-#include <tuple>
-
-#include "base/base_export.h"
-#include "base/hash.h"
-#include "base/logging.h"
-
-namespace base {
-
-struct UnguessableTokenHash;
-
-// A UnguessableToken is an 128-bit token generated from a cryptographically
-// strong random source.
-//
-// UnguessableToken should be used when a sensitive ID needs to be unguessable,
-// and is shared across processes. It can be used as part of a larger aggregate
-// type, or as an ID in and of itself.
-//
-// Use Create() for creating new UnguessableTokens.
-//
-// NOTE: It is illegal to send empty UnguessableTokens across processes, and
-// sending/receiving empty tokens should be treated as a security issue.
-// If there is a valid scenario for sending "no token" across processes,
-// base::Optional should be used instead of an empty token.
-class BASE_EXPORT UnguessableToken {
- public:
-  // Create a unique UnguessableToken.
-  static UnguessableToken Create();
-
-  // Return a UnguessableToken built from the high/low bytes provided.
-  // It should only be used in deserialization scenarios.
-  //
-  // NOTE: If the deserialized token is empty, it means that it was never
-  // initialized via Create(). This is a security issue, and should be handled.
-  static UnguessableToken Deserialize(uint64_t high, uint64_t low);
-
-  // Creates an empty UnguessableToken.
-  // Assign to it with Create() before using it.
-  constexpr UnguessableToken() = default;
-
-  // NOTE: Serializing an empty UnguessableToken is an illegal operation.
-  uint64_t GetHighForSerialization() const {
-    DCHECK(!is_empty());
-    return high_;
-  };
-
-  // NOTE: Serializing an empty UnguessableToken is an illegal operation.
-  uint64_t GetLowForSerialization() const {
-    DCHECK(!is_empty());
-    return low_;
-  }
-
-  bool is_empty() const { return high_ == 0 && low_ == 0; }
-
-  std::string ToString() const;
-
-  explicit operator bool() const { return !is_empty(); }
-
-  bool operator<(const UnguessableToken& other) const {
-    return std::tie(high_, low_) < std::tie(other.high_, other.low_);
-  }
-
-  bool operator==(const UnguessableToken& other) const {
-    return high_ == other.high_ && low_ == other.low_;
-  }
-
-  bool operator!=(const UnguessableToken& other) const {
-    return !(*this == other);
-  }
-
- private:
-  friend struct UnguessableTokenHash;
-  UnguessableToken(uint64_t high, uint64_t low);
-
-  // Note: Two uint64_t are used instead of uint8_t[16], in order to have a
-  // simpler ToString() and is_empty().
-  uint64_t high_ = 0;
-  uint64_t low_ = 0;
-};
-
-BASE_EXPORT std::ostream& operator<<(std::ostream& out,
-                                     const UnguessableToken& token);
-
-// For use in std::unordered_map.
-struct UnguessableTokenHash {
-  size_t operator()(const base::UnguessableToken& token) const {
-    DCHECK(token);
-    return base::HashInts64(token.high_, token.low_);
-  }
-};
-
-}  // namespace base
-
-#endif  // BASE_UNGUESSABLE_TOKEN_H_