USB设备识别为存储设备并查找路径
USBdevice recognise as storage device and find path
如何检测已安装的可用于存储的设备(例如笔式驱动器)?如何找到安装的存储设备的路径以便从中读取文件?
我使用了以下广播接收器获取访问挂载设备的权限:
private final BroadcastReceiver mUsbReceiver = new BroadcastReceiver() {
public void onReceive(Context context, Intent intent) {
String action = intent.getAction();
if (ACTION_USB_PERMISSION.equals(action)) {
synchronized (this) {
UsbDevice device = (UsbDevice) intent
.getParcelableExtra(UsbManager.EXTRA_DEVICE);
if (intent.getBooleanExtra(
UsbManager.EXTRA_PERMISSION_GRANTED, false)) {
if (device != null) {
// call method to set up device communication
Log.d(TAG, "onReceive: "+intent.getExtras().toString());
Log.d(TAG, "onReceive: "+intent.getData());
LinearLayout layoutUsbList = (LinearLayout)findViewById(R.id.layout_usb_list);
Button btn = new Button(MainActivity.this);
btn.setLayoutParams(new LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT));
layoutUsbList.addView(btn);
btn.setText(device.getDeviceId()+"\t"+device.getDeviceName());
Log.d(TAG, "onReceive: "+intent.getExtras().toString());
final String path = intent.getData().getPath();
Log.e(TAG, "onReceive: path of device received from intent: "+ path );
btn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
File file = new File(path);
Toast.makeText(MainActivity.this, "file exists --> "+file.exists()+"", Toast.LENGTH_SHORT).show();
Toast.makeText(MainActivity.this, "file is directory --> "+file.isDirectory()+"", Toast.LENGTH_SHORT).show();
Log.d(TAG, "onClick: file is directory --> "+file.isDirectory()+"");
try{
Toast.makeText(MainActivity.this, file.listFiles().length+"", Toast.LENGTH_LONG).show();
}catch(Exception e){
Toast.makeText(MainActivity.this, "error while showing total items", Toast.LENGTH_SHORT).show();
}
}
});
}
} else {
Log.d("ERROR", "permission denied for device " + device);
}
}
}
}
};
清单文件:
<?xml version="1.0" encoding="utf-8"?>
<uses-feature android:name="android.hardware.usb.host"/>
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme">
<activity
android:name=".MainActivity"
android:configChanges="keyboard|orientation"
android:label="@string/app_name">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
<intent-filter>
<action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED"/>
</intent-filter>
<meta-data
android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED"
android:resource="@xml/device_filter"/>
<intent-filter>
<action android:name="android.hardware.usb.action.USB_DEVICE_DETACHED"/>
</intent-filter>
<!---->
<!---->
<!---->
<intent-filter>
<action android:name="android.intent.action.MEDIA_MOUNTED"/>
<data android:scheme="file"/>
</intent-filter>
</activity>
</application>
根据这个 pdf refrencing this library。
每个大容量存储设备至少有一个接口描述符,其 class 代码为 08h,
代表大容量存储class。设备中未定义大容量存储器 class
描述符! USB 接口恰好有两个端点描述符。一个 IN 端点到
从设备读取和一个 OUT 端点写入设备2。读写
在这种情况下并不一定意味着在实际存储介质上读取或写入,
这在后面描述。
关于大容量存储有两种不同的类型class。有 bulk-only
运输(BBB)机制,这是最常见的一种。所有较新的设备都遵循这一点
标准。然后是 Control/Bulk/Interrupt (CBI) 标准,它不再是
重要,因为 USB-IF 建议使用 BBB 方法
UsbDevice 被识别为 massStorage 设备如果:
usbInterface.getInterfaceClass() == UsbConstants.USB_CLASS_MASS_STORAGE
|| usbInterface.getInterfaceSubclass() == INTERFACE_SUBCLASS // int 6
|| usbInterface.getInterfaceProtocol() == INTERFACE_PROTOCOL // int 80
和
usbInterface.getEndpointCount() == 2
在哪里
其中一个端点必须满足以下条件:
endPoint direction == 0
endPoint type = UsbConstants.USB_ENDPOINT_XFER_BULK //int 2
如何检测已安装的可用于存储的设备(例如笔式驱动器)?如何找到安装的存储设备的路径以便从中读取文件?
我使用了以下广播接收器获取访问挂载设备的权限:
private final BroadcastReceiver mUsbReceiver = new BroadcastReceiver() {
public void onReceive(Context context, Intent intent) {
String action = intent.getAction();
if (ACTION_USB_PERMISSION.equals(action)) {
synchronized (this) {
UsbDevice device = (UsbDevice) intent
.getParcelableExtra(UsbManager.EXTRA_DEVICE);
if (intent.getBooleanExtra(
UsbManager.EXTRA_PERMISSION_GRANTED, false)) {
if (device != null) {
// call method to set up device communication
Log.d(TAG, "onReceive: "+intent.getExtras().toString());
Log.d(TAG, "onReceive: "+intent.getData());
LinearLayout layoutUsbList = (LinearLayout)findViewById(R.id.layout_usb_list);
Button btn = new Button(MainActivity.this);
btn.setLayoutParams(new LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT));
layoutUsbList.addView(btn);
btn.setText(device.getDeviceId()+"\t"+device.getDeviceName());
Log.d(TAG, "onReceive: "+intent.getExtras().toString());
final String path = intent.getData().getPath();
Log.e(TAG, "onReceive: path of device received from intent: "+ path );
btn.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
File file = new File(path);
Toast.makeText(MainActivity.this, "file exists --> "+file.exists()+"", Toast.LENGTH_SHORT).show();
Toast.makeText(MainActivity.this, "file is directory --> "+file.isDirectory()+"", Toast.LENGTH_SHORT).show();
Log.d(TAG, "onClick: file is directory --> "+file.isDirectory()+"");
try{
Toast.makeText(MainActivity.this, file.listFiles().length+"", Toast.LENGTH_LONG).show();
}catch(Exception e){
Toast.makeText(MainActivity.this, "error while showing total items", Toast.LENGTH_SHORT).show();
}
}
});
}
} else {
Log.d("ERROR", "permission denied for device " + device);
}
}
}
}
};
清单文件:
<?xml version="1.0" encoding="utf-8"?>
<uses-feature android:name="android.hardware.usb.host"/>
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:theme="@style/AppTheme">
<activity
android:name=".MainActivity"
android:configChanges="keyboard|orientation"
android:label="@string/app_name">
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
<intent-filter>
<action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED"/>
</intent-filter>
<meta-data
android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED"
android:resource="@xml/device_filter"/>
<intent-filter>
<action android:name="android.hardware.usb.action.USB_DEVICE_DETACHED"/>
</intent-filter>
<!---->
<!---->
<!---->
<intent-filter>
<action android:name="android.intent.action.MEDIA_MOUNTED"/>
<data android:scheme="file"/>
</intent-filter>
</activity>
</application>
根据这个 pdf refrencing this library。 每个大容量存储设备至少有一个接口描述符,其 class 代码为 08h, 代表大容量存储class。设备中未定义大容量存储器 class 描述符! USB 接口恰好有两个端点描述符。一个 IN 端点到 从设备读取和一个 OUT 端点写入设备2。读写 在这种情况下并不一定意味着在实际存储介质上读取或写入, 这在后面描述。 关于大容量存储有两种不同的类型class。有 bulk-only 运输(BBB)机制,这是最常见的一种。所有较新的设备都遵循这一点 标准。然后是 Control/Bulk/Interrupt (CBI) 标准,它不再是 重要,因为 USB-IF 建议使用 BBB 方法
UsbDevice 被识别为 massStorage 设备如果:
usbInterface.getInterfaceClass() == UsbConstants.USB_CLASS_MASS_STORAGE
|| usbInterface.getInterfaceSubclass() == INTERFACE_SUBCLASS // int 6
|| usbInterface.getInterfaceProtocol() == INTERFACE_PROTOCOL // int 80
和
usbInterface.getEndpointCount() == 2
在哪里 其中一个端点必须满足以下条件:
endPoint direction == 0
endPoint type = UsbConstants.USB_ENDPOINT_XFER_BULK //int 2