Two Android apps with the same name, why?
Is there a reason why an Android device can start a new process with the same name, with the same user ID and a different PID, and keep the old one?
The manifest does not specify any other processes than the standard one.
The old process can be killed with the kill command in the terminal.
Is this the expected behavior in some specific cases, or is this an Android bug?
the manifest looks like this:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.mycompany.myapp"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="15"
android:targetSdkVersion="19" />
<!-- omitted <uses-permission> tags -->
<application
android:name=".MyApplication"
android:allowBackup="true"
android:hardwareAccelerated="true"
android:icon="@drawable/ic_launcher"
android:label="@string/app_name"
android:theme="@android:style/Theme.Holo.NoActionBar.Fullscreen" >
<!-- Start up -->
<activity
android:name=".activity.SplashScreenActivity"
android:configChanges="orientation|keyboardHidden" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<!-- other non-launcher activities... -->
<!-- Auto start on boot -->
<receiver android:name=".receiver.StartEventsReceiver" >
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</receiver>
<!-- Update content and configuration -->
<receiver
android:name=".receiver.UpdateContentReceiver"
android:exported="false" >
<intent-filter>
<action android:name="com.mycompany.myapp.UPDATE_CONTENT" />
<action android:name="com.mycompany.myapp.CONTENT_UPDATED" />
</intent-filter>
</receiver>
<!-- other receivers and services... -->
</application>
</manifest>
UPDATE . I managed to get some records. My app has a receiver called UpdateContentReceiver
(manifest above updated) that gets called every minute with intent UPDATE_CONTENT
sent from the main message queue. It does some polling and exits the network. He worked...
08-30 09:46:57.419 2512 2512 V UpdateContentReceiver: Received UPDATE_CONTENT
08-30 09:46:58.349 2512 2512 V UpdateContentReceiver: No update
08-30 09:47:57.439 2512 2512 V UpdateContentReceiver: Received UPDATE_CONTENT
08-30 09:47:57.739 2512 2512 V UpdateContentReceiver: No update
08-30 09:48:57.439 2512 2512 V UpdateContentReceiver: Received UPDATE_CONTENT
08-30 09:49:02.389 2512 2512 V UpdateContentReceiver: No update
... but next time ...
08-30 09:49:57.459 1879 1904 E JavaBinder: !!! FAILED BINDER TRANSACTION !!!
08-30 09:49:57.469 1879 1904 W BroadcastQueue: Exception when sending broadcast to ComponentInfo{com.mycompany.myapp/com.mycompany.myapp.receiver.UpdateContentReceiver}
08-30 09:49:57.469 1879 1904 W BroadcastQueue: android.os.TransactionTooLargeException
08-30 09:49:57.469 1879 1904 W BroadcastQueue: at android.os.BinderProxy.transact(Native Method)
08-30 09:49:57.469 1879 1904 W BroadcastQueue: at android.app.ApplicationThreadProxy.scheduleReceiver(ApplicationThreadNative.java:771)
08-30 09:49:57.469 1879 1904 W BroadcastQueue: at com.android.server.am.BroadcastQueue.processCurBroadcastLocked(BroadcastQueue.java:231)
08-30 09:49:57.469 1879 1904 W BroadcastQueue: at com.android.server.am.BroadcastQueue.processNextBroadcast(BroadcastQueue.java:778)
08-30 09:49:57.469 1879 1904 W BroadcastQueue: at com.android.server.am.BroadcastQueue$1.handleMessage(BroadcastQueue.java:140)
08-30 09:49:57.469 1879 1904 W BroadcastQueue: at android.os.Handler.dispatchMessage(Handler.java:99)
08-30 09:49:57.469 1879 1904 W BroadcastQueue: at android.os.Looper.loop(Looper.java:137)
08-30 09:49:57.469 1879 1904 W BroadcastQueue: at com.android.server.am.ActivityManagerService$AThread.run(ActivityManagerService.java:1487)
08-30 09:49:57.469 1879 1904 W ActivityManagerService: Scheduling restart of crashed service com.mycompany.myapp/.service.ServiceFoo in 5000ms
08-30 09:49:57.469 1879 1904 W ActivityManagerService: Scheduling restart of crashed service com.mycompany.myapp/.service.ServiceBar in 14999ms
08-30 09:49:57.469 1879 1904 W ActivityManagerServiceActivityStack_hong: Force removing ActivityRecord{42768bf8 u0 com.mycompany.myapp/.activity.MyActivity}: app died, no saved state
08-30 09:49:57.529 1879 1904 I ActivityManagerService: Start proc com.mycompany.myapp for broadcast com.mycompany.myapp/.receiver.UpdateContentReceiver: pid=27119 uid=10044 gids={50044, 3003, 1028, 1015, 1023}
The last line clearly states that a new process is being created. After that I see in the logs that it MyApplication
starts up three times with different PIDs until it settles with the last life process. Here's the output ps|grep myapp
:
u0_a44 2512 1286 755540 85548 ffffffff 4003fee4 S com.mycompany.myapp
u0_a44 28541 1286 772220 79204 ffffffff 4003fee4 S com.mycompany.myapp
I can't tell you why this is happening TransactionTooLargeException
(we dispatch UPDATE_CONTENT
without any extra functions, so there is little memory space), but at least I know why the new process is being created. However, it is not clear why the old process is not destroyed. The app has an internal web server: maybe Android sees that it is listening on a TCP port and refuses to kill it?
The funny thing is that the new process doesn't start its own web server (because the listening port is already bound), but everything "works" because the old web server is still alive!
source to share
referencing this: Restarting the Activity at Home button, but ... just the first time or this: How to prevent multiple instances of an activity from being launched with different intents
you can define your application as: android:launchMode="singleInstance"
But I choose:
if (!isTaskRoot()) {
final Intent intent = getIntent();
final String intentAction = intent.getAction();
if (intent.hasCategory(Intent.CATEGORY_LAUNCHER) && intentAction != null && intentAction.equals(Intent.ACTION_MAIN)) {
Log.w(LOG_TAG, "Main Activity is not the root. Finishing Main Activity instead of launching.");
finish();
return;
}
}
Edit: (awaiting the manifest in the question)
Android: Multiple Processes Is it possible to instantiate an action in the process of the component that started it - "true" if possible and "false" if not. The default is "false".
Typically, a new activity instance is launched in the application process that defined it, so all activity instances run in the same process. However, when this flag is set to "true", instances of an activity can run across multiple processes, allowing the system to instantiate where they are used (if permissions allow), which is almost never necessary or desirable.
source: https://developer.android.com/guide/topics/manifest/activity-element.html
source to share