AndroidL的checkPermission方法详解
?在Android源碼的很多地方都會(huì)出現(xiàn)權(quán)限檢查的方法checkPermission,此篇文字主要介紹Android5.1.1源碼中的checkPermission方法是如何實(shí)現(xiàn)的,在此以WallpaperManagerService.java中的checkPermission方法為例來(lái)分析。
./base/services/core/java/com/android/server/wallpaper/WallpaperManagerService.java
? ? ........? ? final Context mContext;
? ? ........
? ? public WallpaperManagerService(Context context) {
? ? ? ? mContext = context;
? ? ? ? ........
? ? }
? ? ........
? ? private void checkPermission(String permission) {
? ? ? ??// 調(diào)用Context的checkCallingOrSelfPermission來(lái)檢查權(quán)限
? ? ? ??if (PackageManager.PERMISSION_GRANTED!= mContext.checkCallingOrSelfPermission(permission)) {?
? ? ? ? ? ? throw new SecurityException("Access denied to process: " + Binder.getCallingPid()? ? ? ? ? ? ? ? ? ? + ", must have permission " + permission);
? ? ? ? }
? ? }
checkCallingOrSelfPermission中checkCallingOrSelfPermission的定義
./base/core/java/android/context/Context.java?
? ? public abstract int checkCallingOrSelfPermission(@NonNull String permission);
ContextImpl實(shí)現(xiàn)了Context接口,權(quán)限檢查是在ContextImpl類(lèi)的checkPermission方法來(lái)完成的
./base/core/java/android/app/ContextImpl.java?
? ? @Override
? ? public int checkPermission(String permission, int pid, int uid) {
? ? ? ? if (permission == null) {
? ? ? ? ? ? throw new IllegalArgumentException("permission is null");
? ? ? ? }
? ? ? ? try {
? ? ? ? ? ? return ActivityManagerNative.getDefault().checkPermission(
? ? ? ? ? ? ? ? ? ? permission, pid, uid);?// 調(diào)用ActivityManagerNative的getDefault()方法來(lái)獲取ActivityManagerService的對(duì)象
? ? ? ? } catch (RemoteException e) {
? ? ? ? ? ? return PackageManager.PERMISSION_DENIED;
? ? ? ? }
? ? }
? ? ........
? ? @Override
? ? public int checkCallingOrSelfPermission(String permission) {
? ? ? ? if (permission == null) {
? ? ? ? ? ? throw new IllegalArgumentException("permission is null");
? ? ? ? }
? ? ? ? return checkPermission(permission, Binder.getCallingPid(),
? ? ? ? ? ? ? ? Binder.getCallingUid());?// 調(diào)用checkPermission函數(shù)來(lái)檢查權(quán)限
? ? }
ActivityManagerNative中g(shù)etDefault方法實(shí)現(xiàn)過(guò)程
./base/core/java/android/app/ActivityManagerNative.java
? ? static public IActivityManager getDefault() {
? ? ? ? return gDefault.get();?// 最終返回的是個(gè)ActivityManagerService的對(duì)象
? ? }
ActivityManagerService中checkPermission的實(shí)現(xiàn)過(guò)程
./base/services/core/java/com/android/server/am/ActivityManagerService.java
? ? int checkComponentPermission(String permission, int pid, int uid,
? ? ? ? ? ? int owningUid, boolean exported) {
? ? ? ? // We might be performing an operation on behalf of an indirect binder
? ? ? ? // invocation, e.g. via {@link #openContentUri}. ?Check and adjust the
? ? ? ? // client identity accordingly before proceeding.
? ? ? ? Identity tlsIdentity = sCallerIdentity.get();
? ? ? ? if (tlsIdentity != null) {
? ? ? ? ? ? Slog.d(TAG, "checkComponentPermission() adjusting {pid,uid} to {"
? ? ? ? ? ? ? ? ? ? + tlsIdentity.pid + "," + tlsIdentity.uid + "}");
? ? ? ? ? ? uid = tlsIdentity.uid;
? ? ? ? ? ? pid = tlsIdentity.pid;
? ? ? ? }
? ? ? ? if (pid == MY_PID) {
? ? ? ? ? ? return PackageManager.PERMISSION_GRANTED;
? ? ? ? }
? ? ? ? return ActivityManager.checkComponentPermission(permission, uid,
? ? ? ? ? ? ? ? owningUid, exported);?// 調(diào)用ActivityManager的checkComponentPermission來(lái)檢查權(quán)限
? ? }
? ? ........
? ? @Override
? ? public int checkPermission(String permission, int pid, int uid) {
? ? ? ? if (permission == null) {
? ? ? ? ? ? return PackageManager.PERMISSION_DENIED;
? ? ? ? }
? ? ? ??// 調(diào)用checkComponentPermission函數(shù)來(lái)檢查權(quán)限
? ? }
ActivityManager中checkComponentPermission的實(shí)現(xiàn)過(guò)程
./base/core/java/android/app/ActivityManager.java
? ? public static int checkComponentPermission(String permission, int uid,
? ? ? ? ? ? int owningUid, boolean exported) {
? ? ? ? ........
? ? ? ? try {
? ? ? ? ? ? return AppGlobals.getPackageManager()?// 調(diào)用AppGlobals的getPackageManager()函數(shù)返回IPackageManager對(duì)象
? ? ? ? ? ? ? ? ? ? .checkUidPermission(permission, uid);
? ? ? ? } catch (RemoteException e) {
? ? ? ? ? ? // Should never happen, but if it does... deny!
? ? ? ? ? ? Slog.e(TAG, "PackageManager is dead?!?", e);
? ? ? ? }
? ? ? ? return PackageManager.PERMISSION_DENIED;
? ? }
AppGlobals的getPackageManager方法實(shí)現(xiàn)過(guò)程
./base/core/java/android/app/AppGlobals.java
? ? public static IPackageManager getPackageManager() {
? ? ? ? return ActivityThread.getPackageManager();?// 調(diào)用ActivityThread的getPackageManager()函數(shù)
? ? }
ActivityThread的getPackageManager實(shí)現(xiàn)過(guò)程
./base/core/java/android/app/ActivityThread.java
? ? public static IPackageManager getPackageManager() {
? ? ? ? if (sPackageManager != null) {
? ? ? ? ? ? //Slog.v("PackageManager", "returning cur default = " + sPackageManager);
? ? ? ? ? ? return sPackageManager;
? ? ? ? }
? ? ? ? IBinder b = ServiceManager.getService("package");
? ? ? ? //Slog.v("PackageManager", "default service binder = " + b);
? ? ? ? sPackageManager = IPackageManager.Stub.asInterface(b);??// 最終獲取的是PackageManagerService的對(duì)象
? ? ? ? //Slog.v("PackageManager", "default service = " + sPackageManager);
? ? ? ? return sPackageManager;
? ? }
PackageManagerService的checkUidPermission實(shí)現(xiàn)過(guò)程
./base/services/core/java/com/android/server/pm/PackageManagerService.java
? ? @Override
? ? public int checkUidPermission(String permName, int uid) {
? ? ? ? synchronized (mPackages) {
? ? ? ? ? ? Object obj = mSettings.getUserIdLPr(UserHandle.getAppId(uid));
? ? ? ? ? ? if (obj != null) {
? ? ? ? ? ? ? ? GrantedPermissions gp = (GrantedPermissions)obj;
? ? ? ? ? ? ? ? if (gp.grantedPermissions.contains(permName)) {?// 判斷應(yīng)用是否已聲明了此權(quán)限
? ? ? ? ? ? ? ? ? ? return PackageManager.PERMISSION_GRANTED;
? ? ? ? ? ? ? ? }
? ? ? ? ? ? } else {
? ? ? ? ? ? ? ? HashSet<String> perms = mSystemPermissions.get(uid);
? ? ? ? ? ? ? ? if (perms != null && perms.contains(permName)) {
? ? ? ? ? ? ? ? ? ? return PackageManager.PERMISSION_GRANTED;
? ? ? ? ? ? ? ? }
? ? ? ? ? ? }
? ? ? ? }
? ? ? ? return PackageManager.PERMISSION_DENIED;
? ? }
至此權(quán)限檢查就已完成
原文地址:?
總結(jié)
以上是生活随笔為你收集整理的AndroidL的checkPermission方法详解的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: Android 插件化原理解析——Hoo
- 下一篇: PackageManagerServic