Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

java.lang.NullPointerException: Attempt to get length of null array on some Huawei devices #1505

Closed
coolguy001tv opened this issue Jan 22, 2019 · 24 comments

Comments

@coolguy001tv
Copy link

Steps to Reproduce

1.crash log shows this error

Expected Behavior

no crash

Actual Behavior

crashed, here's the log:

 java.lang.RuntimeException: Unable to start activity ComponentInfo{com.tota123.fatboy/com.tota123.fatboy.MainActivity}: java.lang.NullPointerException: Attempt to get length of null array
	at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3300)
	at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3484)
	at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:86)
	at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:108)
	at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:68)
	at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2123)
	at android.os.Handler.dispatchMessage(Handler.java:109)
	at android.os.Looper.loop(Looper.java:207)
	at android.app.ActivityThread.main(ActivityThread.java:7470)
	at java.lang.reflect.Method.invoke(Native Method)
	at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:524)
	at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:958)
Caused by: java.lang.NullPointerException: Attempt to get length of null array
	at com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently(FileUtils.java:75)
	at com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently(FileUtils.java:77)
	at com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently(FileUtils.java:77)
	at com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently(FileUtils.java:77)
	at com.microsoft.codepush.react.FileUtils.deleteDirectoryAtPath(FileUtils.java:64)
	at com.microsoft.codepush.react.CodePushUpdateManager.clearUpdates(CodePushUpdateManager.java:332)
	at com.microsoft.codepush.react.CodePush.clearUpdates(CodePush.java:264)
	at com.microsoft.codepush.react.CodePush.getJSBundleFileInternal(CodePush.java:175)
	at com.microsoft.codepush.react.CodePush.getJSBundleFile(CodePush.java:140)
	at com.microsoft.codepush.react.CodePush.getJSBundleFile(CodePush.java:132)
	at com.tota123.fatboy.MainApplication$1.getJSBundleFile(MainApplication.java:58)
	at com.facebook.react.ReactNativeHost.createReactInstanceManager(ReactNativeHost.java:78)
	at com.facebook.react.ReactNativeHost.getReactInstanceManager(ReactNativeHost.java:41)
	at com.facebook.react.ReactActivityDelegate.loadApp(ReactActivityDelegate.java:111)
	at com.facebook.react.ReactActivityDelegate.onCreate(ReactActivityDelegate.java:100)
	at com.facebook.react.ReactActivity.onCreate(ReactActivity.java:54)
	at com.tota123.fatboy.MainActivity.onCreate(MainActivity.java:84)
	at android.app.Activity.performCreate(Activity.java:7436)
	at android.app.Activity.performCreate(Activity.java:7426)
	at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1286)
	at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3279)
	... 11 more

Environment

react-native-code-push version:4.0.0-beta
react-native version:0.46.0 (I know it's so old, we're trying updating)
iOS/Android/Windows version: android
Does this reproduce on a debug build or release build? release
Does this reproduce on a simulator, or only on a physical device? physical device

Other Info

Actually there is a similar issue here #1458
which is not solved but closed.
This happens on a HuaWei Mate20 phone.
It is occasionally happened and I got no such a cellphone, so I cann't reproduct it.
According to the log above, it seems that the deleteFileOrFolderSilently should be responsible for the crash.
https://github.com/Microsoft/react-native-code-push/blob/3144c916018fab077231e88d8718ad3a1cb0a7d8/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java#L74-L75

It seems that files is null? According to file.listFiles doc, this func should return An array of abstract pathnames denoting the files and directories in the directory denoted by this abstract pathname. The array will be empty if the directory is empty. Returns null if this abstract pathname does not denote a directory, or if an I/O error occurs.
So, an I/O error occurs?

@yuri-kulikov
Copy link
Contributor

Hi @coolguy001tv,
Thanks for reporting!

Did it occasionally happen on your device (not Huawei Mate20)? Did I understand you correctly?

@coolguy001tv
Copy link
Author

coolguy001tv commented Jan 23, 2019

I just see it on some logs from server. It shows me there is a crash. I don't own this device.
So I just know it happened. Yet I think it's occasionally happened.
I don't know if I make myself clear.

@yuri-kulikov
Copy link
Contributor

Thanks, I understand now. I think this question might be related to app permissions and it's very strange, these Huawei devices may have an unusual memory configuration, but we can't test it without the actual device, so we can only assume the reasons.

@coolguy001tv
Copy link
Author

Thanks for the reply. I'll try to add the permission.
Besides, I think the code here should have an if-not-null-test between line 74 & 75.
https://github.com/Microsoft/react-native-code-push/blob/3144c916018fab077231e88d8718ad3a1cb0a7d8/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java#L74-L75

@coolguy001tv
Copy link
Author

@yuri-kulikov
Hi~ When I have my colleague checked our app's uses-permission ( I am not familar with Android) , and the android.permission.READ_EXTERNAL_STORAGE is in the list. It can't be the read permission.
Besides, our logs are created each time when app crashes. So if there is a read/write permission, the log can't be created and can't be uploaded to our server. But in fact we see the log in our server.

@yuri-kulikov
Copy link
Contributor

Hey @coolguy001tv,
Sorry for the delay!

Besides, I think the code here should have an if-not-null-test between line 74 & 75.

I think you're right!

However, it still won't solve the issue completely. These specific devices won't be crashed, but still won't be able to update via CodePush. And it's weird that file.isDirectory() returns true before the crash. We will try to investigate the issue in more detail.

@coolguy001tv
Copy link
Author

Thanks. If I get more info, I shall comment it here.
I think I shall have left this issue open for now, at least until the if-not-null-test coded.

@pawlowskim
Copy link

Same problem here:

Android, Huawei Mate 20 Pro Dual SIM (LYA-L29), Android 9, free disk space: 115924271104, free memory: 400024576.
We just released a new version of the app couple days ago, and there isn't any code-push patch for this version yet. This is first time it occurs.

    ActivityThread.java:3300 android.app.ActivityThread.performLaunchActivity
    ActivityThread.java:3484 android.app.ActivityThread.handleLaunchActivity
    LaunchActivityItem.java:86 android.app.servertransaction.LaunchActivityItem.execute
    TransactionExecutor.java:108 android.app.servertransaction.TransactionExecutor.executeCallbacks
    TransactionExecutor.java:68 android.app.servertransaction.TransactionExecutor.execute
    ActivityThread.java:2123 android.app.ActivityThread$H.handleMessage
    Handler.java:109 android.os.Handler.dispatchMessage
    Looper.java:207 android.os.Looper.loop
    ActivityThread.java:7470 android.app.ActivityThread.main
    Method.java:-2 java.lang.reflect.Method.invoke
    RuntimeInit.java:524 com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run
    ZygoteInit.java:958 com.android.internal.os.ZygoteInit.main


Caused by: java.lang.NullPointerException Attempt to get length of null array 
    FileUtils.java:75 com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently
    FileUtils.java:77 com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently
    FileUtils.java:77 com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently
    FileUtils.java:77 com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently
    FileUtils.java:64 com.microsoft.codepush.react.FileUtils.deleteDirectoryAtPath
    CodePushUpdateManager.java:367 com.microsoft.codepush.react.CodePushUpdateManager.clearUpdates
    CodePush.java:359 com.microsoft.codepush.react.CodePush.clearUpdates
    CodePush.java:241 com.microsoft.codepush.react.CodePush.getJSBundleFileInternal
    CodePush.java:209 com.microsoft.codepush.react.CodePush.getJSBundleFile
    CodePush.java:201 com.microsoft.codepush.react.CodePush.getJSBundleFile
    MainApplication.java:88 xxx.xxx.xxx.MainApplication$1.getJSBundleFile
    ReactNativeHost.java:82 com.facebook.react.ReactNativeHost.createReactInstanceManager
    ReactNativeHost.java:41 com.facebook.react.ReactNativeHost.getReactInstanceManager
    ReactActivityDelegate.java:86 com.facebook.react.ReactActivityDelegate.loadApp
    ReactActivityDelegate.java:75 com.facebook.react.ReactActivityDelegate.onCreate
    ReactActivity.java:52 com.facebook.react.ReactActivity.onCreate
    MainActivity.java:20 xxx.xxx.xxx.MainActivity.onCreate
    Activity.java:7436 android.app.Activity.performCreate
    Activity.java:7426 android.app.Activity.performCreate
    Instrumentation.java:1286 android.app.Instrumentation.callActivityOnCreate
    ActivityThread.java:3279 android.app.ActivityThread.performLaunchActivity
    ActivityThread.java:3484 android.app.ActivityThread.handleLaunchActivity
    LaunchActivityItem.java:86 android.app.servertransaction.LaunchActivityItem.execute
    TransactionExecutor.java:108 android.app.servertransaction.TransactionExecutor.executeCallbacks
    TransactionExecutor.java:68 android.app.servertransaction.TransactionExecutor.execute
    ActivityThread.java:2123 android.app.ActivityThread$H.handleMessage
    Handler.java:109 android.os.Handler.dispatchMessage
    Looper.java:207 android.os.Looper.loop
    ActivityThread.java:7470 android.app.ActivityThread.main
    Method.java:-2 java.lang.reflect.Method.invoke
    RuntimeInit.java:524 com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run
    ZygoteInit.java:958 com.android.internal.os.ZygoteInit.main

@coolguy001tv
Copy link
Author

@pawlowskim After I modified the code with an if-not-null-test like discussed above(fork this repo and then modify) , it seems that no devices crash with this error any more. U may try this if the official still faces this.

@pawlowskim
Copy link

I will give it a try when it happens again. Thanks @coolguy001tv
BTW. We are using RN: 0.59.10 and code-push: 5.6.0 (both pretty up to date)

@coolguy001tv
Copy link
Author

@pawlowskim Good luck to you. Besides, we've already updated rn with 0.58.1.

@henrymoulton
Copy link

@pawlowskim did the fix @coolguy001tv suggest work for you?

@pawlowskim
Copy link

@henrymoulton Not occurred again yet.

@henrymoulton
Copy link

henrymoulton commented Aug 27, 2019

Sounds good, rather than forking I've used patch-package, @coolguy001tv was this the patch you recommend?

diff --git a/node_modules/react-native-code-push/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java b/node_modules/react-native-code-push/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java
index 29d52ec..b57db9b 100644
--- a/node_modules/react-native-code-push/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java
+++ b/node_modules/react-native-code-push/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java
@@ -72,11 +72,13 @@ public class FileUtils {
     public static void deleteFileOrFolderSilently(File file) {
         if (file.isDirectory()) {
             File[] files = file.listFiles();
-            for (File fileEntry : files) {
-                if (fileEntry.isDirectory()) {
-                    deleteFileOrFolderSilently(fileEntry);
-                } else {
-                    fileEntry.delete();
+            if (files != null) {
+                for (File fileEntry : files) {
+                    if (fileEntry.isDirectory()) {
+                        deleteFileOrFolderSilently(fileEntry);
+                    } else {
+                        fileEntry.delete();
+                    }
                 }
             }
         }

@coolguy001tv
Copy link
Author

@henrymoulton Yes, this is the patch I recommend. Besides, I also recommend to modify Line 25 for the same reason:


U may refer here to see my modification.

@henrymoulton
Copy link

diff --git a/node_modules/react-native-code-push/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java b/node_modules/react-native-code-push/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java
index 29d52ec..cb6926f 100644
--- a/node_modules/react-native-code-push/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java
+++ b/node_modules/react-native-code-push/android/app/src/main/java/com/microsoft/codepush/react/FileUtils.java
@@ -22,7 +22,11 @@ public class FileUtils {
             destDir.mkdir();
         }
 
-        for (File sourceFile : sourceDir.listFiles()) {
+        File[] files = sourceDir.listFiles();
+        if (files == null) {
+            return;
+        }
+        for (File sourceFile : files) {
             if (sourceFile.isDirectory()) {
                 copyDirectoryContents(
                         CodePushUtils.appendPathComponent(sourceDirectoryPath, sourceFile.getName()),
@@ -72,6 +76,9 @@ public class FileUtils {
     public static void deleteFileOrFolderSilently(File file) {
         if (file.isDirectory()) {
             File[] files = file.listFiles();
+            if (files == null) {
+                return;
+            }
             for (File fileEntry : files) {
                 if (fileEntry.isDirectory()) {
                     deleteFileOrFolderSilently(fileEntry);

Is the patch I'm applying, will feedback how it goes

@adnkh
Copy link

adnkh commented Sep 11, 2019

I have this issue also in production

Screen Shot 2019-09-11 at 12 28 07 PM

Thanks for the patch @henrymoulton, Has this worked for you?

@henrymoulton
Copy link

henrymoulton commented Sep 11, 2019 via email

@henrymoulton
Copy link

@adnkh no longer seeing the com.microsoft.codepush.react.FileUtils.copyDirectoryContents error but still seeing the com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently error

@henrymoulton
Copy link

@coolguy001tv did your patch resolve the com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently problem?

@coolguy001tv
Copy link
Author

@henrymoulton It never occurs again after using the patch. So I think it at least bypasses the com.microsoft.codepush.react.FileUtils.deleteFileOrFolderSilently crash.

@julianD77
Copy link

We are also seeing this issue affecting numerous Huawei devices. Can anyone confirm whether the patch above (or another fix to prevent the crash) is likely to be merged into a release at some point please?

@coolguy001tv
Copy link
Author

@julianD77 Sorry I can't. Since microsoft code-push is so slow in China, we have to migrate to another code-push-like solution.

@snowpardx snowpardx removed the bug label Oct 9, 2020
@snowpardx
Copy link

Hi there.

We investigated the problem and found the following:

  1. the api shouldn't return the null in cases different from when it executed against the non-folder entity https://developer.android.google.cn/reference/java/io/File#listFiles()
  2. there are some cases in reality when the call returns null if there are no permission to read the catalog
  3. the particular code path which attempted to be cleared out is persisted in the app folder, so no special permission are required for the app to work with that even on Android 10 and further.

Unfortunately applying the patch mentioned above in the issue is not an option, because it would just skip deletion which is not expected.

Issue affects only some devices and caused by API to behave against the specification, and may be fixed with OS updates already or be fixed in the future. Until this fixed, we don't have solid solution for the code to work as expected on those devices.

So right now I'm going just close the issue.

@snowpardx snowpardx changed the title java.lang.NullPointerException: Attempt to get length of null array java.lang.NullPointerException: Attempt to get length of null array on some Huawei devices Oct 29, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

7 participants