[core] Workaround for service manager overwritten on Android R (#581)
This commit is contained in:
parent
d9f95d1280
commit
0df0a14808
|
|
@ -0,0 +1,7 @@
|
||||||
|
package org.lsposed.lspd.service;
|
||||||
|
|
||||||
|
import org.lsposed.lspd.service.ILSPApplicationService;
|
||||||
|
|
||||||
|
interface ILSPSystemServerService {
|
||||||
|
ILSPApplicationService requestApplicationService(int uid, int pid, String processName, IBinder heartBeat) = 1;
|
||||||
|
}
|
||||||
|
|
@ -36,21 +36,21 @@ public class LSPApplicationServiceClient implements ILSPApplicationService {
|
||||||
static String processName = null;
|
static String processName = null;
|
||||||
|
|
||||||
public static LSPApplicationServiceClient serviceClient = null;
|
public static LSPApplicationServiceClient serviceClient = null;
|
||||||
|
private static final IBinder.DeathRecipient recipient = new IBinder.DeathRecipient() {
|
||||||
public static void Init(IBinder binder, String niceName) {
|
|
||||||
if (serviceClient == null && binder != null && serviceBinder == null && service == null) {
|
|
||||||
serviceBinder = binder;
|
|
||||||
processName = niceName;
|
|
||||||
try {
|
|
||||||
serviceBinder.linkToDeath(
|
|
||||||
new IBinder.DeathRecipient() {
|
|
||||||
@Override
|
@Override
|
||||||
public void binderDied() {
|
public void binderDied() {
|
||||||
serviceBinder.unlinkToDeath(this, 0);
|
serviceBinder.unlinkToDeath(this, 0);
|
||||||
serviceBinder = null;
|
serviceBinder = null;
|
||||||
service = null;
|
service = null;
|
||||||
}
|
}
|
||||||
}, 0);
|
};
|
||||||
|
|
||||||
|
public static void Init(IBinder binder, String niceName) {
|
||||||
|
if (serviceClient == null && binder != null && serviceBinder == null && service == null) {
|
||||||
|
serviceBinder = binder;
|
||||||
|
processName = niceName;
|
||||||
|
try {
|
||||||
|
serviceBinder.linkToDeath(recipient, 0);
|
||||||
} catch (RemoteException e) {
|
} catch (RemoteException e) {
|
||||||
Utils.logE("link to death error: ", e);
|
Utils.logE("link to death error: ", e);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -34,14 +34,10 @@ import static org.lsposed.lspd.service.ServiceManager.TAG;
|
||||||
|
|
||||||
public class ActivityManagerService {
|
public class ActivityManagerService {
|
||||||
private static IActivityManager am = null;
|
private static IActivityManager am = null;
|
||||||
|
|
||||||
private static IBinder binder = null;
|
private static IBinder binder = null;
|
||||||
|
|
||||||
public static IActivityManager getActivityManager() {
|
private static final IBinder.DeathRecipient deathRecipient = new IBinder.DeathRecipient() {
|
||||||
if (binder == null && am == null) {
|
|
||||||
binder = ServiceManager.getService("activity");
|
|
||||||
if (binder == null) return null;
|
|
||||||
try {
|
|
||||||
binder.linkToDeath(new IBinder.DeathRecipient() {
|
|
||||||
@Override
|
@Override
|
||||||
public void binderDied() {
|
public void binderDied() {
|
||||||
Log.w(TAG, "am is dead");
|
Log.w(TAG, "am is dead");
|
||||||
|
|
@ -49,7 +45,14 @@ public class ActivityManagerService {
|
||||||
binder = null;
|
binder = null;
|
||||||
am = null;
|
am = null;
|
||||||
}
|
}
|
||||||
}, 0);
|
};
|
||||||
|
|
||||||
|
public static IActivityManager getActivityManager() {
|
||||||
|
if (binder == null && am == null) {
|
||||||
|
binder = ServiceManager.getService("activity");
|
||||||
|
if (binder == null) return null;
|
||||||
|
try {
|
||||||
|
binder.linkToDeath(deathRecipient, 0);
|
||||||
} catch (RemoteException e) {
|
} catch (RemoteException e) {
|
||||||
Log.e(TAG, Log.getStackTraceString(e));
|
Log.e(TAG, Log.getStackTraceString(e));
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -64,13 +64,8 @@ public class BridgeService {
|
||||||
private static ILSPosedService service = null;
|
private static ILSPosedService service = null;
|
||||||
|
|
||||||
// for service
|
// for service
|
||||||
static class BridgeServiceDeathRecipient implements IBinder.DeathRecipient {
|
private static IBinder bridgeService;
|
||||||
private final IBinder bridgeService;
|
private static final IBinder.DeathRecipient bridgeRecipient = new IBinder.DeathRecipient() {
|
||||||
|
|
||||||
BridgeServiceDeathRecipient(IBinder bridgeService) throws RemoteException {
|
|
||||||
this.bridgeService = bridgeService;
|
|
||||||
bridgeService.linkToDeath(this, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void binderDied() {
|
public void binderDied() {
|
||||||
|
|
@ -96,16 +91,21 @@ public class BridgeService {
|
||||||
}
|
}
|
||||||
|
|
||||||
bridgeService.unlinkToDeath(this, 0);
|
bridgeService.unlinkToDeath(this, 0);
|
||||||
|
bridgeService = null;
|
||||||
listener.onSystemServerDied();
|
listener.onSystemServerDied();
|
||||||
sendToBridge(serviceBinder, true);
|
sendToBridge(serviceBinder, true);
|
||||||
}
|
}
|
||||||
}
|
};
|
||||||
|
|
||||||
// for client
|
// for client
|
||||||
private static final IBinder.DeathRecipient LSPSERVICE_DEATH_RECIPIENT = () -> {
|
private static final IBinder.DeathRecipient serviceRecipient = new IBinder.DeathRecipient() {
|
||||||
|
@Override
|
||||||
|
public void binderDied() {
|
||||||
|
serviceBinder.unlinkToDeath(this, 0);
|
||||||
serviceBinder = null;
|
serviceBinder = null;
|
||||||
service = null;
|
service = null;
|
||||||
Log.e(TAG, "service is dead");
|
Log.e(TAG, "service is dead");
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
public interface Listener {
|
public interface Listener {
|
||||||
|
|
@ -121,7 +121,6 @@ public class BridgeService {
|
||||||
|
|
||||||
// For service
|
// For service
|
||||||
private static void sendToBridge(IBinder binder, boolean isRestart) {
|
private static void sendToBridge(IBinder binder, boolean isRestart) {
|
||||||
IBinder bridgeService;
|
|
||||||
do {
|
do {
|
||||||
bridgeService = ServiceManager.getService(SERVICE_NAME);
|
bridgeService = ServiceManager.getService(SERVICE_NAME);
|
||||||
if (bridgeService != null && bridgeService.pingBinder()) {
|
if (bridgeService != null && bridgeService.pingBinder()) {
|
||||||
|
|
@ -143,7 +142,7 @@ public class BridgeService {
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
new BridgeServiceDeathRecipient(bridgeService);
|
bridgeService.linkToDeath(bridgeRecipient, 0);
|
||||||
} catch (Throwable e) {
|
} catch (Throwable e) {
|
||||||
Log.w(TAG, "linkToDeath " + Log.getStackTraceString(e));
|
Log.w(TAG, "linkToDeath " + Log.getStackTraceString(e));
|
||||||
sendToBridge(binder, false);
|
sendToBridge(binder, false);
|
||||||
|
|
@ -218,15 +217,16 @@ public class BridgeService {
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
serviceBinder.unlinkToDeath(LSPSERVICE_DEATH_RECIPIENT, 0);
|
serviceBinder.unlinkToDeath(serviceRecipient, 0);
|
||||||
}
|
}
|
||||||
Binder.restoreCallingIdentity(token);
|
Binder.restoreCallingIdentity(token);
|
||||||
|
|
||||||
serviceBinder = Binder_allowBlocking(binder);
|
serviceBinder = Binder_allowBlocking(binder);
|
||||||
service = ILSPosedService.Stub.asInterface(serviceBinder);
|
service = ILSPosedService.Stub.asInterface(serviceBinder);
|
||||||
try {
|
try {
|
||||||
serviceBinder.linkToDeath(LSPSERVICE_DEATH_RECIPIENT, 0);
|
serviceBinder.linkToDeath(serviceRecipient, 0);
|
||||||
} catch (RemoteException ignored) {
|
} catch (Throwable e) {
|
||||||
|
Log.e(TAG, "service link to death: ", e);
|
||||||
}
|
}
|
||||||
|
|
||||||
Log.i(TAG, "binder received");
|
Log.i(TAG, "binder received");
|
||||||
|
|
@ -324,8 +324,8 @@ public class BridgeService {
|
||||||
public static IBinder getApplicationServiceForSystemServer(IBinder binder, IBinder heartBeat) {
|
public static IBinder getApplicationServiceForSystemServer(IBinder binder, IBinder heartBeat) {
|
||||||
if (binder == null || heartBeat == null) return null;
|
if (binder == null || heartBeat == null) return null;
|
||||||
try {
|
try {
|
||||||
ILSPosedService service = ILSPosedService.Stub.asInterface(binder);
|
var service = ILSPSystemServerService.Stub.asInterface(binder);
|
||||||
ILSPApplicationService applicationService = service.requestApplicationService(Process.myUid(), Process.myPid(), "android", heartBeat);
|
var applicationService = service.requestApplicationService(Process.myUid(), Process.myPid(), "android", heartBeat);
|
||||||
if (applicationService != null) return applicationService.asBinder();
|
if (applicationService != null) return applicationService.asBinder();
|
||||||
} catch (Throwable e) {
|
} catch (Throwable e) {
|
||||||
Log.e(TAG, Log.getStackTraceString(e));
|
Log.e(TAG, Log.getStackTraceString(e));
|
||||||
|
|
|
||||||
|
|
@ -35,18 +35,22 @@ public class LSPApplicationService extends ILSPApplicationService.Stub {
|
||||||
// <uid, pid>
|
// <uid, pid>
|
||||||
private final static Set<Pair<Integer, Integer>> cache = ConcurrentHashMap.newKeySet();
|
private final static Set<Pair<Integer, Integer>> cache = ConcurrentHashMap.newKeySet();
|
||||||
private final static Set<IBinder> handles = ConcurrentHashMap.newKeySet();
|
private final static Set<IBinder> handles = ConcurrentHashMap.newKeySet();
|
||||||
|
private final static Set<IBinder.DeathRecipient> recipients = ConcurrentHashMap.newKeySet();
|
||||||
|
|
||||||
public boolean registerHeartBeat(int uid, int pid, IBinder handle) {
|
public boolean registerHeartBeat(int uid, int pid, IBinder handle) {
|
||||||
try {
|
try {
|
||||||
handle.linkToDeath(new DeathRecipient() {
|
var recipient = new DeathRecipient() {
|
||||||
@Override
|
@Override
|
||||||
public void binderDied() {
|
public void binderDied() {
|
||||||
Log.d(TAG, "pid=" + pid + " uid=" + uid + " is dead.");
|
Log.d(TAG, "pid=" + pid + " uid=" + uid + " is dead.");
|
||||||
cache.remove(new Pair<>(uid, pid));
|
cache.remove(new Pair<>(uid, pid));
|
||||||
handles.remove(handle);
|
handles.remove(handle);
|
||||||
handle.unlinkToDeath(this, 0);
|
handle.unlinkToDeath(this, 0);
|
||||||
|
recipients.remove(this);
|
||||||
}
|
}
|
||||||
}, 0);
|
};
|
||||||
|
recipients.add(recipient);
|
||||||
|
handle.linkToDeath(recipient, 0);
|
||||||
handles.add(handle);
|
handles.add(handle);
|
||||||
cache.add(new Pair<>(uid, pid));
|
cache.add(new Pair<>(uid, pid));
|
||||||
return true;
|
return true;
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,82 @@
|
||||||
|
package org.lsposed.lspd.service;
|
||||||
|
|
||||||
|
import static org.lsposed.lspd.service.ServiceManager.TAG;
|
||||||
|
import static org.lsposed.lspd.service.ServiceManager.getSystemServiceManager;
|
||||||
|
|
||||||
|
import android.os.Build;
|
||||||
|
import android.os.IBinder;
|
||||||
|
import android.os.IServiceCallback;
|
||||||
|
import android.os.Parcel;
|
||||||
|
import android.os.RemoteException;
|
||||||
|
import android.util.Log;
|
||||||
|
|
||||||
|
public class LSPSystemServerService extends ILSPSystemServerService.Stub implements IBinder.DeathRecipient {
|
||||||
|
|
||||||
|
public static final String PROXY_SERVICE_NAME = "serial";
|
||||||
|
|
||||||
|
private IBinder originService = null;
|
||||||
|
|
||||||
|
public void putBinderForSystemServer() {
|
||||||
|
android.os.ServiceManager.addService(PROXY_SERVICE_NAME, this);
|
||||||
|
binderDied();
|
||||||
|
}
|
||||||
|
|
||||||
|
private final IServiceCallback serviceCallback = new IServiceCallback.Stub() {
|
||||||
|
@Override
|
||||||
|
public void onRegistration(String name, IBinder binder) {
|
||||||
|
if (name.equals(PROXY_SERVICE_NAME) && binder != null && binder != LSPSystemServerService.this) {
|
||||||
|
Log.d(TAG, "Register " + name + " " + binder);
|
||||||
|
originService = binder;
|
||||||
|
LSPSystemServerService.this.linkToDeath();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public IBinder asBinder() {
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
public LSPSystemServerService() {
|
||||||
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
|
||||||
|
try {
|
||||||
|
getSystemServiceManager().registerForNotifications(PROXY_SERVICE_NAME, serviceCallback);
|
||||||
|
} catch (Throwable e) {
|
||||||
|
Log.e(TAG, "unregister: ", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public ILSPApplicationService requestApplicationService(int uid, int pid, String processName, IBinder heartBeat) throws RemoteException {
|
||||||
|
if (ConfigManager.getInstance().shouldSkipSystemServer() || uid != 1000 || heartBeat == null || !"android".equals(processName))
|
||||||
|
return null;
|
||||||
|
else
|
||||||
|
return ServiceManager.requestApplicationService(uid, pid, heartBeat);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean onTransact(int code, Parcel data, Parcel reply, int flags) throws RemoteException {
|
||||||
|
if (originService != null) {
|
||||||
|
return originService.transact(code, data, reply, flags);
|
||||||
|
}
|
||||||
|
|
||||||
|
return super.onTransact(code, data, reply, flags);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void linkToDeath() {
|
||||||
|
try {
|
||||||
|
originService.linkToDeath(this, 0);
|
||||||
|
} catch (Throwable e) {
|
||||||
|
Log.e(TAG, "system server service: link to death", e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void binderDied() {
|
||||||
|
if (originService != null) {
|
||||||
|
originService.unlinkToDeath(this, 0);
|
||||||
|
originService = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -42,12 +42,6 @@ public class LSPosedService extends ILSPosedService.Stub {
|
||||||
Log.w(TAG, "Someone else got my binder!?");
|
Log.w(TAG, "Someone else got my binder!?");
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
if (uid == 1000 && processName.equals("android")) {
|
|
||||||
if (ConfigManager.getInstance().shouldSkipSystemServer())
|
|
||||||
return null;
|
|
||||||
else
|
|
||||||
return ServiceManager.requestApplicationService(uid, pid, heartBeat);
|
|
||||||
}
|
|
||||||
if (ConfigManager.getInstance().shouldSkipProcess(new ConfigManager.ProcessScope(processName, uid))) {
|
if (ConfigManager.getInstance().shouldSkipProcess(new ConfigManager.ProcessScope(processName, uid))) {
|
||||||
Log.d(TAG, "Skipped " + processName + "/" + uid);
|
Log.d(TAG, "Skipped " + processName + "/" + uid);
|
||||||
return null;
|
return null;
|
||||||
|
|
@ -60,7 +54,6 @@ public class LSPosedService extends ILSPosedService.Stub {
|
||||||
return ServiceManager.requestApplicationService(uid, pid, heartBeat);
|
return ServiceManager.requestApplicationService(uid, pid, heartBeat);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void dispatchPackageChanged(Intent intent) throws RemoteException {
|
public void dispatchPackageChanged(Intent intent) throws RemoteException {
|
||||||
if (Binder.getCallingUid() != 1000 || intent == null) return;
|
if (Binder.getCallingUid() != 1000 || intent == null) return;
|
||||||
|
|
|
||||||
|
|
@ -67,13 +67,7 @@ import hidden.HiddenApiBridge;
|
||||||
public class PackageService {
|
public class PackageService {
|
||||||
private static IPackageManager pm = null;
|
private static IPackageManager pm = null;
|
||||||
private static IBinder binder = null;
|
private static IBinder binder = null;
|
||||||
|
private static final IBinder.DeathRecipient recipient = new IBinder.DeathRecipient() {
|
||||||
public static IPackageManager getPackageManager() {
|
|
||||||
if (binder == null && pm == null) {
|
|
||||||
binder = ServiceManager.getService("package");
|
|
||||||
if (binder == null) return null;
|
|
||||||
try {
|
|
||||||
binder.linkToDeath(new IBinder.DeathRecipient() {
|
|
||||||
@Override
|
@Override
|
||||||
public void binderDied() {
|
public void binderDied() {
|
||||||
Log.w(TAG, "pm is dead");
|
Log.w(TAG, "pm is dead");
|
||||||
|
|
@ -81,7 +75,14 @@ public class PackageService {
|
||||||
binder = null;
|
binder = null;
|
||||||
pm = null;
|
pm = null;
|
||||||
}
|
}
|
||||||
}, 0);
|
};
|
||||||
|
|
||||||
|
public static IPackageManager getPackageManager() {
|
||||||
|
if (binder == null && pm == null) {
|
||||||
|
binder = ServiceManager.getService("package");
|
||||||
|
if (binder == null) return null;
|
||||||
|
try {
|
||||||
|
binder.linkToDeath(recipient, 0);
|
||||||
} catch (RemoteException e) {
|
} catch (RemoteException e) {
|
||||||
Log.e(TAG, Log.getStackTraceString(e));
|
Log.e(TAG, Log.getStackTraceString(e));
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -11,13 +11,7 @@ import static org.lsposed.lspd.service.ServiceManager.TAG;
|
||||||
public class PowerService {
|
public class PowerService {
|
||||||
private static IPowerManager pm = null;
|
private static IPowerManager pm = null;
|
||||||
private static IBinder binder = null;
|
private static IBinder binder = null;
|
||||||
|
private static final IBinder.DeathRecipient recipient = new IBinder.DeathRecipient() {
|
||||||
public static IPowerManager getPowerManager() {
|
|
||||||
if (binder == null && pm == null) {
|
|
||||||
binder = ServiceManager.getService("power");
|
|
||||||
if (binder == null) return null;
|
|
||||||
try {
|
|
||||||
binder.linkToDeath(new IBinder.DeathRecipient() {
|
|
||||||
@Override
|
@Override
|
||||||
public void binderDied() {
|
public void binderDied() {
|
||||||
Log.w(TAG, "pm is dead");
|
Log.w(TAG, "pm is dead");
|
||||||
|
|
@ -25,7 +19,14 @@ public class PowerService {
|
||||||
binder = null;
|
binder = null;
|
||||||
pm = null;
|
pm = null;
|
||||||
}
|
}
|
||||||
}, 0);
|
};
|
||||||
|
|
||||||
|
public static IPowerManager getPowerManager() {
|
||||||
|
if (binder == null && pm == null) {
|
||||||
|
binder = ServiceManager.getService("power");
|
||||||
|
if (binder == null) return null;
|
||||||
|
try {
|
||||||
|
binder.linkToDeath(recipient, 0);
|
||||||
} catch (RemoteException e) {
|
} catch (RemoteException e) {
|
||||||
Log.e(TAG, Log.getStackTraceString(e));
|
Log.e(TAG, Log.getStackTraceString(e));
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -20,18 +20,23 @@
|
||||||
package org.lsposed.lspd.service;
|
package org.lsposed.lspd.service;
|
||||||
|
|
||||||
import android.content.Context;
|
import android.content.Context;
|
||||||
import android.os.Build;
|
|
||||||
import android.os.IBinder;
|
import android.os.IBinder;
|
||||||
|
import android.os.IServiceManager;
|
||||||
import android.os.Looper;
|
import android.os.Looper;
|
||||||
import android.util.Log;
|
import android.util.Log;
|
||||||
|
|
||||||
|
import com.android.internal.os.BinderInternal;
|
||||||
|
|
||||||
import org.lsposed.lspd.BuildConfig;
|
import org.lsposed.lspd.BuildConfig;
|
||||||
|
|
||||||
|
import hidden.HiddenApiBridge;
|
||||||
|
|
||||||
public class ServiceManager {
|
public class ServiceManager {
|
||||||
private static LSPosedService mainService = null;
|
private static LSPosedService mainService = null;
|
||||||
private static LSPModuleService moduleService = null;
|
private static LSPModuleService moduleService = null;
|
||||||
private static LSPApplicationService applicationService = null;
|
private static LSPApplicationService applicationService = null;
|
||||||
private static LSPManagerService managerService = null;
|
private static LSPManagerService managerService = null;
|
||||||
|
private static LSPSystemServerService systemServerService = null;
|
||||||
public static final String TAG = "LSPosedService";
|
public static final String TAG = "LSPosedService";
|
||||||
|
|
||||||
private static void waitSystemService(String name) {
|
private static void waitSystemService(String name) {
|
||||||
|
|
@ -45,8 +50,8 @@ public class ServiceManager {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void putBinderForSystemServer() {
|
public static IServiceManager getSystemServiceManager() {
|
||||||
android.os.ServiceManager.addService("serial", mainService);
|
return IServiceManager.Stub.asInterface(HiddenApiBridge.Binder_allowBlocking(BinderInternal.getContextObject()));
|
||||||
}
|
}
|
||||||
|
|
||||||
// call by ourselves
|
// call by ourselves
|
||||||
|
|
@ -63,8 +68,9 @@ public class ServiceManager {
|
||||||
moduleService = new LSPModuleService();
|
moduleService = new LSPModuleService();
|
||||||
applicationService = new LSPApplicationService();
|
applicationService = new LSPApplicationService();
|
||||||
managerService = new LSPManagerService();
|
managerService = new LSPManagerService();
|
||||||
|
systemServerService = new LSPSystemServerService();
|
||||||
|
|
||||||
putBinderForSystemServer();
|
systemServerService.putBinderForSystemServer();
|
||||||
|
|
||||||
waitSystemService("package");
|
waitSystemService("package");
|
||||||
waitSystemService("activity");
|
waitSystemService("activity");
|
||||||
|
|
@ -89,7 +95,7 @@ public class ServiceManager {
|
||||||
@Override
|
@Override
|
||||||
public void onSystemServerDied() {
|
public void onSystemServerDied() {
|
||||||
Log.w(TAG, "system server died");
|
Log.w(TAG, "system server died");
|
||||||
putBinderForSystemServer();
|
systemServerService.putBinderForSystemServer();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -34,13 +34,7 @@ import static org.lsposed.lspd.service.ServiceManager.TAG;
|
||||||
public class UserService {
|
public class UserService {
|
||||||
private static IUserManager um = null;
|
private static IUserManager um = null;
|
||||||
private static IBinder binder = null;
|
private static IBinder binder = null;
|
||||||
|
private static IBinder.DeathRecipient recipient = new IBinder.DeathRecipient() {
|
||||||
public static IUserManager getUserManager() {
|
|
||||||
if (binder == null && um == null) {
|
|
||||||
binder = ServiceManager.getService("user");
|
|
||||||
if (binder == null) return null;
|
|
||||||
try {
|
|
||||||
binder.linkToDeath(new IBinder.DeathRecipient() {
|
|
||||||
@Override
|
@Override
|
||||||
public void binderDied() {
|
public void binderDied() {
|
||||||
Log.w(TAG, "um is dead");
|
Log.w(TAG, "um is dead");
|
||||||
|
|
@ -48,7 +42,14 @@ public class UserService {
|
||||||
binder = null;
|
binder = null;
|
||||||
um = null;
|
um = null;
|
||||||
}
|
}
|
||||||
}, 0);
|
};
|
||||||
|
|
||||||
|
public static IUserManager getUserManager() {
|
||||||
|
if (binder == null && um == null) {
|
||||||
|
binder = ServiceManager.getService("user");
|
||||||
|
if (binder == null) return null;
|
||||||
|
try {
|
||||||
|
binder.linkToDeath(recipient, 0);
|
||||||
} catch (RemoteException e) {
|
} catch (RemoteException e) {
|
||||||
Log.e(TAG, Log.getStackTraceString(e));
|
Log.e(TAG, Log.getStackTraceString(e));
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,13 @@
|
||||||
|
package android.os;
|
||||||
|
public interface IServiceCallback extends IInterface
|
||||||
|
{
|
||||||
|
public static abstract class Stub extends android.os.Binder implements android.os.IServiceCallback {
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Called when a service is registered.
|
||||||
|
*
|
||||||
|
* @param name the service name that has been registered with
|
||||||
|
* @param binder the binder that is registered
|
||||||
|
*/
|
||||||
|
public void onRegistration(java.lang.String name, android.os.IBinder binder) throws android.os.RemoteException;
|
||||||
|
}
|
||||||
|
|
@ -1,4 +1,16 @@
|
||||||
package android.os;
|
package android.os;
|
||||||
|
|
||||||
public interface IServiceManager {
|
public interface IServiceManager extends IInterface {
|
||||||
|
|
||||||
|
void tryUnregisterService(java.lang.String name, android.os.IBinder service);
|
||||||
|
|
||||||
|
IBinder getService(String name);
|
||||||
|
|
||||||
|
public void registerForNotifications(String name, IServiceCallback cb);
|
||||||
|
|
||||||
|
abstract class Stub extends Binder implements IServiceManager {
|
||||||
|
public static IServiceManager asInterface(IBinder obj) {
|
||||||
|
throw new UnsupportedOperationException();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,7 @@
|
||||||
|
package com.android.internal.os;
|
||||||
|
|
||||||
|
import android.os.IBinder;
|
||||||
|
|
||||||
|
public class BinderInternal {
|
||||||
|
public static final native IBinder getContextObject();
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue