usb 音頻類描述符及其說明(usb audio descriptor)

寫在前面:

前兩天拿到一個產品,也就是一speakerphone;以前自己也參加過音頻類USB設備的研發,當然只是單獨的speaker或microphone,也曾經想過怎麼讓同一USB設備即作speaker輸出又作microphone輸入,只不過沒有具體去實現。當拿到這個speakerphone後就有一種去實現這樣一個USB設備的衝動,於是就有了這篇文章.......

 

先給出完整的usb描述符供參考:

const unsigned char Demo_DeviceDescriptor[] =
{
 //Device:USB1.10,Vid=0x0435,Pid=0x2430,bNumConfigurations = 0x01,
 0x12,       //Length
 0x01,    //DescriptorType
 0x10,0x01,  //bcdUSB
 0x00,     //DeviceClass
 0x00,      //DeviceSubClass
 0x00,      //DeviceProtocol
 0x08,    //bMaxPacketSize 8
 0x35,0x04,  //idVendor........
 0x30,0x24,  //idProduct........
 0x01,0x00, //bcdDevice
 1,      //iManufacturer
 2,        //iProduct
 3,          //iSerialNumber
 0x01        //bNumConfigurations
};

 

/* USB Configuration Descriptor */
/*   All Descriptors (Configuration, Interface, Endpoint, Class, Vendor */
const unsigned char Demo_ConfigDescriptor[] =
{
 //Configuration:wTotalLength = 0x00be,NumInterfaces = 0x03, 
 0x09,    //Length                           
 0x02,    //DescriptorType : ConfigDescriptor
 0xbe,0x00, //TotalLength:0x00be               
 0x03,      //NumInterfaces:3                 
 0x01,    //ConfigurationValue               
 0x00,    //Configuration String             
 0x80,    //Attributes:Bus Power             
 0xfa,     //MaxPower = 0xfa*2ma  

            

 //standard interface AC descriptor(Interface 0, Alternate Setting 0):
 //bNumEndpoints = 0x00,bInterFaceClass = 0x01(audio),bInterfaceSubClass = 0x01(audio ctl),
 0x09,    //Length                    
 0x04,     //DescriptorType:Inerface   
 0x00,     //InterfaceNum:0            
 0x00,       //AlternateSetting:0        
 0x00,       //NumEndpoint:0             
 0x01,       //InterfaceClass:audio      
 0x01,       //InterfaceSubClass:audio ctl
 0x00,       //InterfaceProtocol         
 0x00,      //Interface String       

   

 //class-specific AC interface descriptor,audio interface(0x24),audio control header(0x01),
 //Total Length 0x0048,Number of streaming interface 2,interfaceNr 2,1
 0x0a,    //Length                                                                                       
 0x24,      //DescriptorType:audio interface descriptor                                                    
 0x01,     //DescriptorSubType:audio control header                                                       
 0x00,0x01,  //bcdADC:audio Device Class v1.00                                                              
 0x48,0x00,  //TotalLength:0x0048                                                                           
 0x02,      //InCollection:2 AudioStreaming interface                                                      
 0x02,      //InterfaceNr(2) - AS #1 id AudioStreaming interface 2 belongs to this AudioControl interface  
 0x01,     //InterfaceNr(1) - AS #2 id AudioStreaming interface 1 belongs to this AudioControl interface  

 

 //USB Microphone IT:audio interface descriptor,audio control input terminal(0x02),terminal id 0x01,
 //Microphone(0x0201),Input Terminal(0x02),2 channel:Left Front,Right Front
 0x0c,    //Length                                                                                                   
 0x24,    //DescriptorType:audio interface descriptor                                                                
 0x02,     //DescriptorSubType:Input Terminal                                                                         
 0x01,     //TerminalID:0x01                                                                                          
 0x01,0x02,  //TerminalType:USB Microphone                                                                               
 0x00,      //AssocTerminal                                                                                            
 0x02,      //NrChannels:2 channel                                                                                            
 0x03,0x00,  //ChannelConfig:Left Front,Right Front, 
 0x00,       //ChannelName String                                                                                       
 0x00,       //Terminal String               

                                                                           

 //Audio Feature Unit Descriptor:audio interface descriptor,feature_unit(0x06),terminal id 0x02,
 //SourceId 0x01,ControlSize 0x01,Mute,Volume,                                          
 0x0a,    //Length                                  
 0x24,      //DescriptorType:audio interface descriptor
 0x06,      //DescriptorSubType:Audio Feature Unit    
 0x02,       //UnitID:0x02                             
 0x01,      //SourceID:1 #Microphone IT               
 0x01,      //ControlSize:1 byte                      
 0x01,     //Controls:Mute                          
 0x02,      //Controls(0):Volume                      
 0x02,       //Controls(1):Volume                      
 0x00,       //Feature String            

              

 //USB Streaming OT:audio interface descriptor,audio control output terminal(0x03),terminal id 0x03,
 //USB Streaming(0x0101),Output Terminal(0x03),SourceId 0x02,     
 0x09,    //Length                                    
 0x24,       //DescriptorType:audio interface descriptor 
 0x03,      //DescriptorSubTYpe:Output Terminal         
 0x03,      //TerminalID:0x03                          
 0x01,0x01,  //TerminalType:USB Streaming                
 0x00,       //AssocTerminal:ID 0                        
 0x02,      //SourceID:2 #Feature UNIT                          
 0x00,       //Terminal String          

                 

 //USB USB Streaming IT:audio interface descriptor,audio control input terminal(0x02),terminal id 0x04,
 //USB Streaming(0x0101),Input Terminal(0x02),2 channel:Left Front,Right Front
 0x0c,       //Length                                   
 0x24,       //DescriptorType:audio interface descriptor
 0x02,       //DescriptorSubType:Input Terminal         
 0x04,       //TerminalID:0x04                          
 0x01,0x01,  //TerminalType:USB Streaming              
 0x00,       //AssocTerminal                            
 0x02,       //NrChannels:2 channel                             
 0x03,0x00,  //ChannelConfig:Left Front,Right Front,    
 0x00,       //ChannelName String                       
 0x00,       //Terminal String                          


 //Audio Feature Unit Descriptor:audio interface descriptor,feature_unit(0x06),terminal id 0x05,
 //SourceId 0x04,ControlSize 0x01,Mute,Volume, 
 0x0a,    //Length                                  
 0x24,      //DescriptorType:audio interface descriptor
 0x06,       //DescriptorSubType:Audio Feature Unit    
 0x05,       //UnitID:0x05                            
 0x04,      //SourceID:4 #USB Streaming IT               
 0x01,      //ControlSize:1 byte                      
 0x01,      //Controls:Mute,                    
 0x02,       //Controls(0):Volume                            
 0x02,      //Controls(1):Volume                            
 0x00,       //Feature String              

            

 //USB Speaker OT:audio interface descriptor,audio control output terminal(0x03),terminal id 0x06,
 //USB Speaker(0x0301),Output Terminal(0x03),SourceId 0x05,
 0x09,      //Length                                   
 0x24,      //DescriptorType:audio interface descriptor
 0x03,      //DescriptorSubTYpe:Output Terminal        
 0x06,      //TerminalID:0x06                          
 0x01,0x03,  //TerminalType:Speaker               
 0x00,       //AssocTerminal:                      
 0x05,      //SourceID:5 #Feature UNIT                   
 0x00,      //Terminal String
                       
 //-------------------Microphone  interface---------------------//
 //standard interface AS descriptor(Interface 1, Alternate Setting 0):
 //bNumEndpoints = 0x00,bInterFaceClass = 0x01(audio),bInterfaceSubClass = 0x02(audio stream),                 
 0x09,    //Length                          
 0x04,       //DescriptorType:Interface        
 0x01,      //InterfaceNum:1                  
 0x00,      //AlternateSetting:0              
 0x00,       //NumEndpoint:0                   
 0x01,      //InterfaceClass:audio            
 0x02,      //InterfaceSubClass:audio streaming
 0x00,       //InterfaceProtocol               
 0x00,       //Interface String            

    

 //standard interface AS descriptor(Interface 1, Alternate Setting 1):                        
 //bNumEndpoints = 0x01,bInterFaceClass = 0x01(audio),bInterfaceSubClass = 0x02(audio stream),
 0x09,    //Length                          
 0x04,      //DescriptorType:Interface        
 0x01,      //InterfaceNum:1                  
 0x01,      //AlternateSetting:1              
 0x01,       //NumEndpoint:1                   
 0x01,      //InterfaceClass:audio            
 0x02,       //InterfaceSubClass:audio streaming
 0x00,      //InterfaceProtocol               
 0x00,       //Interface String        

        

 //Audio Streaming Interface Descriptor:AS_GENERAL(0x01),
 //TerminalLink 0x03,PCM(0x0001)
 0x07,    //Length                                     
 0x24,       //DescriptorType:audio interface descriptor  
 0x01,      //DescriptorSubType:AS_GENERAL               
 0x03,       //TerminalLink:#3USB USB Streaming OT          
 0x01,       //Delay:1                                    
 0x01,0x00,  //FormatTag:PCM        

                      

 //Type 1 Format type descriptor:FORMAT_TYPE(0x02),FORMAT_TYPE_I(0x01),
 //physical channels 0x02,two byte per audio subframe(0x02),16bit,
 //32K(0x007d00)
 0x0b,    //Length                                  
 0x24,      //DescriptorType:audio interface descriptor
 0x02,      //DescriptorSubType:Format_type           
 0x01,       //FormatType:Format type 1                
 0x02,      //NumberOfChanne:2                        
 0x02,       //SubframeSize:2byte                      
 0x10,      //BitsResolution:16bit                    
 0x01,       //SampleFreqType:One sampling frequency.   
 0x00,0x7d,0x00,   //32K(0x007d00)                     

    

 //Endpoint 1 - Standard Descriptor:Input Endpoint1                  
 //Isochronous,Synchronization Type(Asynchronous),MaxPacketSize 0x0084,
 0x07,     //Length                                                            
 0x05,      //DescriptorType:endpoint descriptor                                
 0x81,       //EndpointAddress:Input endpoint 1                                 
 0x05,       //Attributes:0x05,Isochronous,Synchronization Type(Asynchronous).........
 0x84,0x00,  //MaxPacketSize:0x0084=........                                       
 0x01,      //Interval                                        

                  

 //Endpoint - Audio Streaming Descriptor:
 //Audio Endpoint descriptor,General, 
 0x07,    //Length                                   
 0x25,      //DescriptorType:audio endpoint descriptor 
 0x01,      //DescriptorSubType:audio endpiont general 
 0x00,       //Attributes:0x00........             
 0x00,      //LockDelayUnits                           
 0x00,0x00,  //LockDelay                 

               

 //-------------------Speaker  interface---------------------//
 //standard interface AS descriptor(Interface 2, Alternate Setting 0):
 //bNumEndpoints = 0x00,bInterFaceClass = 0x01(audio),bInterfaceSubClass = 0x02(audio stream),
 0x09,      //Length                          
 0x04,      //DescriptorType:Interface        
 0x02,       //InterfaceNum:2                  
 0x00,       //AlternateSetting:0              
 0x00,      //NumEndpoint:0                   
 0x01,       //InterfaceClass:audio            
 0x02,      //InterfaceSubClass:audio streaming
 0x00,      //InterfaceProtocol               
 0x00,       //Interface String                

 

 //standard interface AS descriptor(Interface 2, Alternate Setting 1):                       
 //bNumEndpoints = 0x01,bInterFaceClass = 0x01(audio),bInterfaceSubClass = 0x02(audio stream),
 0x09,      //Length                          
 0x04,      //DescriptorType:Interface        
 0x02,       //InterfaceNum:2                  
 0x01,       //AlternateSetting:1              
 0x01,       //NumEndpoint:1                   
 0x01,      //InterfaceClass:audio            
 0x02,       //InterfaceSubClass:audio streaming
 0x00,       //InterfaceProtocol               
 0x00,      //Interface String                

 

 //Audio Streaming Interface Descriptor:AS_GENERAL(0x01),
 //TerminalLink 0x04,PCM(0x0001)
 0x07,      //Length                                  
 0x24,       //DescriptorType:audio interface descriptor
 0x01,       //DescriptorSubType:AS_GENERAL            
 0x04,      //TerminalLink:#4 USB Streaming IT    
 0x01,      //Delay:1                                 
 0x01,0x00,  //FormatTag:PCM     

                      

 //Type 1 Format type descriptor:FORMAT_TYPE(0x02),FORMAT_TYPE_I(0x01),
 //physical channels 0x02,two byte per audio subframe(0x02),16bit,
 //32K(0x007d00)
 0x0b,     //Length                                  
 0x24,       //DescriptorType:audio interface descriptor
 0x02,      //DescriptorSubType:Format_type           
 0x01,       //FormatType:Format type 1                
 0x02,       //NumberOfChanne:2                        
 0x02,       //SubframeSize:2byte                      
 0x10,      //BitsResolution:16bit                    
 0x01,      //SampleFreqType:One sampling frequency.  
 0x00,0x7d,0x00,   //32K(0x007d00)         

                  

 //Endpoint 2 - Standard Descriptor:Output Endpoint2                  
 //Isochronous,Synchronization Type(Asynchronous),MaxPacketSize 0x0084,
 0x07,      //Length                                                               
 0x05,       //DescriptorType:endpoint descriptor                                   
 0x02,       //EndpointAddress:Output endpoint 2                                     
 0x05,      //Attributes:0x05,Isochronous,Synchronization Type(Asynchronous).........
 0x84,0x00,  //MaxPacketSize:0x0084=.....                                           
 0x01,      //Interval                               

                              

 //Endpoint - Audio Streaming Descriptor:
 //Audio Endpoint descriptor,General, 
 0x07,       //Length                                    
 0x25,       //DescriptorType:audio endpoint descriptor  
 0x01,       //DescriptorSubType:audio endpiont general  
 0x00,      //Attributes:0x00.............              
 0x00,       //LockDelayUnits                            
 0x00,0x00,  //LockDelay                            
};

 

/* USB String Descriptor (optional) */
const unsigned char Demo_StringLangID[] =
  {
 0x04,
 0x03,
 0x09,
 0x04
  };


 const unsigned char Demo_StringVendor[] =
  {
    0x26, //Length
    0x03, //DescriptorType
    'D', 0, 'e', 0, 'm', 0, 'o', 0, '-', 0, 's', 0, 'p', 0, 'e', 0,
    'r', 0, 'k', 0, 'e', 0, 'r', 0, 'p', 0, 'h', 0, 'o', 0, 'n', 0,
    'e', 0, '1', 0
  };

 

const unsigned char Demo_StringProduct[] =
  {
    0x1c,  //Length
    0x03,  //DescriptorType
    'S', 0, 'p', 0, 'e', 0, 'a', 0, 'k', 0, 'e', 0,
    'r', 0, 'p', 0, 'h', 0, 'o', 0, 'n', 0, 'e', 0, '2', 0
  };


const unsigned char Demo_StringSerial[] =
  {
    0x1c,  //Length
    0x03,  //DescriptorType
    'S', 0, 'p', 0, 'e', 0, 'a', 0, 'k', 0, 'e', 0,
    'r', 0, 'p', 0, 'h', 0, 'o', 0, 'n', 0, 'e', 0, '2', 0
  };

 

相關說明:

這裏就不針對整個描述符去作具體的分析,其實註釋已經寫的很詳細了。這裏只是對一些細節性的進行說明

 

1.根據USB描述符可以得到其拓撲圖:

 speakerphone拓撲圖

 

2.描述符的分層組織結構

 speakerphone描述符層次結構

 

3.設備描述符裏採用的Vendor和Product ID號是隨便寫的一個用於測試。

 

4.設備描述符下包含一個配置描述符,配置描述符下包含了3組接口,IF0作爲音頻控制接口,IF1作爲microphone接口,IF2作爲speaker接口。

 

5.在IF0的定義中沒有包含任何端點,所以與音頻相關的控制信息將通過默認的控制端點0來進行信息的交付。也就是說端點0除了響應默認的控制事務(Set interfance等等)以外還需要響應音頻類相關控制事務(set cur,get max等等),音量調節就是通過控制端點0來完成的。

 

6.IF0中的Feature Unit定義了音量調節方式,mute和Volume,其中ID號爲2的Unit控制microphone,ID 5控制speaker。具體關係常見其拓撲圖。

 

7.IF0中兩個IT(Input Terminal)定義了音頻流邏輯通道數及其具體組成形式,在該示例中包含了2個邏輯通道,分別是LEFT&RIGHT,如果需要更多的通道可以通過修改相應描述符單元得到(同時注意修改相應的Streaming描述符中物理通道數,相應USB endpoint支持的包字節大小)。

 

8. IF1和IF2中都定義了2個setting,其中setting 0都不包含傳輸endpoint,setting 1都包含一個同步傳輸endpoint。這裏要說明的是之所以都要定義一個不含有任何傳輸endpoint(除了默認端點0)的setting,是由usb audio設備特性決定的,該setting不可省略,該setting用於在設備沒有被使用時作爲usb設備的設置。如果沒有利用該usb設備進行放音,和錄音則主機使用的接口是IF(1,0)(接口1的設置0)和IF(2,0)(接口2的設置0),如果開始放音則使用的接口是IF(1,0)和IF(2,1),如果即用於放音又用於錄音則使用IF(1,1)和IF(2,1)。這裏敘述的有些累贅,其實大家可以利用USB協議相關分析軟件得到其具體交互過程。

 

9.在IF1和IF2中定義了音頻流格式爲PCM格式(更多關於格式的信息參考USB audio相關文檔)。支持一個採樣頻點:32K,如果需要更多的採樣頻點的支持,可以通過修改相應字段得到(注意修改相應同步端點支持的包大小)。

 

10.IF1(microphone)定義了endpoint 1 作爲其同步傳輸輸入端點。端點支持的最大傳輸字節爲0x84(132byte),這裏的0x44是由 32*2*2=128=0x80(採樣率*通道數*每個樣點的字節數)得到的(0x80byte/ms),之所以會多出4字節是因爲在之前的應用中如果支持44.1K時的一個考慮,當然這裏可以將其定義爲0x80。

 

11.在IF1和IF2的AS endpoint Descriptor中的字段attributes可以用來定義是否支持採樣率相關事務處理。也就是說如果在同一個IF的同一setting中支持多個採樣率,那麼在進行同步傳輸前,主機可以發起一個告知設備即將使用的採樣率的事務處理,而這裏的attributes用來定義設備是否支持這類事務處理。

 

12.支持多個採樣率不僅可以通過在第9點所敘述的方式來實現(同一setting下支持多個採樣率),也可以通過增加新的setting來支持(每個setting支持一個單獨的採樣率)。兩種方式各有優缺點,第一種方式比較簡潔不過需要由主機告知設備即將使用的採樣率。第二種方式會較大幅度的增加整個描述符長度,但是不需要主機告知設備使用的採樣率。也就是說在第一種方式下主機先告訴即將使用的接口setting,然後再發起一個採樣率的SET CUR事務處理。而第二種方式只需要告訴即將使用的接口就可以了(因爲一個setting只支持一個採樣率,不同採樣率將採用不同setting)。

 

13.同步問題,因爲usb傳輸都是主機發起的,而設備只是被動的響應來進行數據傳輸。對於同步傳輸,usb在每一個 frame中啓動一次同步傳輸,該同步傳輸的啓動是基於主機USB主控制器所使用的時鐘來進行的,而設備得到數據是依據自己的時鐘源,所以這裏就存在兩個時鐘源差異的問題。我採用的方式是利用設備響應主機的SOF中斷來調整自身時鐘來與主機同步。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章