Build native android graphics library for desktop

The purpose of this is to be able to use the native graphics code from
the Android platform directly in Android Studio (running on desktop) to
do layout rendering.

This creates a host library that is a subset of libandroid_runtime
including only the JNI files relevant to Android graphics. It also
includes LayoutlibLoader.cpp which is used to load the JNI when using
it as part of layoutlib (the graphics library for Android Studio).

This also creates libhwui-host, a host library that is a subset of
libhwui.

Bug: 117921091
Test: lunch sdk && m libandroid_runtime
Change-Id: I3850020d2d4c13c85e377476bc463d3eb6a01c6d
diff --git a/core/jni/Android.bp b/core/jni/Android.bp
index 0e31ab9..6301db0 100644
--- a/core/jni/Android.bp
+++ b/core/jni/Android.bp
@@ -10,7 +10,7 @@
 
 cc_library_shared {
     name: "libandroid_runtime",
-
+    host_supported: true,
     cflags: [
         "-Wno-unused-parameter",
         "-Wno-non-virtual-dtor",
@@ -32,189 +32,43 @@
     cppflags: ["-Wno-conversion-null"],
 
     srcs: [
-        "AndroidRuntime.cpp",
-        "com_android_internal_content_NativeLibraryHelper.cpp",
-        "com_google_android_gles_jni_EGLImpl.cpp",
-        "com_google_android_gles_jni_GLImpl.cpp", // TODO: .arm
-        "android_app_Activity.cpp",
-        "android_app_ActivityThread.cpp",
-        "android_app_NativeActivity.cpp",
-        "android_app_admin_SecurityLog.cpp",
-        "android_opengl_EGL14.cpp",
-        "android_opengl_EGL15.cpp",
-        "android_opengl_EGLExt.cpp",
-        "android_opengl_GLES10.cpp",
-        "android_opengl_GLES10Ext.cpp",
-        "android_opengl_GLES11.cpp",
-        "android_opengl_GLES11Ext.cpp",
-        "android_opengl_GLES20.cpp",
-        "android_opengl_GLES30.cpp",
-        "android_opengl_GLES31.cpp",
-        "android_opengl_GLES31Ext.cpp",
-        "android_opengl_GLES32.cpp",
-        "android_database_CursorWindow.cpp",
-        "android_database_SQLiteCommon.cpp",
-        "android_database_SQLiteConnection.cpp",
-        "android_database_SQLiteGlobal.cpp",
-        "android_database_SQLiteDebug.cpp",
+        "android_animation_PropertyValuesHolder.cpp",
         "android_graphics_Canvas.cpp",
         "android_graphics_ColorSpace.cpp",
         "android_graphics_drawable_AnimatedVectorDrawable.cpp",
         "android_graphics_drawable_VectorDrawable.cpp",
         "android_graphics_Picture.cpp",
-        "android_view_CompositionSamplingListener.cpp",
-        "android_view_DisplayEventReceiver.cpp",
-        "android_view_DisplayListCanvas.cpp",
-        "android_view_TextureLayer.cpp",
-        "android_view_InputChannel.cpp",
-        "android_view_InputDevice.cpp",
-        "android_view_InputEventReceiver.cpp",
-        "android_view_InputEventSender.cpp",
-        "android_view_InputQueue.cpp",
-        "android_view_KeyCharacterMap.cpp",
-        "android_view_KeyEvent.cpp",
-        "android_view_MotionEvent.cpp",
-        "android_view_PointerIcon.cpp",
-        "android_view_RenderNode.cpp",
-        "android_view_RenderNodeAnimator.cpp",
-        "android_view_Surface.cpp",
-        "android_view_SurfaceControl.cpp",
-        "android_view_SurfaceSession.cpp",
-        "android_view_TextureView.cpp",
-        "android_view_ThreadedRenderer.cpp",
-        "android_view_VelocityTracker.cpp",
-        "android_text_AndroidCharacter.cpp",
-        "android_text_Hyphenator.cpp",
-        "android_os_Debug.cpp",
-        "android_os_GraphicsEnvironment.cpp",
-        "android_os_HidlSupport.cpp",
-        "android_os_HwBinder.cpp",
-        "android_os_HwBlob.cpp",
-        "android_os_HwParcel.cpp",
-        "android_os_HwRemoteBinder.cpp",
-        "android_os_NativeHandle.cpp",
-        "android_os_MemoryFile.cpp",
-        "android_os_MessageQueue.cpp",
-        "android_os_Parcel.cpp",
-        "android_os_SELinux.cpp",
-        "android_os_SharedMemory.cpp",
-        "android_os_SystemClock.cpp",
-        "android_os_SystemProperties.cpp",
-        "android_os_Trace.cpp",
-        "android_os_UEventObserver.cpp",
-        "android_os_VintfObject.cpp",
-        "android_os_VintfRuntimeInfo.cpp",
-        "android_net_LocalSocketImpl.cpp",
-        "android_net_NetUtils.cpp",
         "android_nio_utils.cpp",
-        "android_util_AssetManager.cpp",
-        "android_util_Binder.cpp",
-        "android_util_EventLog.cpp",
-        "android_util_Log.cpp",
-        "android_util_StatsLog.cpp",
-        "android_util_MemoryIntArray.cpp",
         "android_util_PathParser.cpp",
-        "android_util_Process.cpp",
-        "android_util_StringBlock.cpp",
-        "android_util_XmlBlock.cpp",
-        "android_util_jar_StrictJarFile.cpp",
-        "android/graphics/AnimatedImageDrawable.cpp",
         "android/graphics/Bitmap.cpp",
         "android/graphics/BitmapFactory.cpp",
         "android/graphics/ByteBufferStreamAdaptor.cpp",
-        "android/graphics/Camera.cpp",
-        "android/graphics/CanvasProperty.cpp",
         "android/graphics/ColorFilter.cpp",
+        "android/graphics/CreateJavaOutputStreamAdaptor.cpp",
         "android/graphics/FontFamily.cpp",
         "android/graphics/FontUtils.cpp",
-        "android/graphics/CreateJavaOutputStreamAdaptor.cpp",
-        "android/graphics/GIFMovie.cpp",
-        "android/graphics/GraphicBuffer.cpp",
         "android/graphics/Graphics.cpp",
         "android/graphics/ImageDecoder.cpp",
-        "android/graphics/Interpolator.cpp",
         "android/graphics/MaskFilter.cpp",
         "android/graphics/Matrix.cpp",
-        "android/graphics/Movie.cpp",
-        "android/graphics/MovieImpl.cpp",
         "android/graphics/NinePatch.cpp",
         "android/graphics/NinePatchPeeker.cpp",
         "android/graphics/Paint.cpp",
         "android/graphics/PaintFilter.cpp",
         "android/graphics/Path.cpp",
-        "android/graphics/PathMeasure.cpp",
         "android/graphics/PathEffect.cpp",
+        "android/graphics/PathMeasure.cpp",
         "android/graphics/Picture.cpp",
-        "android/graphics/BitmapRegionDecoder.cpp",
         "android/graphics/Region.cpp",
         "android/graphics/Shader.cpp",
-        "android/graphics/SurfaceTexture.cpp",
         "android/graphics/Typeface.cpp",
         "android/graphics/Utils.cpp",
-        "android/graphics/YuvToJpegEncoder.cpp",
         "android/graphics/fonts/Font.cpp",
         "android/graphics/fonts/FontFamily.cpp",
-        "android/graphics/pdf/PdfDocument.cpp",
-        "android/graphics/pdf/PdfEditor.cpp",
-        "android/graphics/pdf/PdfRenderer.cpp",
-        "android/graphics/pdf/PdfUtils.cpp",
         "android/graphics/text/LineBreaker.cpp",
         "android/graphics/text/MeasuredText.cpp",
-        "android_media_AudioEffectDescriptor.cpp",
-        "android_media_AudioRecord.cpp",
-        "android_media_AudioSystem.cpp",
-        "android_media_AudioTrack.cpp",
-        "android_media_AudioAttributes.cpp",
-        "android_media_AudioProductStrategies.cpp",
-        "android_media_AudioVolumeGroups.cpp",
-        "android_media_AudioVolumeGroupCallback.cpp",
-        "android_media_DeviceCallback.cpp",
-        "android_media_JetPlayer.cpp",
-        "android_media_MediaMetricsJNI.cpp",
-        "android_media_MicrophoneInfo.cpp",
-        "android_media_midi.cpp",
-        "android_media_RemoteDisplay.cpp",
-        "android_media_ToneGenerator.cpp",
-        "android_hardware_Camera.cpp",
-        "android_hardware_camera2_CameraMetadata.cpp",
-        "android_hardware_camera2_legacy_LegacyCameraDevice.cpp",
-        "android_hardware_camera2_legacy_PerfMeasurement.cpp",
-        "android_hardware_camera2_DngCreator.cpp",
-        "android_hardware_display_DisplayViewport.cpp",
-        "android_hardware_HardwareBuffer.cpp",
-        "android_hardware_SensorManager.cpp",
-        "android_hardware_SerialPort.cpp",
-        "android_hardware_SoundTrigger.cpp",
-        "android_hardware_UsbDevice.cpp",
-        "android_hardware_UsbDeviceConnection.cpp",
-        "android_hardware_UsbRequest.cpp",
-        "android_hardware_location_ActivityRecognitionHardware.cpp",
-        "android_util_FileObserver.cpp",
-        "android/opengl/poly_clip.cpp", // TODO: .arm
-        "android/opengl/util.cpp",
-        "android_server_NetworkManagementSocketTagger.cpp",
-        "android_ddm_DdmHandleNativeHeap.cpp",
-        "android_backup_BackupDataInput.cpp",
-        "android_backup_BackupDataOutput.cpp",
-        "android_backup_FileBackupHelperBase.cpp",
-        "android_backup_BackupHelperDispatcher.cpp",
-        "android_app_backup_FullBackup.cpp",
-        "android_content_res_ApkAssets.cpp",
-        "android_content_res_ObbScanner.cpp",
-        "android_content_res_Configuration.cpp",
-        "android_animation_PropertyValuesHolder.cpp",
-        "android_security_Scrypt.cpp",
-        "com_android_internal_os_AtomicDirectory.cpp",
-        "com_android_internal_os_ClassLoaderFactory.cpp",
-        "com_android_internal_os_FuseAppLoop.cpp",
-        "com_android_internal_os_Zygote.cpp",
-        "com_android_internal_os_ZygoteInit.cpp",
         "com_android_internal_util_VirtualRefBasePtr.cpp",
         "com_android_internal_view_animation_NativeInterpolatorFactoryHelper.cpp",
-        "hwbinder/EphemeralStorage.cpp",
-        "fd_utils.cpp",
-        "android_hardware_input_InputWindowHandle.cpp",
-        "android_hardware_input_InputApplicationHandle.cpp",
     ],
 
     include_dirs: [
@@ -233,95 +87,271 @@
         "system/media/private/camera/include",
     ],
 
-    static_libs: [
-        "libasync_safe",
-        "libgif",
-        "libseccomp_policy",
-        "libgrallocusage",
-        "libscrypt_static",
-        "libstatssocket",
-    ],
-
     shared_libs: [
-        "libbpf_android",
-        "libnetdbpf",
-        "libnetdutils",
-        "libmemtrack",
-        "libandroidfw",
-        "libappfuse",
-        "libbase",
-        "libcrypto",
-        "libnativehelper",
-        "liblog",
-        "libcutils",
-        "libdebuggerd_client",
-        "libutils",
-        "libbinder",
-        "libui",
-        "libgraphicsenv",
-        "libgui",
-        "libsensor",
-        "libinput",
-        "libcamera_client",
-        "libcamera_metadata",
-        "libsqlite",
-        "libEGL",
-        "libGLESv1_CM",
-        "libGLESv2",
-        "libGLESv3",
-        "libvulkan",
-        "libziparchive",
-        "libETC1",
-        "libhardware",
-        "libhardware_legacy",
-        "libselinux",
         "libandroidicu",
-        "libmedia",
-        "libmedia_helper",
-        "libmediametrics",
-        "libmeminfo",
-        "libaudioclient",
-        "libaudiopolicy",
-        "libjpeg",
-        "libusbhost",
+        "libbase",
+        "libcutils",
         "libharfbuzz_ng",
-        "libz",
-        "libpdfium",
-        "libimg_utils",
-        "libnetd_client",
-        "libsoundtrigger",
+        "liblog",
         "libminikin",
-        "libprocessgroup",
-        "libnativebridge_lazy",
-        "libnativeloader_lazy",
-        "libmemunreachable",
-        "libhidlbase",
-        "libhidltransport",
-        "libhwbinder",
-        "libvintf",
-        "libnativewindow",
-        "libhwui",
-        "libdl",
-        "libdl_android",
-        "libstatslog",
-        "server_configurable_flags",
+        "libnativehelper",
+        "libz",
+        "libziparchive",
     ],
 
-    generated_sources: ["android_util_StatsLogInternal.cpp"],
-
     local_include_dirs: ["android/graphics"],
     export_include_dirs: [
         ".",
         "include",
     ],
-    export_shared_lib_headers: [
-        // AndroidRuntime.h depends on nativehelper/jni.h
-        "libnativehelper",
 
-        // our headers include libnativewindow's public headers
-        "libnativewindow",
+    target: {
+        android: {
+            srcs: [
+                "AndroidRuntime.cpp",
+                "com_android_internal_content_NativeLibraryHelper.cpp",
+                "com_google_android_gles_jni_EGLImpl.cpp",
+                "com_google_android_gles_jni_GLImpl.cpp", // TODO: .arm
+                "android_app_Activity.cpp",
+                "android_app_ActivityThread.cpp",
+                "android_app_NativeActivity.cpp",
+                "android_app_admin_SecurityLog.cpp",
+                "android_opengl_EGL14.cpp",
+                "android_opengl_EGL15.cpp",
+                "android_opengl_EGLExt.cpp",
+                "android_opengl_GLES10.cpp",
+                "android_opengl_GLES10Ext.cpp",
+                "android_opengl_GLES11.cpp",
+                "android_opengl_GLES11Ext.cpp",
+                "android_opengl_GLES20.cpp",
+                "android_opengl_GLES30.cpp",
+                "android_opengl_GLES31.cpp",
+                "android_opengl_GLES31Ext.cpp",
+                "android_opengl_GLES32.cpp",
+                "android_database_CursorWindow.cpp",
+                "android_database_SQLiteCommon.cpp",
+                "android_database_SQLiteConnection.cpp",
+                "android_database_SQLiteGlobal.cpp",
+                "android_database_SQLiteDebug.cpp",
+                "android_view_CompositionSamplingListener.cpp",
+                "android_view_DisplayEventReceiver.cpp",
+                "android_view_DisplayListCanvas.cpp",
+                "android_view_TextureLayer.cpp",
+                "android_view_InputChannel.cpp",
+                "android_view_InputDevice.cpp",
+                "android_view_InputEventReceiver.cpp",
+                "android_view_InputEventSender.cpp",
+                "android_view_InputQueue.cpp",
+                "android_view_KeyCharacterMap.cpp",
+                "android_view_KeyEvent.cpp",
+                "android_view_MotionEvent.cpp",
+                "android_view_PointerIcon.cpp",
+                "android_view_RenderNode.cpp",
+                "android_view_RenderNodeAnimator.cpp",
+                "android_view_Surface.cpp",
+                "android_view_SurfaceControl.cpp",
+                "android_view_SurfaceSession.cpp",
+                "android_view_TextureView.cpp",
+                "android_view_ThreadedRenderer.cpp",
+                "android_view_VelocityTracker.cpp",
+                "android_text_AndroidCharacter.cpp",
+                "android_text_Hyphenator.cpp",
+                "android_os_Debug.cpp",
+                "android_os_GraphicsEnvironment.cpp",
+                "android_os_HidlSupport.cpp",
+                "android_os_HwBinder.cpp",
+                "android_os_HwBlob.cpp",
+                "android_os_HwParcel.cpp",
+                "android_os_HwRemoteBinder.cpp",
+                "android_os_NativeHandle.cpp",
+                "android_os_MemoryFile.cpp",
+                "android_os_MessageQueue.cpp",
+                "android_os_Parcel.cpp",
+                "android_os_SELinux.cpp",
+                "android_os_SharedMemory.cpp",
+                "android_os_SystemClock.cpp",
+                "android_os_SystemProperties.cpp",
+                "android_os_Trace.cpp",
+                "android_os_UEventObserver.cpp",
+                "android_os_VintfObject.cpp",
+                "android_os_VintfRuntimeInfo.cpp",
+                "android_net_LocalSocketImpl.cpp",
+                "android_net_NetUtils.cpp",
+                "android_util_AssetManager.cpp",
+                "android_util_Binder.cpp",
+                "android_util_EventLog.cpp",
+                "android_util_Log.cpp",
+                "android_util_StatsLog.cpp",
+                "android_util_MemoryIntArray.cpp",
+                "android_util_Process.cpp",
+                "android_util_StringBlock.cpp",
+                "android_util_XmlBlock.cpp",
+                "android_util_jar_StrictJarFile.cpp",
+                "android/graphics/AnimatedImageDrawable.cpp",
+                "android/graphics/Camera.cpp",
+                "android/graphics/CanvasProperty.cpp",
+                "android/graphics/GIFMovie.cpp",
+                "android/graphics/GraphicBuffer.cpp",
+                "android/graphics/Interpolator.cpp",
+                "android/graphics/Movie.cpp",
+                "android/graphics/MovieImpl.cpp",
+                "android/graphics/BitmapRegionDecoder.cpp",
+                "android/graphics/SurfaceTexture.cpp",
+                "android/graphics/YuvToJpegEncoder.cpp",
+                "android/graphics/pdf/PdfDocument.cpp",
+                "android/graphics/pdf/PdfEditor.cpp",
+                "android/graphics/pdf/PdfRenderer.cpp",
+                "android/graphics/pdf/PdfUtils.cpp",
+                "android_media_AudioEffectDescriptor.cpp",
+                "android_media_AudioRecord.cpp",
+                "android_media_AudioSystem.cpp",
+                "android_media_AudioTrack.cpp",
+                "android_media_AudioAttributes.cpp",
+                "android_media_AudioProductStrategies.cpp",
+                "android_media_AudioVolumeGroups.cpp",
+                "android_media_AudioVolumeGroupCallback.cpp",
+                "android_media_DeviceCallback.cpp",
+                "android_media_JetPlayer.cpp",
+                "android_media_MediaMetricsJNI.cpp",
+                "android_media_MicrophoneInfo.cpp",
+                "android_media_midi.cpp",
+                "android_media_RemoteDisplay.cpp",
+                "android_media_ToneGenerator.cpp",
+                "android_hardware_Camera.cpp",
+                "android_hardware_camera2_CameraMetadata.cpp",
+                "android_hardware_camera2_legacy_LegacyCameraDevice.cpp",
+                "android_hardware_camera2_legacy_PerfMeasurement.cpp",
+                "android_hardware_camera2_DngCreator.cpp",
+                "android_hardware_display_DisplayViewport.cpp",
+                "android_hardware_HardwareBuffer.cpp",
+                "android_hardware_SensorManager.cpp",
+                "android_hardware_SerialPort.cpp",
+                "android_hardware_SoundTrigger.cpp",
+                "android_hardware_UsbDevice.cpp",
+                "android_hardware_UsbDeviceConnection.cpp",
+                "android_hardware_UsbRequest.cpp",
+                "android_hardware_location_ActivityRecognitionHardware.cpp",
+                "android_util_FileObserver.cpp",
+                "android/opengl/poly_clip.cpp", // TODO: .arm
+                "android/opengl/util.cpp",
+                "android_server_NetworkManagementSocketTagger.cpp",
+                "android_ddm_DdmHandleNativeHeap.cpp",
+                "android_backup_BackupDataInput.cpp",
+                "android_backup_BackupDataOutput.cpp",
+                "android_backup_FileBackupHelperBase.cpp",
+                "android_backup_BackupHelperDispatcher.cpp",
+                "android_app_backup_FullBackup.cpp",
+                "android_content_res_ApkAssets.cpp",
+                "android_content_res_ObbScanner.cpp",
+                "android_content_res_Configuration.cpp",
+                "android_security_Scrypt.cpp",
+                "com_android_internal_os_AtomicDirectory.cpp",
+                "com_android_internal_os_ClassLoaderFactory.cpp",
+                "com_android_internal_os_FuseAppLoop.cpp",
+                "com_android_internal_os_Zygote.cpp",
+                "com_android_internal_os_ZygoteInit.cpp",
+                "hwbinder/EphemeralStorage.cpp",
+                "fd_utils.cpp",
+                "android_hardware_input_InputWindowHandle.cpp",
+                "android_hardware_input_InputApplicationHandle.cpp",
+            ],
 
-        // GraphicsJNI.h includes hwui headers
-        "libhwui",
-    ],
-}
+            static_libs: [
+                "libasync_safe",
+                "libgif",
+                "libseccomp_policy",
+                "libgrallocusage",
+                "libscrypt_static",
+                "libstatssocket",
+            ],
+
+            shared_libs: [
+                "libbpf_android",
+                "libnetdbpf",
+                "libnetdutils",
+                "libmemtrack",
+                "libandroidfw",
+                "libappfuse",
+                "libcrypto",
+                "libcutils",
+                "libdebuggerd_client",
+                "libutils",
+                "libbinder",
+                "libui",
+                "libgraphicsenv",
+                "libgui",
+                "libsensor",
+                "libinput",
+                "libcamera_client",
+                "libcamera_metadata",
+                "libsqlite",
+                "libEGL",
+                "libGLESv1_CM",
+                "libGLESv2",
+                "libGLESv3",
+                "libvulkan",
+                "libETC1",
+                "libhardware",
+                "libhardware_legacy",
+                "libselinux",
+                "libmedia",
+                "libmedia_helper",
+                "libmediametrics",
+                "libmeminfo",
+                "libaudioclient",
+                "libaudiopolicy",
+                "libjpeg",
+                "libusbhost",
+                "libpdfium",
+                "libimg_utils",
+                "libnetd_client",
+                "libsoundtrigger",
+                "libprocessgroup",
+                "libnativebridge_lazy",
+                "libnativeloader_lazy",
+                "libmemunreachable",
+                "libhidlbase",
+                "libhidltransport",
+                "libhwbinder",
+                "libvintf",
+                "libnativewindow",
+                "libhwui",
+                "libdl",
+                "libdl_android",
+                "libstatslog",
+                "server_configurable_flags",
+            ],
+            export_shared_lib_headers: [
+                // AndroidRuntime.h depends on nativehelper/jni.h
+                "libnativehelper",
+
+                // our headers include libnativewindow's public headers
+                "libnativewindow",
+
+                // GraphicsJNI.h includes hwui headers
+                "libhwui",
+            ],
+            generated_sources: ["android_util_StatsLogInternal.cpp"],
+        },
+        host: {
+            cflags: [
+                "-Wno-unused-const-variable",
+                "-Wno-unused-function",
+            ],
+            srcs: [
+                "LayoutlibLoader.cpp",
+            ],
+            include_dirs: [
+                "external/vulkan-headers/include",
+            ],
+            shared_libs: [
+                "libhwui-host",
+            ],
+            static_libs: [
+                "libandroidfw",
+                "libcompiler_rt",
+                "libutils",
+            ],
+        },
+    },
+}
\ No newline at end of file
diff --git a/core/jni/Android.mk b/core/jni/Android.mk
new file mode 100644
index 0000000..17b9a65
--- /dev/null
+++ b/core/jni/Android.mk
@@ -0,0 +1,42 @@
+#
+# Copyright (C) 2008 The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#      http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+LOCAL_PATH := $(call my-dir)
+my_native_layoutlib_dependencies := \
+    libandroid_runtime \
+    libandroidicu-host \
+    libbase \
+    libc++ \
+    libcutils \
+    libdng_sdk \
+    libexpat-host \
+    libft2 \
+    libharfbuzz_ng \
+    libhwui-host \
+    libicui18n-host \
+    libicuuc-host \
+    libjpeg \
+    liblog \
+    libminikin \
+    libnativehelper \
+    libpiex \
+    libpng \
+    libz-host \
+    libziparchive
+$(call dist-for-goals, layoutlib, \
+    $(foreach m,$(my_native_layoutlib_dependencies), \
+    $(HOST_LIBRARY_PATH)/$(m)$(HOST_SHLIB_SUFFIX):layoutlib_native/$(m)$(HOST_SHLIB_SUFFIX)))
+$(call dist-for-goals, layoutlib, $(HOST_OUT)/com.android.runtime/etc/icu/icudt63l.dat:layoutlib_native/icu/icudt63l.dat)
+my_native_layoutlib_dependencies :=
\ No newline at end of file
diff --git a/core/jni/AndroidRuntime.cpp b/core/jni/AndroidRuntime.cpp
index f266502..785b7a5 100644
--- a/core/jni/AndroidRuntime.cpp
+++ b/core/jni/AndroidRuntime.cpp
@@ -1235,6 +1235,10 @@
     // If AndroidRuntime had anything to do here, we'd have done it in 'start'.
 }
 
+/*static*/ JavaVM* AndroidRuntime::getJavaVM() {
+    return AndroidRuntime::mJavaVM;
+}
+
 /*
  * Get the JNIEnv pointer for this thread.
  *
diff --git a/core/jni/LayoutlibLoader.cpp b/core/jni/LayoutlibLoader.cpp
new file mode 100644
index 0000000..b0dbb68
--- /dev/null
+++ b/core/jni/LayoutlibLoader.cpp
@@ -0,0 +1,204 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "jni.h"
+#include "core_jni_helpers.h"
+
+#include <unicode/putil.h>
+#include <vector>
+
+using namespace std;
+
+/*
+ * This is responsible for setting up the JNI environment for communication between
+ * the Java and native parts of layoutlib, including registering native methods.
+ * This is mostly achieved by copying the way it is done in the platform
+ * (see AndroidRuntime.cpp).
+ */
+
+static JavaVM* javaVM;
+
+extern int register_android_graphics_Bitmap(JNIEnv*);
+extern int register_android_graphics_BitmapFactory(JNIEnv*);
+extern int register_android_graphics_ByteBufferStreamAdaptor(JNIEnv* env);
+extern int register_android_graphics_CreateJavaOutputStreamAdaptor(JNIEnv* env);
+extern int register_android_graphics_Graphics(JNIEnv* env);
+extern int register_android_graphics_ImageDecoder(JNIEnv*);
+extern int register_android_graphics_MaskFilter(JNIEnv* env);
+extern int register_android_graphics_NinePatch(JNIEnv*);
+extern int register_android_graphics_PathEffect(JNIEnv* env);
+extern int register_android_graphics_Shader(JNIEnv* env);
+extern int register_android_graphics_Typeface(JNIEnv* env);
+
+namespace android {
+
+extern int register_android_animation_PropertyValuesHolder(JNIEnv *env);
+extern int register_android_graphics_Canvas(JNIEnv* env);
+extern int register_android_graphics_ColorFilter(JNIEnv* env);
+extern int register_android_graphics_ColorSpace(JNIEnv* env);
+extern int register_android_graphics_DrawFilter(JNIEnv* env);
+extern int register_android_graphics_FontFamily(JNIEnv* env);
+extern int register_android_graphics_Matrix(JNIEnv* env);
+extern int register_android_graphics_Paint(JNIEnv* env);
+extern int register_android_graphics_Path(JNIEnv* env);
+extern int register_android_graphics_PathMeasure(JNIEnv* env);
+extern int register_android_graphics_Picture(JNIEnv* env);
+extern int register_android_graphics_Region(JNIEnv* env);
+extern int register_android_graphics_drawable_AnimatedVectorDrawable(JNIEnv* env);
+extern int register_android_graphics_drawable_VectorDrawable(JNIEnv* env);
+extern int register_android_graphics_fonts_Font(JNIEnv* env);
+extern int register_android_graphics_fonts_FontFamily(JNIEnv* env);
+extern int register_android_graphics_text_LineBreaker(JNIEnv* env);
+extern int register_android_graphics_text_MeasuredText(JNIEnv* env);
+extern int register_android_util_PathParser(JNIEnv* env);
+extern int register_com_android_internal_util_VirtualRefBasePtr(JNIEnv *env);
+extern int register_com_android_internal_view_animation_NativeInterpolatorFactoryHelper(JNIEnv *env);
+
+#define REG_JNI(name)      { name }
+struct RegJNIRec {
+    int (*mProc)(JNIEnv*);
+};
+
+static const RegJNIRec gRegJNI[] = {
+    REG_JNI(register_android_animation_PropertyValuesHolder),
+    REG_JNI(register_android_graphics_Bitmap),
+    REG_JNI(register_android_graphics_BitmapFactory),
+    REG_JNI(register_android_graphics_ByteBufferStreamAdaptor),
+    REG_JNI(register_android_graphics_Canvas),
+    REG_JNI(register_android_graphics_ColorFilter),
+    REG_JNI(register_android_graphics_ColorSpace),
+    REG_JNI(register_android_graphics_CreateJavaOutputStreamAdaptor),
+    REG_JNI(register_android_graphics_DrawFilter),
+    REG_JNI(register_android_graphics_FontFamily),
+    REG_JNI(register_android_graphics_Graphics),
+    REG_JNI(register_android_graphics_ImageDecoder),
+    REG_JNI(register_android_graphics_MaskFilter),
+    REG_JNI(register_android_graphics_Matrix),
+    REG_JNI(register_android_graphics_NinePatch),
+    REG_JNI(register_android_graphics_Paint),
+    REG_JNI(register_android_graphics_Path),
+    REG_JNI(register_android_graphics_PathEffect),
+    REG_JNI(register_android_graphics_PathMeasure),
+    REG_JNI(register_android_graphics_Picture),
+    REG_JNI(register_android_graphics_Region),
+    REG_JNI(register_android_graphics_Shader),
+    REG_JNI(register_android_graphics_Typeface),
+    REG_JNI(register_android_graphics_drawable_AnimatedVectorDrawable),
+    REG_JNI(register_android_graphics_drawable_VectorDrawable),
+    REG_JNI(register_android_graphics_fonts_Font),
+    REG_JNI(register_android_graphics_fonts_FontFamily),
+    REG_JNI(register_android_graphics_text_LineBreaker),
+    REG_JNI(register_android_graphics_text_MeasuredText),
+    REG_JNI(register_android_util_PathParser),
+    REG_JNI(register_com_android_internal_util_VirtualRefBasePtr),
+    REG_JNI(register_com_android_internal_view_animation_NativeInterpolatorFactoryHelper),
+};
+
+// Vector to store the names of classes that need delegates of their native methods
+static vector<string> classesToDelegate;
+
+static int register_jni_procs(const RegJNIRec array[], size_t count, JNIEnv* env) {
+    for (size_t i = 0; i < count; i++) {
+        if (array[i].mProc(env) < 0) {
+            return -1;
+        }
+    }
+    return 0;
+}
+
+int AndroidRuntime::registerNativeMethods(JNIEnv* env,
+        const char* className, const JNINativeMethod* gMethods, int numMethods) {
+
+    string classNameString = string(className);
+    if (find(classesToDelegate.begin(), classesToDelegate.end(), classNameString)
+            != classesToDelegate.end()) {
+        // Register native methods to the delegate class <classNameString>_NativeDelegate
+        // by adding _Original to the name of each method.
+        replace(classNameString.begin(), classNameString.end(), '$', '_');
+        string delegateClassName = classNameString + "_NativeDelegate";
+        jclass clazz = env->FindClass(delegateClassName.c_str());
+        JNINativeMethod gTypefaceDelegateMethods[numMethods];
+        for (int i = 0; i < numMethods; i++) {
+            JNINativeMethod gTypefaceMethod = gMethods[i];
+            string newName = string(gTypefaceMethod.name) + "_Original";
+            gTypefaceDelegateMethods[i].name = strdup(newName.c_str());
+            gTypefaceDelegateMethods[i].signature = gTypefaceMethod.signature;
+            gTypefaceDelegateMethods[i].fnPtr = gTypefaceMethod.fnPtr;
+        }
+        int result = env->RegisterNatives(clazz, gTypefaceDelegateMethods, numMethods);
+        for (int i = 0; i < numMethods; i++) {
+            free((char*)gTypefaceDelegateMethods[i].name);
+        }
+        return result;
+    }
+
+    jclass clazz = env->FindClass(className);
+
+    return env->RegisterNatives(clazz, gMethods, numMethods);
+}
+
+JNIEnv* AndroidRuntime::getJNIEnv()
+{
+    JNIEnv* env;
+    if (javaVM->GetEnv((void**) &env, JNI_VERSION_1_6) != JNI_OK)
+        return nullptr;
+    return env;
+}
+
+JavaVM* AndroidRuntime::getJavaVM() {
+    return javaVM;
+}
+
+} // namespace android
+
+using namespace android;
+
+JNIEXPORT jint JNI_OnLoad(JavaVM* vm, void*) {
+    javaVM = vm;
+    JNIEnv* env = nullptr;
+    if (vm->GetEnv(reinterpret_cast<void**>(&env), JNI_VERSION_1_6) != JNI_OK) {
+        return JNI_ERR;
+    }
+
+    // Get the names of classes that have to delegate their native methods
+    jclass createInfo = FindClassOrDie(env, "com/android/tools/layoutlib/create/CreateInfo");
+    jfieldID arrayId = GetStaticFieldIDOrDie(env, createInfo,
+            "DELEGATE_CLASS_NATIVES_TO_NATIVES", "[Ljava/lang/String;");
+    jobjectArray array = (jobjectArray) env->GetStaticObjectField(createInfo, arrayId);
+    jsize size = env->GetArrayLength(array);
+
+    for (int i=0; i < size; ++i) {
+        jstring string = (jstring) env->GetObjectArrayElement(array, i);
+        const char* charArray = env->GetStringUTFChars(string, 0);
+        std::string className = std::string(charArray);
+        std::replace(className.begin(), className.end(), '.', '/');
+        classesToDelegate.push_back(className);
+        env->ReleaseStringUTFChars(string, charArray);
+    }
+
+    if (register_jni_procs(gRegJNI, NELEM(gRegJNI), env) < 0) {
+        return JNI_ERR;
+    }
+
+    // Set the location of ICU data
+    jclass bridge = FindClassOrDie(env, "com/android/layoutlib/bridge/Bridge");
+    jstring stringPath = (jstring) env->CallStaticObjectMethod(bridge,
+            GetStaticMethodIDOrDie(env, bridge, "getIcuDataPath", "()Ljava/lang/String;"));
+    const char* path = env->GetStringUTFChars(stringPath, 0);
+    u_setDataDirectory(path);
+    env->ReleaseStringUTFChars(stringPath, path);
+    return JNI_VERSION_1_6;
+}
diff --git a/core/jni/android/graphics/Bitmap.cpp b/core/jni/android/graphics/Bitmap.cpp
index a4e3709..f3abcf1 100755
--- a/core/jni/android/graphics/Bitmap.cpp
+++ b/core/jni/android/graphics/Bitmap.cpp
@@ -1,7 +1,6 @@
 #define LOG_TAG "Bitmap"
 #include "Bitmap.h"
 
-#include "GraphicBuffer.h"
 #include "SkBitmap.h"
 #include "SkPixelRef.h"
 #include "SkImageEncoder.h"
@@ -11,19 +10,22 @@
 #include "GraphicsJNI.h"
 #include "SkStream.h"
 
-#include <binder/Parcel.h>
 #include "android_os_Parcel.h"
 #include "android_util_Binder.h"
 #include "android_nio_utils.h"
 #include "CreateJavaOutputStreamAdaptor.h"
 #include <hwui/Paint.h>
 #include <hwui/Bitmap.h>
-#include <renderthread/RenderProxy.h>
 #include <utils/Color.h>
 
+#ifdef __ANDROID__ // Layoutlib does not support graphic buffer, parcel or render thread
+#include "GraphicBuffer.h"
+#include <binder/Parcel.h>
+#include <renderthread/RenderProxy.h>
 #include <android_runtime/android_hardware_HardwareBuffer.h>
 
 #include <private/android/AHardwareBufferHelpers.h>
+#endif
 
 #include "core_jni_helpers.h"
 
@@ -667,6 +669,7 @@
 static constexpr uint32_t kMaxColorSpaceSerializedBytes = 80;
 
 static jobject Bitmap_createFromParcel(JNIEnv* env, jobject, jobject parcel) {
+#ifdef __ANDROID__ // Layoutlib does not support parcel
     if (parcel == NULL) {
         SkDebugf("-------- unparcel parcel is NULL\n");
         return NULL;
@@ -783,12 +786,17 @@
 
     return createBitmap(env, nativeBitmap.release(),
             getPremulBitmapCreateFlags(isMutable), NULL, NULL, density);
+#else
+    doThrowRE(env, "Cannot use parcels outside of Android");
+    return NULL;
+#endif
 }
 
 static jboolean Bitmap_writeToParcel(JNIEnv* env, jobject,
                                      jlong bitmapHandle,
                                      jboolean isMutable, jint density,
                                      jobject parcel) {
+#ifdef __ANDROID__ // Layoutlib does not support parcel
     if (parcel == NULL) {
         SkDebugf("------- writeToParcel null parcel\n");
         return JNI_FALSE;
@@ -868,6 +876,10 @@
 
     blob.release();
     return JNI_TRUE;
+#else
+    doThrowRE(env, "Cannot use parcels outside of Android");
+    return JNI_FALSE;
+#endif
 }
 
 static jobject Bitmap_extractAlpha(JNIEnv* env, jobject clazz,
@@ -1085,9 +1097,11 @@
 }
 
 static void Bitmap_prepareToDraw(JNIEnv* env, jobject, jlong bitmapPtr) {
+#ifdef __ANDROID__ // Layoutlib does not support render thread
     LocalScopedBitmap bitmapHandle(bitmapPtr);
     if (!bitmapHandle.valid()) return;
     android::uirenderer::renderthread::RenderProxy::prepareToDraw(bitmapHandle->bitmap());
+#endif
 }
 
 static jint Bitmap_getAllocationByteCount(JNIEnv* env, jobject, jlong bitmapPtr) {
@@ -1114,6 +1128,7 @@
 
 static jobject Bitmap_wrapHardwareBufferBitmap(JNIEnv* env, jobject, jobject hardwareBuffer,
                                                jlong colorSpacePtr) {
+#ifdef __ANDROID__ // Layoutlib does not support graphic buffer
     AHardwareBuffer* hwBuf = android_hardware_HardwareBuffer_getNativeHardwareBuffer(env,
         hardwareBuffer);
     sp<GraphicBuffer> buffer(AHardwareBuffer_to_GraphicBuffer(hwBuf));
@@ -1125,9 +1140,13 @@
         return NULL;
     }
     return bitmap::createBitmap(env, bitmap.release(), getPremulBitmapCreateFlags(false));
+#else
+    return NULL;
+#endif
 }
 
 static jobject Bitmap_createGraphicBufferHandle(JNIEnv* env, jobject, jlong bitmapPtr) {
+#ifdef __ANDROID__ // Layoutlib does not support graphic buffer
     LocalScopedBitmap bitmapHandle(bitmapPtr);
     LOG_ALWAYS_FATAL_IF(!bitmapHandle->isHardware(),
             "Hardware config is only supported config in Bitmap_getGraphicBuffer");
@@ -1135,9 +1154,12 @@
     Bitmap& hwuiBitmap = bitmapHandle->bitmap();
     sp<GraphicBuffer> buffer(hwuiBitmap.graphicBuffer());
     return createJavaGraphicBuffer(env, buffer);
+#else
+    return NULL;
+#endif
 }
 
-static jboolean Bitmap_isImmutable(jlong bitmapHandle) {
+static jboolean Bitmap_isImmutable(CRITICAL_JNI_PARAMS_COMMA jlong bitmapHandle) {
     LocalScopedBitmap bitmapHolder(bitmapHandle);
     if (!bitmapHolder.valid()) return JNI_FALSE;
 
diff --git a/core/jni/android/graphics/FontFamily.cpp b/core/jni/android/graphics/FontFamily.cpp
index 2e7501f..8fc6afa 100644
--- a/core/jni/android/graphics/FontFamily.cpp
+++ b/core/jni/android/graphics/FontFamily.cpp
@@ -74,7 +74,7 @@
     return toJLong(builder);
 }
 
-static jlong FontFamily_create(jlong builderPtr) {
+static jlong FontFamily_create(CRITICAL_JNI_PARAMS_COMMA jlong builderPtr) {
     if (builderPtr == 0) {
         return 0;
     }
@@ -95,7 +95,7 @@
     delete toNativeBuilder(builderPtr);
 }
 
-static jlong FontFamily_getBuilderReleaseFunc() {
+static jlong FontFamily_getBuilderReleaseFunc(CRITICAL_JNI_PARAMS) {
     return toJLong(&releaseBuilder);
 }
 
@@ -103,7 +103,7 @@
     delete toFamily(familyPtr);
 }
 
-static jlong FontFamily_getFamilyReleaseFunc() {
+static jlong FontFamily_getFamilyReleaseFunc(CRITICAL_JNI_PARAMS) {
     return toJLong(&releaseFamily);
 }
 
@@ -219,6 +219,7 @@
 static jboolean FontFamily_addFontFromAssetManager(JNIEnv* env, jobject, jlong builderPtr,
         jobject jassetMgr, jstring jpath, jint cookie, jboolean isAsset, jint ttcIndex,
         jint weight, jint isItalic) {
+#ifdef __ANDROID__ // Layoutlib does not support native AssetManager
     NPE_CHECK_RETURN_ZERO(env, jassetMgr);
     NPE_CHECK_RETURN_ZERO(env, jpath);
 
@@ -263,9 +264,12 @@
     sk_sp<SkData> data(SkData::MakeWithProc(buf, asset->getLength(), releaseAsset,
             asset.release()));
     return addSkTypeface(builder, std::move(data), ttcIndex, weight, isItalic);
+#else
+    return false;
+#endif
 }
 
-static void FontFamily_addAxisValue(jlong builderPtr, jint tag, jfloat value) {
+static void FontFamily_addAxisValue(CRITICAL_JNI_PARAMS_COMMA jlong builderPtr, jint tag, jfloat value) {
     NativeFamilyBuilder* builder = toNativeBuilder(builderPtr);
     builder->axes.push_back({static_cast<minikin::AxisTag>(tag), value});
 }
diff --git a/core/jni/android/graphics/Matrix.cpp b/core/jni/android/graphics/Matrix.cpp
index 755fcfb..1336976 100644
--- a/core/jni/android/graphics/Matrix.cpp
+++ b/core/jni/android/graphics/Matrix.cpp
@@ -139,191 +139,191 @@
 
     // ---------------- @CriticalNative -----------------------------
 
-    static jboolean isIdentity(jlong objHandle) {
+    static jboolean isIdentity(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         return obj->isIdentity() ? JNI_TRUE : JNI_FALSE;
     }
 
-    static jboolean isAffine(jlong objHandle) {
+    static jboolean isAffine(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         return obj->asAffine(NULL) ? JNI_TRUE : JNI_FALSE;
     }
 
-    static jboolean rectStaysRect(jlong objHandle) {
+    static jboolean rectStaysRect(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         return obj->rectStaysRect() ? JNI_TRUE : JNI_FALSE;
     }
 
-    static void reset(jlong objHandle) {
+    static void reset(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->reset();
     }
 
-    static void set(jlong objHandle, jlong otherHandle) {
+    static void set(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong otherHandle) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         SkMatrix* other = reinterpret_cast<SkMatrix*>(otherHandle);
         *obj = *other;
     }
 
-    static void setTranslate(jlong objHandle, jfloat dx, jfloat dy) {
+    static void setTranslate(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat dx, jfloat dy) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setTranslate(dx, dy);
     }
 
-    static void setScale__FFFF(jlong objHandle, jfloat sx, jfloat sy, jfloat px,
+    static void setScale__FFFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat sx, jfloat sy, jfloat px,
             jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setScale(sx, sy, px, py);
     }
 
-    static void setScale__FF(jlong objHandle, jfloat sx, jfloat sy) {
+    static void setScale__FF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat sx, jfloat sy) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setScale(sx, sy);
     }
 
-    static void setRotate__FFF(jlong objHandle, jfloat degrees, jfloat px,
+    static void setRotate__FFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat degrees, jfloat px,
             jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setRotate(degrees, px, py);
     }
 
-    static void setRotate__F(jlong objHandle, jfloat degrees) {
+    static void setRotate__F(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat degrees) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setRotate(degrees);
     }
 
-    static void setSinCos__FFFF(jlong objHandle, jfloat sinValue,
+    static void setSinCos__FFFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat sinValue,
             jfloat cosValue, jfloat px, jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setSinCos(sinValue, cosValue, px, py);
     }
 
-    static void setSinCos__FF(jlong objHandle, jfloat sinValue,
+    static void setSinCos__FF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat sinValue,
             jfloat cosValue) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setSinCos(sinValue, cosValue);
     }
 
-    static void setSkew__FFFF(jlong objHandle, jfloat kx, jfloat ky, jfloat px,
+    static void setSkew__FFFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat kx, jfloat ky, jfloat px,
             jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setSkew(kx, ky, px, py);
     }
 
-    static void setSkew__FF(jlong objHandle, jfloat kx, jfloat ky) {
+    static void setSkew__FF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat kx, jfloat ky) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->setSkew(kx, ky);
     }
 
-    static void setConcat(jlong objHandle, jlong aHandle, jlong bHandle) {
+    static void setConcat(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong aHandle, jlong bHandle) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         SkMatrix* a = reinterpret_cast<SkMatrix*>(aHandle);
         SkMatrix* b = reinterpret_cast<SkMatrix*>(bHandle);
         obj->setConcat(*a, *b);
     }
 
-    static void preTranslate(jlong objHandle, jfloat dx, jfloat dy) {
+    static void preTranslate(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat dx, jfloat dy) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->preTranslate(dx, dy);
     }
 
-    static void preScale__FFFF(jlong objHandle, jfloat sx, jfloat sy, jfloat px,
+    static void preScale__FFFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat sx, jfloat sy, jfloat px,
             jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->preScale(sx, sy, px, py);
     }
 
-    static void preScale__FF(jlong objHandle, jfloat sx, jfloat sy) {
+    static void preScale__FF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat sx, jfloat sy) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->preScale(sx, sy);
     }
 
-    static void preRotate__FFF(jlong objHandle, jfloat degrees, jfloat px,
+    static void preRotate__FFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat degrees, jfloat px,
             jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->preRotate(degrees, px, py);
     }
 
-    static void preRotate__F(jlong objHandle, jfloat degrees) {
+    static void preRotate__F(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat degrees) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->preRotate(degrees);
     }
 
-    static void preSkew__FFFF(jlong objHandle, jfloat kx, jfloat ky, jfloat px,
+    static void preSkew__FFFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat kx, jfloat ky, jfloat px,
             jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->preSkew(kx, ky, px, py);
     }
 
-    static void preSkew__FF(jlong objHandle, jfloat kx, jfloat ky) {
+    static void preSkew__FF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat kx, jfloat ky) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->preSkew(kx, ky);
     }
 
-    static void preConcat(jlong objHandle, jlong otherHandle) {
+    static void preConcat(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong otherHandle) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         SkMatrix* other = reinterpret_cast<SkMatrix*>(otherHandle);
         obj->preConcat(*other);
     }
 
-    static void postTranslate(jlong objHandle, jfloat dx, jfloat dy) {
+    static void postTranslate(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat dx, jfloat dy) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->postTranslate(dx, dy);
     }
 
-    static void postScale__FFFF(jlong objHandle, jfloat sx, jfloat sy,
+    static void postScale__FFFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat sx, jfloat sy,
             jfloat px, jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->postScale(sx, sy, px, py);
     }
 
-    static void postScale__FF(jlong objHandle, jfloat sx, jfloat sy) {
+    static void postScale__FF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat sx, jfloat sy) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->postScale(sx, sy);
     }
 
-    static void postRotate__FFF(jlong objHandle, jfloat degrees, jfloat px,
+    static void postRotate__FFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat degrees, jfloat px,
             jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->postRotate(degrees, px, py);
     }
 
-    static void postRotate__F(jlong objHandle, jfloat degrees) {
+    static void postRotate__F(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat degrees) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->postRotate(degrees);
     }
 
-    static void postSkew__FFFF(jlong objHandle, jfloat kx, jfloat ky, jfloat px,
+    static void postSkew__FFFF(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jfloat kx, jfloat ky, jfloat px,
             jfloat py) {
         SkMatrix* obj = reinterpret_cast<SkMatrix*>(objHandle);
         obj->postSkew(kx, ky, px, py);
     }
 
-    static void postSkew__FF(jlong matrixHandle, jfloat kx, jfloat ky) {
+    static void postSkew__FF(CRITICAL_JNI_PARAMS_COMMA jlong matrixHandle, jfloat kx, jfloat ky) {
         SkMatrix* matrix = reinterpret_cast<SkMatrix*>(matrixHandle);
         matrix->postSkew(kx, ky);
     }
 
-    static void postConcat(jlong matrixHandle, jlong otherHandle) {
+    static void postConcat(CRITICAL_JNI_PARAMS_COMMA jlong matrixHandle, jlong otherHandle) {
         SkMatrix* matrix = reinterpret_cast<SkMatrix*>(matrixHandle);
         SkMatrix* other = reinterpret_cast<SkMatrix*>(otherHandle);
         matrix->postConcat(*other);
     }
 
-    static jboolean invert(jlong matrixHandle, jlong inverseHandle) {
+    static jboolean invert(CRITICAL_JNI_PARAMS_COMMA jlong matrixHandle, jlong inverseHandle) {
         SkMatrix* matrix = reinterpret_cast<SkMatrix*>(matrixHandle);
         SkMatrix* inverse = reinterpret_cast<SkMatrix*>(inverseHandle);
         return matrix->invert(inverse);
     }
 
-    static jfloat mapRadius(jlong matrixHandle, jfloat radius) {
+    static jfloat mapRadius(CRITICAL_JNI_PARAMS_COMMA jlong matrixHandle, jfloat radius) {
         SkMatrix* matrix = reinterpret_cast<SkMatrix*>(matrixHandle);
         float result;
         result = SkScalarToFloat(matrix->mapRadius(radius));
         return static_cast<jfloat>(result);
     }
 
-    static jboolean equals(jlong aHandle, jlong bHandle) {
+    static jboolean equals(CRITICAL_JNI_PARAMS_COMMA jlong aHandle, jlong bHandle) {
         const SkMatrix* a = reinterpret_cast<SkMatrix*>(aHandle);
         const SkMatrix* b = reinterpret_cast<SkMatrix*>(bHandle);
         return *a == *b;
diff --git a/core/jni/android/graphics/Paint.cpp b/core/jni/android/graphics/Paint.cpp
index 8bb163b..8e1bc84 100644
--- a/core/jni/android/graphics/Paint.cpp
+++ b/core/jni/android/graphics/Paint.cpp
@@ -650,154 +650,154 @@
 
     // ------------------ @CriticalNative ---------------------------
 
-    static void reset(jlong objHandle) {
+    static void reset(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         reinterpret_cast<Paint*>(objHandle)->reset();
     }
 
-    static void assign(jlong dstPaintHandle, jlong srcPaintHandle) {
+    static void assign(CRITICAL_JNI_PARAMS_COMMA jlong dstPaintHandle, jlong srcPaintHandle) {
         Paint* dst = reinterpret_cast<Paint*>(dstPaintHandle);
         const Paint* src = reinterpret_cast<Paint*>(srcPaintHandle);
         *dst = *src;
     }
 
-    static jint getFlags(jlong paintHandle) {
+    static jint getFlags(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         uint32_t flags = reinterpret_cast<Paint*>(paintHandle)->getJavaFlags();
         return static_cast<jint>(flags);
     }
 
-    static void setFlags(jlong paintHandle, jint flags) {
+    static void setFlags(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint flags) {
         reinterpret_cast<Paint*>(paintHandle)->setJavaFlags(flags);
     }
 
-    static jint getHinting(jlong paintHandle) {
+    static jint getHinting(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         return (SkFontHinting)reinterpret_cast<Paint*>(paintHandle)->getSkFont().getHinting()
                 == SkFontHinting::kNone ? 0 : 1;
     }
 
-    static void setHinting(jlong paintHandle, jint mode) {
+    static void setHinting(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint mode) {
         reinterpret_cast<Paint*>(paintHandle)->getSkFont().setHinting(
                 mode == 0 ? SkFontHinting::kNone : SkFontHinting::kNormal);
     }
 
-    static void setAntiAlias(jlong paintHandle, jboolean aa) {
+    static void setAntiAlias(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean aa) {
         reinterpret_cast<Paint*>(paintHandle)->setAntiAlias(aa);
     }
 
-    static void setLinearText(jlong paintHandle, jboolean linearText) {
+    static void setLinearText(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean linearText) {
         reinterpret_cast<Paint*>(paintHandle)->getSkFont().setLinearMetrics(linearText);
     }
 
-    static void setSubpixelText(jlong paintHandle, jboolean subpixelText) {
+    static void setSubpixelText(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean subpixelText) {
         reinterpret_cast<Paint*>(paintHandle)->getSkFont().setSubpixel(subpixelText);
     }
 
-    static void setUnderlineText(jlong paintHandle, jboolean underlineText) {
+    static void setUnderlineText(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean underlineText) {
         reinterpret_cast<Paint*>(paintHandle)->setUnderline(underlineText);
     }
 
-    static void setStrikeThruText(jlong paintHandle, jboolean strikeThruText) {
+    static void setStrikeThruText(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean strikeThruText) {
         reinterpret_cast<Paint*>(paintHandle)->setStrikeThru(strikeThruText);
     }
 
-    static void setFakeBoldText(jlong paintHandle, jboolean fakeBoldText) {
+    static void setFakeBoldText(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean fakeBoldText) {
         reinterpret_cast<Paint*>(paintHandle)->getSkFont().setEmbolden(fakeBoldText);
     }
 
-    static void setFilterBitmap(jlong paintHandle, jboolean filterBitmap) {
+    static void setFilterBitmap(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean filterBitmap) {
         reinterpret_cast<Paint*>(paintHandle)->setFilterQuality(
                 filterBitmap ? kLow_SkFilterQuality : kNone_SkFilterQuality);
     }
 
-    static void setDither(jlong paintHandle, jboolean dither) {
+    static void setDither(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean dither) {
         reinterpret_cast<Paint*>(paintHandle)->setDither(dither);
     }
 
-    static jint getStyle(jlong objHandle) {
+    static jint getStyle(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         return static_cast<jint>(obj->getStyle());
     }
 
-    static void setStyle(jlong objHandle, jint styleHandle) {
+    static void setStyle(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jint styleHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         Paint::Style style = static_cast<Paint::Style>(styleHandle);
         obj->setStyle(style);
     }
 
-    static void setColorLong(jlong paintHandle, jlong colorSpaceHandle,
+    static void setColorLong(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jlong colorSpaceHandle,
             jlong colorLong) {
         SkColor4f color = GraphicsJNI::convertColorLong(colorLong);
         sk_sp<SkColorSpace> cs = GraphicsJNI::getNativeColorSpace(colorSpaceHandle);
         reinterpret_cast<Paint*>(paintHandle)->setColor4f(color, cs.get());
     }
 
-    static void setColor(jlong paintHandle, jint color) {
+    static void setColor(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint color) {
         reinterpret_cast<Paint*>(paintHandle)->setColor(color);
     }
 
-    static void setAlpha(jlong paintHandle, jint a) {
+    static void setAlpha(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint a) {
         reinterpret_cast<Paint*>(paintHandle)->setAlpha(a);
     }
 
-    static jfloat getStrokeWidth(jlong paintHandle) {
+    static jfloat getStrokeWidth(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         return SkScalarToFloat(reinterpret_cast<Paint*>(paintHandle)->getStrokeWidth());
     }
 
-    static void setStrokeWidth(jlong paintHandle, jfloat width) {
+    static void setStrokeWidth(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jfloat width) {
         reinterpret_cast<Paint*>(paintHandle)->setStrokeWidth(width);
     }
 
-    static jfloat getStrokeMiter(jlong paintHandle) {
+    static jfloat getStrokeMiter(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         return SkScalarToFloat(reinterpret_cast<Paint*>(paintHandle)->getStrokeMiter());
     }
 
-    static void setStrokeMiter(jlong paintHandle, jfloat miter) {
+    static void setStrokeMiter(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jfloat miter) {
         reinterpret_cast<Paint*>(paintHandle)->setStrokeMiter(miter);
     }
 
-    static jint getStrokeCap(jlong objHandle) {
+    static jint getStrokeCap(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         return static_cast<jint>(obj->getStrokeCap());
     }
 
-    static void setStrokeCap(jlong objHandle, jint capHandle) {
+    static void setStrokeCap(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jint capHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         Paint::Cap cap = static_cast<Paint::Cap>(capHandle);
         obj->setStrokeCap(cap);
     }
 
-    static jint getStrokeJoin(jlong objHandle) {
+    static jint getStrokeJoin(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         return static_cast<jint>(obj->getStrokeJoin());
     }
 
-    static void setStrokeJoin(jlong objHandle, jint joinHandle) {
+    static void setStrokeJoin(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jint joinHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         Paint::Join join = (Paint::Join) joinHandle;
         obj->setStrokeJoin(join);
     }
 
-    static jboolean getFillPath(jlong objHandle, jlong srcHandle, jlong dstHandle) {
+    static jboolean getFillPath(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong srcHandle, jlong dstHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         SkPath* src = reinterpret_cast<SkPath*>(srcHandle);
         SkPath* dst = reinterpret_cast<SkPath*>(dstHandle);
         return obj->getFillPath(*src, dst) ? JNI_TRUE : JNI_FALSE;
     }
 
-    static jlong setShader(jlong objHandle, jlong shaderHandle) {
+    static jlong setShader(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong shaderHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         SkShader* shader = reinterpret_cast<SkShader*>(shaderHandle);
         obj->setShader(sk_ref_sp(shader));
         return reinterpret_cast<jlong>(obj->getShader());
     }
 
-    static jlong setColorFilter(jlong objHandle, jlong filterHandle) {
+    static jlong setColorFilter(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong filterHandle) {
         Paint* obj = reinterpret_cast<Paint *>(objHandle);
         SkColorFilter* filter  = reinterpret_cast<SkColorFilter *>(filterHandle);
         obj->setColorFilter(sk_ref_sp(filter));
         return reinterpret_cast<jlong>(obj->getColorFilter());
     }
 
-    static void setXfermode(jlong paintHandle, jint xfermodeHandle) {
+    static void setXfermode(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint xfermodeHandle) {
         // validate that the Java enum values match our expectations
         static_assert(0 == static_cast<int>(SkBlendMode::kClear), "xfermode_mismatch");
         static_assert(1 == static_cast<int>(SkBlendMode::kSrc), "xfermode_mismatch");
@@ -834,132 +834,132 @@
         paint->setBlendMode(mode);
     }
 
-    static jlong setPathEffect(jlong objHandle, jlong effectHandle) {
+    static jlong setPathEffect(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong effectHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         SkPathEffect* effect  = reinterpret_cast<SkPathEffect*>(effectHandle);
         obj->setPathEffect(sk_ref_sp(effect));
         return reinterpret_cast<jlong>(obj->getPathEffect());
     }
 
-    static jlong setMaskFilter(jlong objHandle, jlong maskfilterHandle) {
+    static jlong setMaskFilter(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong maskfilterHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         SkMaskFilter* maskfilter  = reinterpret_cast<SkMaskFilter*>(maskfilterHandle);
         obj->setMaskFilter(sk_ref_sp(maskfilter));
         return reinterpret_cast<jlong>(obj->getMaskFilter());
     }
 
-    static void setTypeface(jlong objHandle, jlong typefaceHandle) {
+    static void setTypeface(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jlong typefaceHandle) {
         Paint* paint = reinterpret_cast<Paint*>(objHandle);
         paint->setAndroidTypeface(reinterpret_cast<Typeface*>(typefaceHandle));
     }
 
-    static jint getTextAlign(jlong objHandle) {
+    static jint getTextAlign(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         return static_cast<jint>(obj->getTextAlign());
     }
 
-    static void setTextAlign(jlong objHandle, jint alignHandle) {
+    static void setTextAlign(CRITICAL_JNI_PARAMS_COMMA jlong objHandle, jint alignHandle) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         Paint::Align align = static_cast<Paint::Align>(alignHandle);
         obj->setTextAlign(align);
     }
 
-    static void setTextLocalesByMinikinLocaleListId(jlong objHandle,
+    static void setTextLocalesByMinikinLocaleListId(CRITICAL_JNI_PARAMS_COMMA jlong objHandle,
             jint minikinLocaleListId) {
         Paint* obj = reinterpret_cast<Paint*>(objHandle);
         obj->setMinikinLocaleListId(minikinLocaleListId);
     }
 
-    static jboolean isElegantTextHeight(jlong paintHandle) {
+    static jboolean isElegantTextHeight(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         Paint* obj = reinterpret_cast<Paint*>(paintHandle);
         return obj->getFamilyVariant() == minikin::FamilyVariant::ELEGANT;
     }
 
-    static void setElegantTextHeight(jlong paintHandle, jboolean aa) {
+    static void setElegantTextHeight(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jboolean aa) {
         Paint* obj = reinterpret_cast<Paint*>(paintHandle);
         obj->setFamilyVariant(
                 aa ? minikin::FamilyVariant::ELEGANT : minikin::FamilyVariant::DEFAULT);
     }
 
-    static jfloat getTextSize(jlong paintHandle) {
+    static jfloat getTextSize(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         return SkScalarToFloat(reinterpret_cast<Paint*>(paintHandle)->getSkFont().getSize());
     }
 
-    static void setTextSize(jlong paintHandle, jfloat textSize) {
+    static void setTextSize(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jfloat textSize) {
         if (textSize >= 0) {
             reinterpret_cast<Paint*>(paintHandle)->getSkFont().setSize(textSize);
         }
     }
 
-    static jfloat getTextScaleX(jlong paintHandle) {
+    static jfloat getTextScaleX(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         return SkScalarToFloat(reinterpret_cast<Paint*>(paintHandle)->getSkFont().getScaleX());
     }
 
-    static void setTextScaleX(jlong paintHandle, jfloat scaleX) {
+    static void setTextScaleX(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jfloat scaleX) {
         reinterpret_cast<Paint*>(paintHandle)->getSkFont().setScaleX(scaleX);
     }
 
-    static jfloat getTextSkewX(jlong paintHandle) {
+    static jfloat getTextSkewX(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         return SkScalarToFloat(reinterpret_cast<Paint*>(paintHandle)->getSkFont().getSkewX());
     }
 
-    static void setTextSkewX(jlong paintHandle, jfloat skewX) {
+    static void setTextSkewX(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jfloat skewX) {
         reinterpret_cast<Paint*>(paintHandle)->getSkFont().setSkewX(skewX);
     }
 
-    static jfloat getLetterSpacing(jlong paintHandle) {
+    static jfloat getLetterSpacing(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         return paint->getLetterSpacing();
     }
 
-    static void setLetterSpacing(jlong paintHandle, jfloat letterSpacing) {
+    static void setLetterSpacing(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jfloat letterSpacing) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         paint->setLetterSpacing(letterSpacing);
     }
 
-    static jfloat getWordSpacing(jlong paintHandle) {
+    static jfloat getWordSpacing(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         return paint->getWordSpacing();
     }
 
-    static void setWordSpacing(jlong paintHandle, jfloat wordSpacing) {
+    static void setWordSpacing(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jfloat wordSpacing) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         paint->setWordSpacing(wordSpacing);
     }
 
-    static jint getStartHyphenEdit(jlong paintHandle, jint hyphen) {
+    static jint getStartHyphenEdit(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint hyphen) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         return static_cast<jint>(paint->getStartHyphenEdit());
     }
 
-    static jint getEndHyphenEdit(jlong paintHandle, jint hyphen) {
+    static jint getEndHyphenEdit(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint hyphen) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         return static_cast<jint>(paint->getEndHyphenEdit());
     }
 
-    static void setStartHyphenEdit(jlong paintHandle, jint hyphen) {
+    static void setStartHyphenEdit(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint hyphen) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         paint->setStartHyphenEdit((uint32_t)hyphen);
     }
 
-    static void setEndHyphenEdit(jlong paintHandle, jint hyphen) {
+    static void setEndHyphenEdit(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jint hyphen) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         paint->setEndHyphenEdit((uint32_t)hyphen);
     }
 
-    static jfloat ascent(jlong paintHandle) {
+    static jfloat ascent(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         SkFontMetrics metrics;
         getMetricsInternal(paintHandle, &metrics);
         return SkScalarToFloat(metrics.fAscent);
     }
 
-    static jfloat descent(jlong paintHandle) {
+    static jfloat descent(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         SkFontMetrics metrics;
         getMetricsInternal(paintHandle, &metrics);
         return SkScalarToFloat(metrics.fDescent);
     }
 
-    static jfloat getUnderlinePosition(jlong paintHandle) {
+    static jfloat getUnderlinePosition(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         SkFontMetrics metrics;
         getMetricsInternal(paintHandle, &metrics);
         SkScalar position;
@@ -971,7 +971,7 @@
         }
     }
 
-    static jfloat getUnderlineThickness(jlong paintHandle) {
+    static jfloat getUnderlineThickness(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         SkFontMetrics metrics;
         getMetricsInternal(paintHandle, &metrics);
         SkScalar thickness;
@@ -983,17 +983,17 @@
         }
     }
 
-    static jfloat getStrikeThruPosition(jlong paintHandle) {
+    static jfloat getStrikeThruPosition(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         const SkScalar textSize = reinterpret_cast<Paint*>(paintHandle)->getSkFont().getSize();
         return SkScalarToFloat(Paint::kStdStrikeThru_Top * textSize);
     }
 
-    static jfloat getStrikeThruThickness(jlong paintHandle) {
+    static jfloat getStrikeThruThickness(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         const SkScalar textSize = reinterpret_cast<Paint*>(paintHandle)->getSkFont().getSize();
         return SkScalarToFloat(Paint::kStdStrikeThru_Thickness * textSize);
     }
 
-    static void setShadowLayer(jlong paintHandle, jfloat radius,
+    static void setShadowLayer(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle, jfloat radius,
                                jfloat dx, jfloat dy, jlong colorSpaceHandle,
                                jlong colorLong) {
         SkColor4f color = GraphicsJNI::convertColorLong(colorLong);
@@ -1009,12 +1009,12 @@
         }
     }
 
-    static jboolean hasShadowLayer(jlong paintHandle) {
+    static jboolean hasShadowLayer(CRITICAL_JNI_PARAMS_COMMA jlong paintHandle) {
         Paint* paint = reinterpret_cast<Paint*>(paintHandle);
         return paint->getLooper() && paint->getLooper()->asABlurShadow(nullptr);
     }
 
-    static jboolean equalsForTextMeasurement(jlong lPaint, jlong rPaint) {
+    static jboolean equalsForTextMeasurement(CRITICAL_JNI_PARAMS_COMMA jlong lPaint, jlong rPaint) {
         if (lPaint == rPaint) {
             return true;
         }
diff --git a/core/jni/android/graphics/Path.cpp b/core/jni/android/graphics/Path.cpp
index aedb6ac..d73affc 100644
--- a/core/jni/android/graphics/Path.cpp
+++ b/core/jni/android/graphics/Path.cpp
@@ -475,32 +475,32 @@
 
     // ---------------- @CriticalNative -------------------------
 
-    static void reset(jlong objHandle) {
+    static void reset(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkPath* obj = reinterpret_cast<SkPath*>(objHandle);
         obj->reset();
     }
 
-    static void rewind(jlong objHandle) {
+    static void rewind(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkPath* obj = reinterpret_cast<SkPath*>(objHandle);
         obj->rewind();
     }
 
-    static jboolean isEmpty(jlong objHandle) {
+    static jboolean isEmpty(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkPath* obj = reinterpret_cast<SkPath*>(objHandle);
         return obj->isEmpty();
     }
 
-    static jboolean isConvex(jlong objHandle) {
+    static jboolean isConvex(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkPath* obj = reinterpret_cast<SkPath*>(objHandle);
         return obj->isConvex();
     }
 
-    static jint getFillType(jlong objHandle) {
+    static jint getFillType(CRITICAL_JNI_PARAMS_COMMA jlong objHandle) {
         SkPath* obj = reinterpret_cast<SkPath*>(objHandle);
         return obj->getFillType();
     }
 
-    static void setFillType(jlong pathHandle, jint ftHandle) {;
+    static void setFillType(CRITICAL_JNI_PARAMS_COMMA jlong pathHandle, jint ftHandle) {;
         SkPath* path = reinterpret_cast<SkPath*>(pathHandle);
         SkPath::FillType ft = static_cast<SkPath::FillType>(ftHandle);
         path->setFillType(ft);
diff --git a/core/jni/android/graphics/Region.cpp b/core/jni/android/graphics/Region.cpp
index 2bffaf0..90ca3bb 100644
--- a/core/jni/android/graphics/Region.cpp
+++ b/core/jni/android/graphics/Region.cpp
@@ -18,7 +18,9 @@
 #include "SkPath.h"
 #include "GraphicsJNI.h"
 
+#ifdef __ANDROID__ // Layoutlib does not support parcel
 #include <binder/Parcel.h>
+#endif
 #include "android_os_Parcel.h"
 #include "android_util_Binder.h"
 
@@ -206,6 +208,7 @@
 
 static jlong Region_createFromParcel(JNIEnv* env, jobject clazz, jobject parcel)
 {
+#ifdef __ANDROID__ // Layoutlib does not support parcel
     if (parcel == nullptr) {
         return 0;
     }
@@ -225,10 +228,14 @@
     }
 
     return reinterpret_cast<jlong>(region);
+#else
+    return 0;
+#endif
 }
 
 static jboolean Region_writeToParcel(JNIEnv* env, jobject clazz, jlong regionHandle, jobject parcel)
 {
+#ifdef __ANDROID__ // Layoutlib does not support parcel
     const SkRegion* region = reinterpret_cast<SkRegion*>(regionHandle);
     if (parcel == nullptr) {
         return JNI_FALSE;
@@ -249,6 +256,9 @@
 
     p->writeInt32Vector(rects);
     return JNI_TRUE;
+#else
+    return JNI_FALSE;
+#endif
 }
 
 ////////////////////////////////////////////////////////////////////////////////////////////////////////////
diff --git a/core/jni/android/graphics/Typeface.cpp b/core/jni/android/graphics/Typeface.cpp
index 30d6ff4..9603a10 100644
--- a/core/jni/android/graphics/Typeface.cpp
+++ b/core/jni/android/graphics/Typeface.cpp
@@ -81,17 +81,17 @@
 }
 
 // CriticalNative
-static jlong Typeface_getReleaseFunc() {
+static jlong Typeface_getReleaseFunc(CRITICAL_JNI_PARAMS) {
     return toJLong(&releaseFunc);
 }
 
 // CriticalNative
-static jint Typeface_getStyle(jlong faceHandle) {
+static jint Typeface_getStyle(CRITICAL_JNI_PARAMS_COMMA jlong faceHandle) {
     return toTypeface(faceHandle)->fAPIStyle;
 }
 
 // CriticalNative
-static jint Typeface_getWeight(jlong faceHandle) {
+static jint Typeface_getWeight(CRITICAL_JNI_PARAMS_COMMA jlong faceHandle) {
     return toTypeface(faceHandle)->fStyle.weight();
 }
 
@@ -108,7 +108,7 @@
 }
 
 // CriticalNative
-static void Typeface_setDefault(jlong faceHandle) {
+static void Typeface_setDefault(CRITICAL_JNI_PARAMS_COMMA jlong faceHandle) {
     Typeface::setDefault(toTypeface(faceHandle));
     minikin::SystemFonts::registerDefault(toTypeface(faceHandle)->fFontCollection);
 }
diff --git a/core/jni/android/graphics/fonts/Font.cpp b/core/jni/android/graphics/fonts/Font.cpp
index 8178318..bb0654d 100644
--- a/core/jni/android/graphics/fonts/Font.cpp
+++ b/core/jni/android/graphics/fonts/Font.cpp
@@ -81,6 +81,7 @@
 // Regular JNI
 static jlong Font_Builder_getNativeAsset(
     JNIEnv* env, jobject clazz, jobject assetMgr, jstring path, jboolean isAsset, jint cookie) {
+#ifdef __ANDROID__ // Layoutlib does not support native AssetManager
     NPE_CHECK_RETURN_ZERO(env, assetMgr);
     NPE_CHECK_RETURN_ZERO(env, path);
 
@@ -109,6 +110,9 @@
     }
 
     return reinterpret_cast<jlong>(asset.release());
+#else
+    return 0;
+#endif
 }
 
 // Regular JNI
@@ -118,7 +122,7 @@
 }
 
 // CriticalNative
-static jlong Font_Builder_getReleaseNativeAssetFunc() {
+static jlong Font_Builder_getReleaseNativeAssetFunc(CRITICAL_JNI_PARAMS) {
     return reinterpret_cast<jlong>(&releaseAsset);
 }
 
@@ -128,7 +132,7 @@
 }
 
 // Critical Native
-static void Font_Builder_addAxis(jlong builderPtr, jint tag, jfloat value) {
+static void Font_Builder_addAxis(CRITICAL_JNI_PARAMS_COMMA jlong builderPtr, jint tag, jfloat value) {
     toBuilder(builderPtr)->axes.emplace_back(static_cast<minikin::AxisTag>(tag), value);
 }
 
@@ -181,7 +185,7 @@
 }
 
 // Critical Native
-static jlong Font_Builder_getReleaseNativeFont() {
+static jlong Font_Builder_getReleaseNativeFont(CRITICAL_JNI_PARAMS) {
     return reinterpret_cast<jlong>(releaseFont);
 }
 
diff --git a/core/jni/android/graphics/fonts/FontFamily.cpp b/core/jni/android/graphics/fonts/FontFamily.cpp
index 249e4f3..b0d10c3 100644
--- a/core/jni/android/graphics/fonts/FontFamily.cpp
+++ b/core/jni/android/graphics/fonts/FontFamily.cpp
@@ -51,7 +51,7 @@
 }
 
 // Critical Native
-static void FontFamily_Builder_addFont(jlong builderPtr, jlong fontPtr) {
+static void FontFamily_Builder_addFont(CRITICAL_JNI_PARAMS_COMMA jlong builderPtr, jlong fontPtr) {
     toBuilder(builderPtr)->fonts.push_back(toFontWrapper(fontPtr)->font);
 }
 
@@ -79,7 +79,7 @@
 }
 
 // CriticalNative
-static jlong FontFamily_Builder_GetReleaseFunc() {
+static jlong FontFamily_Builder_GetReleaseFunc(CRITICAL_JNI_PARAMS) {
     return reinterpret_cast<jlong>(releaseFontFamily);
 }
 
diff --git a/core/jni/android/graphics/text/LineBreaker.cpp b/core/jni/android/graphics/text/LineBreaker.cpp
index a23f99a..8dae655 100644
--- a/core/jni/android/graphics/text/LineBreaker.cpp
+++ b/core/jni/android/graphics/text/LineBreaker.cpp
@@ -68,7 +68,7 @@
 }
 
 // CriticalNative
-static jlong nGetReleaseFunc() {
+static jlong nGetReleaseFunc(CRITICAL_JNI_PARAMS) {
     return reinterpret_cast<jlong>(nFinish);
 }
 
@@ -98,27 +98,27 @@
     return reinterpret_cast<jlong>(result.release());
 }
 
-static jint nGetLineCount(jlong ptr) {
+static jint nGetLineCount(CRITICAL_JNI_PARAMS_COMMA jlong ptr) {
     return reinterpret_cast<minikin::LineBreakResult*>(ptr)->breakPoints.size();
 }
 
-static jint nGetLineBreakOffset(jlong ptr, jint i) {
+static jint nGetLineBreakOffset(CRITICAL_JNI_PARAMS_COMMA jlong ptr, jint i) {
     return reinterpret_cast<minikin::LineBreakResult*>(ptr)->breakPoints[i];
 }
 
-static jfloat nGetLineWidth(jlong ptr, jint i) {
+static jfloat nGetLineWidth(CRITICAL_JNI_PARAMS_COMMA jlong ptr, jint i) {
     return reinterpret_cast<minikin::LineBreakResult*>(ptr)->widths[i];
 }
 
-static jfloat nGetLineAscent(jlong ptr, jint i) {
+static jfloat nGetLineAscent(CRITICAL_JNI_PARAMS_COMMA jlong ptr, jint i) {
     return reinterpret_cast<minikin::LineBreakResult*>(ptr)->ascents[i];
 }
 
-static jfloat nGetLineDescent(jlong ptr, jint i) {
+static jfloat nGetLineDescent(CRITICAL_JNI_PARAMS_COMMA jlong ptr, jint i) {
     return reinterpret_cast<minikin::LineBreakResult*>(ptr)->descents[i];
 }
 
-static jint nGetLineFlag(jlong ptr, jint i) {
+static jint nGetLineFlag(CRITICAL_JNI_PARAMS_COMMA jlong ptr, jint i) {
     return reinterpret_cast<minikin::LineBreakResult*>(ptr)->flags[i];
 }
 
@@ -126,7 +126,7 @@
     delete reinterpret_cast<minikin::LineBreakResult*>(ptr);
 }
 
-static jlong nGetReleaseResultFunc() {
+static jlong nGetReleaseResultFunc(CRITICAL_JNI_PARAMS) {
     return reinterpret_cast<jlong>(nReleaseResult);
 }
 
diff --git a/core/jni/android/graphics/text/MeasuredText.cpp b/core/jni/android/graphics/text/MeasuredText.cpp
index 68ba38b..3b5ecbc 100644
--- a/core/jni/android/graphics/text/MeasuredText.cpp
+++ b/core/jni/android/graphics/text/MeasuredText.cpp
@@ -60,7 +60,7 @@
 }
 
 // Regular JNI
-static jlong nInitBuilder() {
+static jlong nInitBuilder(CRITICAL_JNI_PARAMS) {
     return toJLong(new minikin::MeasuredTextBuilder());
 }
 
@@ -98,7 +98,7 @@
 }
 
 // CriticalNative
-static jfloat nGetWidth(jlong ptr, jint start, jint end) {
+static jfloat nGetWidth(CRITICAL_JNI_PARAMS_COMMA jlong ptr, jint start, jint end) {
     minikin::MeasuredText* mt = toMeasuredParagraph(ptr);
     float r = 0.0f;
     for (int i = start; i < end; ++i) {
@@ -107,7 +107,7 @@
     return r;
 }
 
-static jfloat nGetCharWidthAt(jlong ptr, jint offset) {
+static jfloat nGetCharWidthAt(CRITICAL_JNI_PARAMS_COMMA jlong ptr, jint offset) {
     return toMeasuredParagraph(ptr)->widths[offset];
 }
 
@@ -132,11 +132,11 @@
 }
 
 // CriticalNative
-static jlong nGetReleaseFunc() {
+static jlong nGetReleaseFunc(CRITICAL_JNI_PARAMS) {
     return toJLong(&releaseMeasuredParagraph);
 }
 
-static jint nGetMemoryUsage(jlong ptr) {
+static jint nGetMemoryUsage(CRITICAL_JNI_PARAMS_COMMA jlong ptr) {
     return static_cast<jint>(toMeasuredParagraph(ptr)->getMemoryUsage());
 }
 
diff --git a/core/jni/android_graphics_Canvas.cpp b/core/jni/android_graphics_Canvas.cpp
index ebc6cd7..0ad3339 100644
--- a/core/jni/android_graphics_Canvas.cpp
+++ b/core/jni/android_graphics_Canvas.cpp
@@ -18,7 +18,11 @@
 #include "GraphicsJNI.h"
 #include "core_jni_helpers.h"
 
+#ifdef __ANDROID_
 #include <android/api-level.h>
+#else
+#define __ANDROID_API_P__ 28
+#endif
 #include <androidfw/ResourceTypes.h>
 #include <hwui/Canvas.h>
 #include <hwui/Paint.h>
@@ -72,46 +76,46 @@
     get_canvas(canvasHandle)->setBitmap(bitmap);
 }
 
-static jboolean isOpaque(jlong canvasHandle) {
+static jboolean isOpaque(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle) {
     return get_canvas(canvasHandle)->isOpaque() ? JNI_TRUE : JNI_FALSE;
 }
 
-static jint getWidth(jlong canvasHandle) {
+static jint getWidth(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle) {
     return static_cast<jint>(get_canvas(canvasHandle)->width());
 }
 
-static jint getHeight(jlong canvasHandle) {
+static jint getHeight(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle) {
     return static_cast<jint>(get_canvas(canvasHandle)->height());
 }
 
-static jint save(jlong canvasHandle, jint flagsHandle) {
+static jint save(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jint flagsHandle) {
     SaveFlags::Flags flags = static_cast<SaveFlags::Flags>(flagsHandle);
     return static_cast<jint>(get_canvas(canvasHandle)->save(flags));
 }
 
-static jint saveLayer(jlong canvasHandle, jfloat l, jfloat t,
+static jint saveLayer(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jfloat l, jfloat t,
                       jfloat r, jfloat b, jlong paintHandle, jint flagsHandle) {
     Paint* paint  = reinterpret_cast<Paint*>(paintHandle);
     SaveFlags::Flags flags = static_cast<SaveFlags::Flags>(flagsHandle);
     return static_cast<jint>(get_canvas(canvasHandle)->saveLayer(l, t, r, b, paint, flags));
 }
 
-static jint saveLayerAlpha(jlong canvasHandle, jfloat l, jfloat t,
+static jint saveLayerAlpha(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jfloat l, jfloat t,
                            jfloat r, jfloat b, jint alpha, jint flagsHandle) {
     SaveFlags::Flags flags = static_cast<SaveFlags::Flags>(flagsHandle);
     return static_cast<jint>(get_canvas(canvasHandle)->saveLayerAlpha(l, t, r, b, alpha, flags));
 }
 
-static jint saveUnclippedLayer(jlong canvasHandle, jint l, jint t, jint r, jint b) {
+static jint saveUnclippedLayer(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jint l, jint t, jint r, jint b) {
     return reinterpret_cast<jint>(get_canvas(canvasHandle)->saveUnclippedLayer(l, t, r, b));
 }
 
-static void restoreUnclippedLayer(jlong canvasHandle, jint saveCount, jlong paintHandle) {
+static void restoreUnclippedLayer(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jint saveCount, jlong paintHandle) {
     Paint* paint = reinterpret_cast<Paint*>(paintHandle);
     get_canvas(canvasHandle)->restoreUnclippedLayer(saveCount, *paint);
 }
 
-static bool restore(jlong canvasHandle) {
+static bool restore(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle) {
     Canvas* canvas = get_canvas(canvasHandle);
     if (canvas->getSaveCount() <= 1) {
         return false; // cannot restore anymore
@@ -120,43 +124,43 @@
     return true; // success
 }
 
-static void restoreToCount(jlong canvasHandle, jint saveCount) {
+static void restoreToCount(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jint saveCount) {
     Canvas* canvas = get_canvas(canvasHandle);
     canvas->restoreToCount(saveCount);
 }
 
-static jint getSaveCount(jlong canvasHandle) {
+static jint getSaveCount(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle) {
     return static_cast<jint>(get_canvas(canvasHandle)->getSaveCount());
 }
 
-static void getMatrix(jlong canvasHandle, jlong matrixHandle) {
+static void getMatrix(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jlong matrixHandle) {
     SkMatrix* matrix = reinterpret_cast<SkMatrix*>(matrixHandle);
     get_canvas(canvasHandle)->getMatrix(matrix);
 }
 
-static void setMatrix(jlong canvasHandle, jlong matrixHandle) {
+static void setMatrix(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jlong matrixHandle) {
     const SkMatrix* matrix = reinterpret_cast<SkMatrix*>(matrixHandle);
     get_canvas(canvasHandle)->setMatrix(matrix ? *matrix : SkMatrix::I());
 }
 
-static void concat(jlong canvasHandle, jlong matrixHandle) {
+static void concat(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jlong matrixHandle) {
     const SkMatrix* matrix = reinterpret_cast<SkMatrix*>(matrixHandle);
     get_canvas(canvasHandle)->concat(*matrix);
 }
 
-static void rotate(jlong canvasHandle, jfloat degrees) {
+static void rotate(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jfloat degrees) {
     get_canvas(canvasHandle)->rotate(degrees);
 }
 
-static void scale(jlong canvasHandle, jfloat sx, jfloat sy) {
+static void scale(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jfloat sx, jfloat sy) {
     get_canvas(canvasHandle)->scale(sx, sy);
 }
 
-static void skew(jlong canvasHandle, jfloat sx, jfloat sy) {
+static void skew(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jfloat sx, jfloat sy) {
     get_canvas(canvasHandle)->skew(sx, sy);
 }
 
-static void translate(jlong canvasHandle, jfloat dx, jfloat dy) {
+static void translate(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jfloat dx, jfloat dy) {
     get_canvas(canvasHandle)->translate(dx, dy);
 }
 
@@ -174,13 +178,13 @@
     return result ? JNI_TRUE : JNI_FALSE;
 }
 
-static jboolean quickRejectRect(jlong canvasHandle,
+static jboolean quickRejectRect(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle,
                                 jfloat left, jfloat top, jfloat right, jfloat bottom) {
     bool result = get_canvas(canvasHandle)->quickRejectRect(left, top, right, bottom);
     return result ? JNI_TRUE : JNI_FALSE;
 }
 
-static jboolean quickRejectPath(jlong canvasHandle, jlong pathHandle) {
+static jboolean quickRejectPath(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jlong pathHandle) {
     SkPath* path = reinterpret_cast<SkPath*>(pathHandle);
     bool result = get_canvas(canvasHandle)->quickRejectPath(*path);
     return result ? JNI_TRUE : JNI_FALSE;
@@ -208,14 +212,14 @@
     return static_cast<SkClipOp>(rgnOp);
 }
 
-static jboolean clipRect(jlong canvasHandle, jfloat l, jfloat t,
+static jboolean clipRect(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jfloat l, jfloat t,
                          jfloat r, jfloat b, jint opHandle) {
     bool nonEmptyClip = get_canvas(canvasHandle)->clipRect(l, t, r, b,
             opHandleToClipOp(opHandle));
     return nonEmptyClip ? JNI_TRUE : JNI_FALSE;
 }
 
-static jboolean clipPath(jlong canvasHandle, jlong pathHandle,
+static jboolean clipPath(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jlong pathHandle,
                          jint opHandle) {
     SkPath* path = reinterpret_cast<SkPath*>(pathHandle);
     bool nonEmptyClip = get_canvas(canvasHandle)->clipPath(path, opHandleToClipOp(opHandle));
@@ -634,7 +638,7 @@
     env->ReleaseStringChars(text, jchars);
 }
 
-static void setPaintFilter(jlong canvasHandle, jlong filterHandle) {
+static void setPaintFilter(CRITICAL_JNI_PARAMS_COMMA jlong canvasHandle, jlong filterHandle) {
     PaintFilter* paintFilter = reinterpret_cast<PaintFilter*>(filterHandle);
     get_canvas(canvasHandle)->setPaintFilter(sk_ref_sp(paintFilter));
 }
diff --git a/core/jni/core_jni_helpers.h b/core/jni/core_jni_helpers.h
index 16ef753..f03f427 100644
--- a/core/jni/core_jni_helpers.h
+++ b/core/jni/core_jni_helpers.h
@@ -22,6 +22,18 @@
 #include <nativehelper/scoped_utf_chars.h>
 #include <android_runtime/AndroidRuntime.h>
 
+// Host targets (layoutlib) do not differentiate between regular and critical native methods,
+// and they need all the JNI methods to have JNIEnv* and jclass/jobject as their first two arguments.
+// The following macro allows to have those arguments when compiling for host while omitting them when
+// compiling for Android.
+#ifdef __ANDROID__
+#define CRITICAL_JNI_PARAMS
+#define CRITICAL_JNI_PARAMS_COMMA
+#else
+#define CRITICAL_JNI_PARAMS JNIEnv*, jclass
+#define CRITICAL_JNI_PARAMS_COMMA JNIEnv*, jclass,
+#endif
+
 namespace android {
 
 // Defines some helpful functions.
diff --git a/core/jni/include/android_runtime/AndroidRuntime.h b/core/jni/include/android_runtime/AndroidRuntime.h
index 3ec8b1f..a19f954 100644
--- a/core/jni/include/android_runtime/AndroidRuntime.h
+++ b/core/jni/include/android_runtime/AndroidRuntime.h
@@ -105,7 +105,7 @@
         void* arg);
 
     /** return a pointer to the VM running in this process */
-    static JavaVM* getJavaVM() { return mJavaVM; }
+    static JavaVM* getJavaVM();
 
     /** return a pointer to the JNIEnv pointer for this thread */
     static JNIEnv* getJNIEnv();