首页 文章

USB Control Transfer使用libusb获取AudioStreaming描述符

提问于
浏览
2

我目前正在使用libusb(1.0.9)为我的Android应用程序支持USB麦克风(Samson Q1U) . 我从设备获得数据流没有问题,但我想读取有关数据格式(位深度,采样率,通道)的信息 . 到目前为止,USB一直很混乱,所以请原谅我在下面使用它的尝试 . 问题是控制转移,我不相信它设置正确 . 我尝试了许多不同的传输参数组合,但都有返回错误代码-1,-7和-9 . 任何帮助都会很棒 .

基本上,我想得到这个描述符:

AudioStreaming Interface Descriptor:
    bLength                23
    bDescriptorType        36
    bDescriptorSubtype      2 (FORMAT_TYPE)
    bFormatType             1 (FORMAT_TYPE_I)
    bNrChannels             1
    bSubframeSize           2
    bBitResolution         16
    bSamFreqType            5 Discrete
    tSamFreq[ 0]         8000
    tSamFreq[ 1]        11025
    tSamFreq[ 2]        22050
    tSamFreq[ 3]        44100
    tSamFreq[ 4]        48000

这是我的控制转移代码:

extern "C" void Java_com_example_test_LibUsb_nativeGetAudioInfo(JNIEnv *env, jobject obj){

libusb_init(NULL);
devh = libusb_open_device_with_vid_pid(NULL,VID,PID);
libusb_kernel_driver_active(devh, 0);
libusb_detach_kernel_driver(devh, 0);
libusb_claim_interface(devh, 0);
libusb_set_interface_alt_setting(devh,0,0);

uint8_t requestType = 0b1 | 0b01 | 0b00001;
uint8_t bRequest = 0x06;
uint16_t wValue = 0x24;
uint16_t wIndex = 0;
unsigned char data[23];
unsigned int timeout = 1000;

int rc = libusb_control_transfer(devh, requestType, bRequest, wValue, wIndex, data, sizeof(data), timeout);
LOGD("%d",rc);

int cnt = 0;
if(rc > 0){

    char bLength = data[cnt++];
    char bDescriptorType = data[cnt++];
    char bDescriptorSubtype = data[cnt++];
    char bFormatType = data[cnt++];
    char bNrChannels = data[cnt++];
    char bSubframeSize = data[cnt++];
    char bBitResolution = data[cnt++];
    char bSamFreqType = data[cnt++];

    int rates[bSamFreqType];

    LOGD("%d",bNrChannels);
    LOGD("%d",bBitResolution);

    for(int i = 0;i < bSamFreqType;i++){
        char byte1 = data[cnt++];
        char byte2 = data[cnt++];
        char byte3 = data[cnt++];

        rates[i] = ((byte1 & 0xFF) << 8 | (byte2 & 0xFF) << 16 | (byte3 & 0xFF) << 24);
        LOGD("%d",rates[i]);
    }

}

libusb_exit(NULL);

}

这是完整的设备描述符:

Device Descriptor:
bLength                18
bDescriptorType         1
bcdUSB               1.10
bDeviceClass            0 (Defined at Interface level)
bDeviceSubClass         0 
bDeviceProtocol         0 
bMaxPacketSize0         8
idVendor           0x17a0 Samson Technologies Corp.
idProduct          0x0002 Q1U dynamic microphone
bcdDevice            0.01
iManufacturer           1 
iProduct                2 
iSerial                 0 
bNumConfigurations      1
  Configuration Descriptor:
  bLength                 9
  bDescriptorType         2
  wTotalLength          177
  bNumInterfaces          2
  bConfigurationValue     1
  iConfiguration          0 
  bmAttributes         0x80
    (Bus Powered)
  MaxPower               90mA
  Interface Descriptor:
    bLength                 9
    bDescriptorType         4
    bInterfaceNumber        0
    bAlternateSetting       0
    bNumEndpoints           0
    bInterfaceClass         1 Audio
    bInterfaceSubClass      1 Control Device
    bInterfaceProtocol      0 
    iInterface              0 
    AudioControl Interface Descriptor:
      bLength                 9
      bDescriptorType        36
      bDescriptorSubtype      1 (HEADER)
      bcdADC               1.00
      wTotalLength           40
      bInCollection           1
      baInterfaceNr( 0)       1
    AudioControl Interface Descriptor:
      bLength                12
      bDescriptorType        36
      bDescriptorSubtype      2 (INPUT_TERMINAL)
      bTerminalID             1
      wTerminalType      0x0201 Microphone
      bAssocTerminal          2
      bNrChannels             2
      wChannelConfig     0x0003
        Left Front (L)
        Right Front (R)
      iChannelNames           0 
      iTerminal               0 
    AudioControl Interface Descriptor:
      bLength                 9
      bDescriptorType        36
      bDescriptorSubtype      3 (OUTPUT_TERMINAL)
      bTerminalID             2
      wTerminalType      0x0101 USB Streaming
      bAssocTerminal          1
      bSourceID               3
      iTerminal               0 
    AudioControl Interface Descriptor:
      bLength                10
      bDescriptorType        36
      bDescriptorSubtype      6 (FEATURE_UNIT)
      bUnitID                 3
      bSourceID               1
      bControlSize            1
      bmaControls( 0)      0x01
        Mute Control
      bmaControls( 1)      0x02
        Volume Control
      bmaControls( 2)      0x02
        Volume Control
      iFeature                0 
  Interface Descriptor:
    bLength                 9
    bDescriptorType         4
    bInterfaceNumber        1
    bAlternateSetting       0
    bNumEndpoints           0
    bInterfaceClass         1 Audio
    bInterfaceSubClass      2 Streaming
    bInterfaceProtocol      0 
    iInterface              0 
  Interface Descriptor:
    bLength                 9
    bDescriptorType         4
    bInterfaceNumber        1
    bAlternateSetting       1
    bNumEndpoints           1
    bInterfaceClass         1 Audio
    bInterfaceSubClass      2 Streaming
    bInterfaceProtocol      0 
    iInterface              0 
    AudioStreaming Interface Descriptor:
      bLength                 7
      bDescriptorType        36
      bDescriptorSubtype      1 (AS_GENERAL)
      bTerminalLink           2
      bDelay                  1 frames
      wFormatTag              1 PCM
    AudioStreaming Interface Descriptor:
      bLength                23
      bDescriptorType        36
      bDescriptorSubtype      2 (FORMAT_TYPE)
      bFormatType             1 (FORMAT_TYPE_I)
      bNrChannels             1
      bSubframeSize           2
      bBitResolution         16
      bSamFreqType            5 Discrete
      tSamFreq[ 0]         8000
      tSamFreq[ 1]        11025
      tSamFreq[ 2]        22050
      tSamFreq[ 3]        44100
      tSamFreq[ 4]        48000
    Endpoint Descriptor:
      bLength                 9
      bDescriptorType         5
      bEndpointAddress     0x81  EP 1 IN
      bmAttributes            5
        Transfer Type            Isochronous
        Synch Type               Asynchronous
        Usage Type               Data
      wMaxPacketSize     0x0064  1x 100 bytes
      bInterval               1
      bRefresh                0
      bSynchAddress           0
      AudioControl Endpoint Descriptor:
        bLength                 7
        bDescriptorType        37
        bDescriptorSubtype      1 (EP_GENERAL)
        bmAttributes         0x01
        Sampling Frequency
        bLockDelayUnits         0 Undefined
        wLockDelay              0 Undefined
  Interface Descriptor:
    bLength                 9
    bDescriptorType         4
    bInterfaceNumber        1
    bAlternateSetting       2
    bNumEndpoints           1
    bInterfaceClass         1 Audio
    bInterfaceSubClass      2 Streaming
    bInterfaceProtocol      0 
    iInterface              0 
    AudioStreaming Interface Descriptor:
      bLength                 7
      bDescriptorType        36
      bDescriptorSubtype      1 (AS_GENERAL)
      bTerminalLink           2
      bDelay                  1 frames
      wFormatTag              1 PCM
    AudioStreaming Interface Descriptor:
      bLength                23
      bDescriptorType        36
      bDescriptorSubtype      2 (FORMAT_TYPE)
      bFormatType             1 (FORMAT_TYPE_I)
      bNrChannels             2
      bSubframeSize           2
      bBitResolution         16
      bSamFreqType            5 Discrete
      tSamFreq[ 0]         8000
      tSamFreq[ 1]        11025
      tSamFreq[ 2]        22050
      tSamFreq[ 3]        44100
      tSamFreq[ 4]        48000
    Endpoint Descriptor:
      bLength                 9
      bDescriptorType         5
      bEndpointAddress     0x81  EP 1 IN
      bmAttributes            5
        Transfer Type            Isochronous
        Synch Type               Asynchronous
        Usage Type               Data
      wMaxPacketSize     0x00c8  1x 200 bytes
      bInterval               1
      bRefresh                0
      bSynchAddress           0
      AudioControl Endpoint Descriptor:
        bLength                 7
        bDescriptorType        37
        bDescriptorSubtype      1 (EP_GENERAL)
        bmAttributes         0x01
          Sampling Frequency
        bLockDelayUnits         0 Undefined
        wLockDelay              0 Undefined

1 回答

  • 0

    我也使用libusb库从Android上的USB麦克风录制 .

    我试图使用libusb接口来解析描述符,例如 libusb_get_config_descriptor() ,但不幸的是它没有用 .

    我的解决方案是自己做 . 在UsbDeviceConnection中使用USB documentation getRawDescriptors()方法:

    //parse audio interface descriptors of TYPE 1 FORMAT (PCM) - get all recording settings
    public static List<UsbAudioInfo>  ParseUsbRawDescriptor(byte[] rawDesc)
    {
        //list of settings my flat custom class
        List<UsbAudioInfo>  list = new ArrayList<>();
    
        final int INTERFACE = 4;
        final int AUDIO = 1;
        final int STREAMING = 2;
    
        //Timber.i("Descriptor length: " + rawDesc.length);
        int idVendor = ((rawDesc[9] & 0xff) << 8) | (rawDesc[8] & 0xff);
        int idProduct = ((rawDesc[11] & 0xff) << 8) | (rawDesc[10] & 0xff);
    
        int bLength = 0;
        for(int i = 0; i<rawDesc.length; i+=bLength) {
    
            bLength = rawDesc[i];
            int bDescriptorType  = rawDesc[i+1];
    
            if (bDescriptorType == INTERFACE)
            {
                int bInterfaceNumber = rawDesc[i+2];
                int bAlternateSetting = rawDesc[i+3];
                int bNumEndpoints = rawDesc[i+4];
                int bInterfaceClass = rawDesc[i+5];
                int bInterfaceSubClass =  rawDesc[i+6];
    
                //interested only in ADUIO  STREAMING interface with endpoints (support only PCM >> Type I Format Type Descriptor)
                if (bInterfaceClass == AUDIO && bInterfaceSubClass == STREAMING && bNumEndpoints>0)
                {
                    //AudioStreaming Interface Descriptor: (AS_GENERAL)
                    bLength += rawDesc[i+bLength];
    
                    //AudioStreaming Interface Descriptor: (FORMAT_TYPE)
                    int ftbLength = rawDesc[i+bLength];
    
                    //before we proceed check if IN endpoint (recording) => jump to endpoint desc
                    int bEndpointAddress =  rawDesc[i+bLength+ftbLength + 2];
                    int direction = bEndpointAddress & 0x80; // 10000000b; Bit 7
                    //only recording
                    if (direction == USB_DIR_IN)
                    {
                        int epaddress = bEndpointAddress & 0xff;
                        int epmaxpacket = ((rawDesc[i+bLength+ftbLength+5] & 0xff) << 8) | (rawDesc[i+bLength+ftbLength+4] & 0xff);
                        //PCM TYPE_1 descrtiptor
                        //http://www.usb.org/developers/docs/devclass_docs/frmts10.pdf
                        int bNrChannels = rawDesc[i+bLength + 4];
                        int bBitResolution = rawDesc[i+bLength + 6];
                        int bSamFreqType = rawDesc[i+bLength + 7];
    
                        int ratesind = i+bLength + 8;
    
                        for( int s = 0; s < bSamFreqType; s++)
                        {
                            //3 byte int:
                            byte b1 =  rawDesc[ratesind + s*3 + 0];
                            byte b2 =  rawDesc[ratesind + s*3 + 1];
                            byte b3 =  rawDesc[ratesind + s*3 + 2];
    
                            int rate = (b1 & 0xFF) | ((b2 & 0xFF) << 8) | ((b3 & 0x0F) << 16);
    
                            //store in my custom  object
                            UsbAudioInfo info = new UsbAudioInfo();
                            info.SAMPLING_RATE = rate;
                            info.ALTSET_NUM = bAlternateSetting;
                            info.CHANNELS = bNrChannels;
                            info.ENDPOINT_ADDRESS = epaddress;
                            info.ENDPOINT_MAXPCKSIZE = epmaxpacket;
                            info.FORMAT = bBitResolution;
                            info.INTERFACE_NUM = bInterfaceNumber;
                            info.VID = idVendor;
                            info.PID = idProduct;
    
                            list.add(info);
                        }
                    }
                }
            }
        }
    
        return list;
    }
    

相关问题