Unable to use USE_ICC_AUTH_WITH_DEVICE_IDENTIFIER permission signed Android app

671 Views Asked by At

for my use cases I needed to extract non-resettable hardware information like IMEI, MAC from android devices.

As per the android docs for getting IMEI https://developer.android.com/reference/android/telephony/TelephonyManager#getImei(int)

It says the method can be invoked if one of the following requirements is met. and I am trying to satisfy. If the calling app has been granted the USE_ICC_AUTH_WITH_DEVICE_IDENTIFIER permission.

As per permission API document https://developer.android.com/reference/android/Manifest.permission#USE_ICC_AUTH_WITH_DEVICE_IDENTIFIER this permission has protection level signature or apops

So, I am going ahead with signature protection level. So, I am creating a signed app and running on my andriod device google pixel 5A which runs on Android 12.

when I am running this code I am facing "The user 10240 does not meet the requirements to access device identifiers." security exception

2022-06-30 12:09:53.703 23348-23348/com.android.dataextraction E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.android.dataextraction, PID: 23348
    java.lang.RuntimeException: Unable to start activity ComponentInfo{com.android.dataextraction/com.android.dataextraction.LauncherActivity}: java.lang.SecurityException: getImeiForSlot: The user 10240 does not meet the requirements to access device identifiers.
        at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3635)
        at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3792)
        at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:103)
        at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135)
        at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95)
        at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2210)
        at android.os.Handler.dispatchMessage(Handler.java:106)
        at android.os.Looper.loopOnce(Looper.java:201)
        at android.os.Looper.loop(Looper.java:288)
        at android.app.ActivityThread.main(ActivityThread.java:7839)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:548)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1003)
     Caused by: java.lang.SecurityException: getImeiForSlot: The user 10240 does not meet the requirements to access device identifiers.
        at android.os.Parcel.createExceptionOrNull(Parcel.java:2425)
        at android.os.Parcel.createException(Parcel.java:2409)
        at android.os.Parcel.readException(Parcel.java:2392)
        at android.os.Parcel.readException(Parcel.java:2334)
        at com.android.internal.telephony.ITelephony$Stub$Proxy.getImeiForSlot(ITelephony.java:12142)
        at android.telephony.TelephonyManager.getImei(TelephonyManager.java:2088)
        at android.telephony.TelephonyManager.getImei(TelephonyManager.java:2043)
        at com.android.dataextraction.LauncherActivity.onCreate(LauncherActivity.java:44)
        at android.app.Activity.performCreate(Activity.java:8051)
        at android.app.Activity.performCreate(Activity.java:8031)
        at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1329)
        at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:3608)
        at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:3792) 
        at android.app.servertransaction.LaunchActivityItem.execute(LaunchActivityItem.java:103) 
        at android.app.servertransaction.TransactionExecutor.executeCallbacks(TransactionExecutor.java:135) 
        at android.app.servertransaction.TransactionExecutor.execute(TransactionExecutor.java:95) 
        at android.app.ActivityThread$H.handleMessage(ActivityThread.java:2210) 
        at android.os.Handler.dispatchMessage(Handler.java:106) 
        at android.os.Looper.loopOnce(Looper.java:201) 
        at android.os.Looper.loop(Looper.java:288) 
        at android.app.ActivityThread.main(ActivityThread.java:7839) 
        at java.lang.reflect.Method.invoke(Native Method) 
        at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:548) 
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1003) 

and I am using a signed app for testing. here is my build. Gradle configs

signingConfigs {
        config {
            keyAlias 'AndroidKey'
            keyPassword '**********'
            storeFile file('../android.jks')
            storePassword '********'
        }
    }

buildTypes {
        
        debug {
            signingConfig signingConfigs.config
            debuggable true
        }
    }

There is no problem with signing the app.

I am not sure why signature protection level is not allowing me to access device identifiers

1

There are 1 best solutions below

4
Toan Le On

Take a second look at definition of signature protection

A permission that the system grants only if the requesting application is signed with the same certificate as the application that declared the permission. If the certificates match, the system automatically grants the permission without notifying the user or asking for the user's explicit approval.

Unless your app is signed with Google's keystore (same keystore as the provider signing your firmware), it cannot get access to signature-level permission.