简体   繁体   中英

bypass-android-usb-host-permission-confirmation-dialog

I am trying to bypass usb permissions on android when android is used as host, i followed this link which provides the way to do it on Android 4.x bypass android usb host permission confirmation dialog

This doesn't work on Android 9.0, however. After checking the AOSP source code, it looks like there's quite a few changes for IUsbManager interface. I tried to stub out the new methods that were added, and I had to also create stubs for two more classes under the android.hardware.usb package along the way, name UsbPort and UsbPortStatus.

Here is the code i have for android 9.0, but it doesn't work. I keep getting NoSuchMethod exception when i call grantDevicePermission. The code for ServiceManager.java is the same as in the link so I didn't paste it here.

Help would be appreciated!

IUsbManager interface:

package android.hardware.usb;

import android.os.IBinder;

public interface IUsbManager extends android.os.IInterface
{
    /** Local-side IPC implementation stub class. */
    public static abstract class Stub extends android.os.Binder implements android.hardware.usb.IUsbManager
    {
        /** Construct the stub at attach it to the interface. */
        public Stub()
        {
            throw new RuntimeException( "Stub!" );
        }
        /**
         * Cast an IBinder object into an android.hardware.usb.IUsbManager interface,
         * generating a proxy if needed.
         */
        public static android.hardware.usb.IUsbManager asInterface( android.os.IBinder obj )
        {
            throw new RuntimeException( "Stub!" );
        }

    public android.os.IBinder asBinder()
    {
        throw new RuntimeException( "Stub!" );
    }

    public boolean onTransact( int code, android.os.Parcel data, android.os.Parcel reply, int flags ) throws android.os.RemoteException
    {
        throw new RuntimeException( "Stub!" );
    }

    static final int TRANSACTION_getDeviceList = (android.os.IBinder.FIRST_CALL_TRANSACTION + 0);
    static final int TRANSACTION_openDevice = (android.os.IBinder.FIRST_CALL_TRANSACTION + 1);
    static final int TRANSACTION_getCurrentAccessory = (android.os.IBinder.FIRST_CALL_TRANSACTION + 2);
    static final int TRANSACTION_openAccessory = (android.os.IBinder.FIRST_CALL_TRANSACTION + 3);
    static final int TRANSACTION_setDevicePackage = (android.os.IBinder.FIRST_CALL_TRANSACTION + 4);
    static final int TRANSACTION_setAccessoryPackage = (android.os.IBinder.FIRST_CALL_TRANSACTION + 5);
    static final int TRANSACTION_hasDevicePermission = (android.os.IBinder.FIRST_CALL_TRANSACTION + 6);
    static final int TRANSACTION_hasAccessoryPermission = (android.os.IBinder.FIRST_CALL_TRANSACTION + 7);
    static final int TRANSACTION_requestDevicePermission = (android.os.IBinder.FIRST_CALL_TRANSACTION + 8);
    static final int TRANSACTION_requestAccessoryPermission = (android.os.IBinder.FIRST_CALL_TRANSACTION + 9);
    static final int TRANSACTION_grantDevicePermission = (android.os.IBinder.FIRST_CALL_TRANSACTION + 10);
    static final int TRANSACTION_grantAccessoryPermission = (android.os.IBinder.FIRST_CALL_TRANSACTION + 11);
    static final int TRANSACTION_hasDefaults = (android.os.IBinder.FIRST_CALL_TRANSACTION + 12);
    static final int TRANSACTION_clearDefaults = (android.os.IBinder.FIRST_CALL_TRANSACTION + 13);
    static final int TRANSACTION_isFunctionEnabled = (android.os.IBinder.FIRST_CALL_TRANSACTION + 14);
    static final int TRANSACTION_setCurrentFunctions = (android.os.IBinder.FIRST_CALL_TRANSACTION + 15);
    static final int TRANSACTION_setCurrentFunction = (android.os.IBinder.FIRST_CALL_TRANSACTION + 16);
    static final int TRANSACTION_getCurrentFunctions = (android.os.IBinder.FIRST_CALL_TRANSACTION + 17);
    static final int TRANSACTION_setScreenUnlockedFunctions = (android.os.IBinder.FIRST_CALL_TRANSACTION + 18);
    static final int TRANSACTION_getScreenUnlockedFunctions = (android.os.IBinder.FIRST_CALL_TRANSACTION + 19);
    static final int TRANSACTION_getControlFd = (android.os.IBinder.FIRST_CALL_TRANSACTION + 20);
    static final int TRANSACTION_allowUsbDebugging = (android.os.IBinder.FIRST_CALL_TRANSACTION + 21);
    static final int TRANSACTION_denyUsbDebugging = (android.os.IBinder.FIRST_CALL_TRANSACTION + 22);
    static final int TRANSACTION_clearUsbDebuggingKeys = (android.os.IBinder.FIRST_CALL_TRANSACTION + 23);
    static final int TRANSACTION_getPorts = (android.os.IBinder.FIRST_CALL_TRANSACTION + 24);
    static final int TRANSACTION_getPortStatus = (android.os.IBinder.FIRST_CALL_TRANSACTION + 25);
    static final int TRANSACTION_setPortRoles = (android.os.IBinder.FIRST_CALL_TRANSACTION + 26);
    static final int TRANSACTION_setUsbDeviceConnectionHandler = (android.os.IBinder.FIRST_CALL_TRANSACTION + 27);
}

/* Returns a list of all currently attached USB devices */
public void getDeviceList( android.os.Bundle devices ) throws android.os.RemoteException;
/* Returns a file descriptor for communicating with the USB device.
 * The native fd can be passed to usb_device_new() in libusbhost.
 */
public android.os.ParcelFileDescriptor openDevice( java.lang.String deviceName, java.lang.String packageName) throws android.os.RemoteException;
/* Returns the currently attached USB accessory */
public android.hardware.usb.UsbAccessory getCurrentAccessory() throws android.os.RemoteException;
/* Returns a file descriptor for communicating with the USB accessory.
 * This file descriptor can be used with standard Java file operations.
 */
public android.os.ParcelFileDescriptor openAccessory( android.hardware.usb.UsbAccessory accessory ) throws android.os.RemoteException;
/* Sets the default package for a USB device
 * (or clears it if the package name is null)
 */
public void setDevicePackage(android.hardware.usb.UsbDevice device, java.lang.String packageName, int userId) throws android.os.RemoteException;
/* Sets the default package for a USB accessory
 * (or clears it if the package name is null)
 */
public void setAccessoryPackage( android.hardware.usb.UsbAccessory accessory, java.lang.String packageName, int userId ) throws android.os.RemoteException;
/* Returns true if the caller has permission to access the device. */
public boolean hasDevicePermission(android.hardware.usb.UsbDevice device, java.lang.String packageName) throws android.os.RemoteException;
/* Returns true if the caller has permission to access the accessory. */
public boolean hasAccessoryPermission( android.hardware.usb.UsbAccessory accessory ) throws android.os.RemoteException;
/* Requests permission for the given package to access the device.
 * Will display a system dialog to query the user if permission
 * had not already been given.
 */
public void requestDevicePermission( android.hardware.usb.UsbDevice device, java.lang.String packageName, android.app.PendingIntent pi ) throws android.os.RemoteException;
/* Requests permission for the given package to access the accessory.
 * Will display a system dialog to query the user if permission
 * had not already been given. Result is returned via pi.
 */
public void requestAccessoryPermission( android.hardware.usb.UsbAccessory accessory, java.lang.String packageName, android.app.PendingIntent pi ) throws android.os.RemoteException;
/* Grants permission for the given UID to access the device */
public void grantDevicePermission( android.hardware.usb.UsbDevice device, int uid ) throws android.os.RemoteException;
/* Grants permission for the given UID to access the accessory */
public void grantAccessoryPermission( android.hardware.usb.UsbAccessory accessory, int uid ) throws android.os.RemoteException;
/* Returns true if the USB manager has default preferences or permissions for the package */
public boolean hasDefaults( java.lang.String packageName, int userId ) throws android.os.RemoteException;
/* Clears default preferences and permissions for the package */
public void clearDefaults( java.lang.String packageName, int userId ) throws android.os.RemoteException;
/* Returns true if the specified USB function is enabled. */
public boolean isFunctionEnabled(java.lang.String function) throws android.os.RemoteException;
/* Sets the current USB function. */
public void setCurrentFunctions(long functions) throws android.os.RemoteException;
/* Sets the current USB function. */
public void setCurrentFunction( java.lang.String function, boolean usbDataUnlocked ) throws android.os.RemoteException;
/* Gets the current USB functions. */
public long getCurrentFunctions() throws android.os.RemoteException;
/* Sets the screen unlocked USB function(s), which will be set automatically
 * when the screen is unlocked.
 */
public void setScreenUnlockedFunctions(long functions) throws android.os.RemoteException;
/* Gets the current screen unlocked functions. */
public long getScreenUnlockedFunctions() throws android.os.RemoteException;
/* Get the functionfs control handle for the given function. Usb
 * descriptors will already be written, and the handle will be
 * ready to use.
 */
public android.os.ParcelFileDescriptor getControlFd(long function) throws android.os.RemoteException;
/* Allow USB debugging from the attached host. If alwaysAllow is true, add the
 * the public key to list of host keys that the user has approved.
 */
public void allowUsbDebugging(boolean alwaysAllow, java.lang.String publicKey) throws android.os.RemoteException;
/* Deny USB debugging from the attached host */
public void denyUsbDebugging() throws android.os.RemoteException;
/* Clear public keys installed for secure USB debugging */
public void clearUsbDebuggingKeys() throws android.os.RemoteException;
/* Gets the list of USB ports. */
public android.hardware.usb.UsbPort[] getPorts() throws android.os.RemoteException;
/* Gets the status of the specified USB port. */
public android.hardware.usb.UsbPortStatus getPortStatus(java.lang.String portId) throws android.os.RemoteException;
/* Sets the port's current role. */
public void setPortRoles(java.lang.String portId, int powerRole, int dataRole) throws android.os.RemoteException;
/* Sets USB device connection handler. */
public void setUsbDeviceConnectionHandler(android.content.ComponentName usbDeviceConnectionHandler) throws android.os.RemoteException;
}

UsbPort.java:

package android.hardware.usb;

public class UsbPort implements android.os.Parcelable {

/** @hide */
public UsbPort(String id, int supportedModes) {
    throw new RuntimeException( "Stub!" );
}

/**
 * Gets the unique id of the port.
 *
 * @return The unique id of the port; not intended for display.
 */
public String getId() {
    throw new RuntimeException( "Stub!" );
}

/**
 * Gets the supported modes of the port.
 * <p>
 * The actual mode of the port may vary depending on what is plugged into it.
 * </p>
 *
 */
public int getSupportedModes() {
    throw new RuntimeException( "Stub!" );
}

/**
 * Combines one power and one data role together into a unique value with
 * exactly one bit set.  This can be used to efficiently determine whether
 * a combination of roles is supported by testing whether that bit is present
 * in a bit-field.
 *
 */
public static int combineRolesAsBit(int powerRole, int dataRole) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public static String modeToString(int mode) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public static String powerRoleToString(int role) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public static String dataRoleToString(int role) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public static String roleCombinationsToString(int combo) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public static void checkMode(int powerRole) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public static void checkPowerRole(int dataRole) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public static void checkDataRole(int mode) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public static void checkRoles(int powerRole, int dataRole) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public boolean isModeSupported(int mode) {
    throw new RuntimeException( "Stub!" );
}


@Override
public String toString() {
    throw new RuntimeException( "Stub!" );
}

@Override
public int describeContents() {
    throw new RuntimeException( "Stub!" );
}

@Override
public void writeToParcel(android.os.Parcel dest, int flags) {
    throw new RuntimeException( "Stub!" );
}

public static final android.os.Parcelable.Creator<UsbPort> CREATOR =
        new android.os.Parcelable.Creator<UsbPort>() {
            @Override
            public UsbPort createFromParcel(android.os.Parcel in) {
                throw new RuntimeException( "Stub!" );
            }

            @Override
            public UsbPort[] newArray(int size) {
                throw new RuntimeException( "Stub!" );
            }
        };
}

UsbPortStatus.java:

package android.hardware.usb;

public class UsbPortStatus implements android.os.Parcelable {

/** @hide */
public UsbPortStatus(int currentMode, int currentPowerRole, int currentDataRole,
                     int supportedRoleCombinations) {
    throw new RuntimeException( "Stub!" );
}

/**
 * Returns true if there is anything connected to the port.
 *
 */
public boolean isConnected() {
    throw new RuntimeException( "Stub!" );
}

/**
 * Gets the current mode of the port.
 *
 */
public int getCurrentMode() {
    throw new RuntimeException( "Stub!" );
}

/**
 * Gets the current power role of the port.
 *
 */
public int getCurrentPowerRole() {
    throw new RuntimeException( "Stub!" );
}

/**
 * Gets the current data role of the port.
 *
 */
public int getCurrentDataRole() {
    throw new RuntimeException( "Stub!" );
}

/**
 * Returns true if the specified power and data role combination is supported
 * given what is currently connected to the port.
 *
 */
public boolean isRoleCombinationSupported(int powerRole, int dataRole) {
    throw new RuntimeException( "Stub!" );
}

/** @hide */
public int getSupportedRoleCombinations() {
    throw new RuntimeException( "Stub!" );
}

@Override
public String toString() {
    throw new RuntimeException( "Stub!" );
}

@Override
public int describeContents() {
    throw new RuntimeException( "Stub!" );
}

@Override
public void writeToParcel(android.os.Parcel dest, int flags) {
    throw new RuntimeException( "Stub!" );
}

public static final android.os.Parcelable.Creator<UsbPortStatus> CREATOR =
        new android.os.Parcelable.Creator<UsbPortStatus>() {
            @Override
            public UsbPortStatus createFromParcel(android.os.Parcel in) {
                throw new RuntimeException( "Stub!" );
            }

            @Override
            public UsbPortStatus[] newArray(int size) {
                throw new RuntimeException( "Stub!" );
            }
        };
}

It's new restrictions on non-SDK interfaces (Android 9): https://developer.android.com/distribute/best-practices/develop/restrictions-non-sdk-interfaces

Can be solved by:

adb shell
su
settings put global hidden_api_policy_pre_p_apps  1
settings put global hidden_api_policy_p_apps 1

https://stackoverflow.com/a/57622623/7767664

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM