/*++
Copyright (c) 1997-1998 Microsoft Corporation
Module Name:
DISPAUD.C
Abstract:
This source file contains routines which update the edit control
to display information about USB Audio descriptors.
Environment:
user mode
Revision History:
03-07-1998 : created
--*/
//*****************************************************************************
// I N C L U D E S
//*****************************************************************************
#include <windows.h>
#include <basetyps.h>
#include "usbview.h"
//*****************************************************************************
// D E F I N E S
//*****************************************************************************
//*****************************************************************************
// T Y P E D E F S
//*****************************************************************************
typedef struct _TERMTYPE
{
USHORT TermTypeCode;
PCHAR TermTypeName;
} TERMTYPE, *PTERMTYPE;
typedef struct _FORMATTYPE
{
USHORT FormatTypeCode;
PCHAR FormatTypeName;
} FORMATTYPE, *PFORMATTYPE;
//*****************************************************************************
// G L O B A L S P R I V A T E T O T H I S F I L E
//*****************************************************************************
//
// USB Device Class Definition for Terminal Types 0.9 Draft Revision
//
TERMTYPE TermTypes[] =
{
//
// 2.1 USB Terminal Types
//
{0x0100, "USB Undefined"},
{0x0101, "USB streaming"},
{0x01FF, "USB vendor specific"},
//
// 2.2 Input Terminal Types
//
{0x0200, "Input Undefined"},
{0x0201, "Microphone"},
{0x0202, "Desktop microphone"},
{0x0203, "Personal microphone"},
{0x0204, "Omni-directional microphone"},
{0x0205, "Microphone array"},
{0x0206, "Processing microphone array"},
//
// 2.3 Output Terminal Types
//
{0x0300, "Output Undefined"},
{0x0301, "Speaker"},
{0x0302, "Headphones"},
{0x0303, "Head Mounted Display Audio"},
{0x0304, "Desktop speaker"},
{0x0305, "Room speaker"},
{0x0306, "Communication speaker"},
{0x0307, "Low frequency effects speaker"},
//
// 2.4 Bi-directional Terminal Types
//
{0x0400, "Bi-directional Undefined"},
{0x0401, "Handset"},
{0x0402, "Headset"},
{0x0403, "Speakerphone, no echo reduction"},
{0x0404, "Echo-suppressing speakerphone"},
{0x0405, "Echo-canceling speakerphone"},
//
// 2.5 Telephony Terminal Types
//
{0x0500, "Telephony Undefined"},
{0x0501, "Phone line"},
{0x0502, "Telephone"},
{0x0503, "Down Line Phone"},
//
// 2.6 External Terminal Types
//
{0x0600, "External Undefined"},
{0x0601, "Analog connector"},
{0x0602, "Digital audio interface"},
{0x0603, "Line connector"},
{0x0604, "Legacy audio connector"},
{0x0605, "S/PDIF interface"},
{0x0606, "1394 DA stream"},
{0x0607, "1394 DV stream soundtrack"},
//
// Embedded Function Terminal Types
//
{0x0700, "Embedded Undefined"},
{0x0701, "Level Calibration Noise Source"},
{0x0702, "Equalization Noise"},
{0x0703, "CD player"},
{0x0704, "DAT"},
{0x0705, "DCC"},
{0x0706, "MiniDisk"},
{0x0707, "Analog Tape"},
{0x0708, "Phonograph"},
{0x0709, "VCR Audio"},
{0x070A, "Video Disc Audio"},
{0x070B, "DVD Audio"},
{0x070C, "TV Tuner Audio"},
{0x070D, "Satellite Receiver Audio"},
{0x070E, "Cable Tuner Audio"},
{0x070F, "DSS Audio"},
{0x0710, "Radio Receiver"},
{0x0711, "Radio Transmitter"},
{0x0712, "Multi-track Recorder"},
{0x0713, "Synthesizer"},
//
// Terminate List
//
{0xFFFF, NULL}
};
//
// USB Device Class Definition for Audio Data Formats 0.9 Draft Revision
//
FORMATTYPE FormatTypes[] =
{
//
// A.1.1 Audio Data Format Type I Codes
//
{0x0000, "TYPE_I_UNDEFINED"},
{0x0001, "PCM"},
{0x0002, "PCM8"},
{0x0003, "IEEE_FLOAT"},
{0x0004, "ALAW"},
{0x0005, "MULAW"},
//
// A.1.2 Audio Data Format Type II Codes
//
{0x1000, "TYPE_II_UNDEFINED"},
{0x1001, "MPEG"},
{0x1002, "AC-3"},
//
// A.1.3 Audio Data Format Type III Codes
//
{0x2000, "TYPE_III_UNDEFINED"},
{0x2001, "IEC1937_AC-3"},
{0x2002, "IEC1937_MPEG-1_Layer1"},
{0x2003, "IEC1937_MPEG-1_Layer2/3 or IEC1937_MPEG-2_NOEXT"},
{0x2004, "IEC1937_MPEG-2_EXT"},
{0x2005, "IEC1937_MPEG-2_Layer1_LS"},
{0x2006, "IEC1937_MPEG-2_Layer2/3_LS"},
//
// Terminate List
//
{0xFFFF, NULL}
};
//*****************************************************************************
// L O C A L F U N C T I O N P R O T O T Y P E S
//*****************************************************************************
BOOL
DisplayACHeader (
PUSB_AUDIO_AC_INTERFACE_HEADER_DESCRIPTOR HeaderDesc
);
BOOL
DisplayACInputTerminal (
PUSB_AUDIO_INPUT_TERMINAL_DESCRIPTOR ITDesc
);
BOOL
DisplayACOutputTerminal (
PUSB_AUDIO_OUTPUT_TERMINAL_DESCRIPTOR OTDesc
);
BOOL
DisplayACMixerUnit (
PUSB_AUDIO_MIXER_UNIT_DESCRIPTOR MixerDesc
);
BOOL
DisplayACSelectorUnit (
PUSB_AUDIO_SELECTOR_UNIT_DESCRIPTOR SelectorDesc
);
BOOL
DisplayACFeatureUnit (
PUSB_AUDIO_FEATURE_UNIT_DESCRIPTOR FeatureDesc
);
BOOL
DisplayACProcessingUnit (
PUSB_AUDIO_PROCESSING_UNIT_DESCRIPTOR ProcessingDesc
);
BOOL
DisplayACExtensionUnit (
PUSB_AUDIO_EXTENSION_UNIT_DESCRIPTOR ExtensionDesc
);
BOOL
DisplayASGeneral (
PUSB_AUDIO_GENERAL_DESCRIPTOR GeneralDesc
);
BOOL
DisplayCSEndpoint (
PUSB_AUDIO_ENDPOINT_DESCRIPTOR EndpointDesc
);
BOOL
DisplayASFormatType (
PUSB_AUDIO_COMMON_FORMAT_DESCRIPTOR FormatDesc
);
BOOL
DisplayASFormatSpecific (
PUSB_AUDIO_COMMON_DESCRIPTOR CommonDesc
);
VOID
DisplayBytes (
PUCHAR Data,
USHORT Len
);
PCHAR
TermTypeCodeToName (
USHORT TermTypeCode
);
PCHAR
FormatTypeCodeToName (
USHORT FormatTypeCode
);
//*****************************************************************************
// L O C A L F U N C T I O N S
//*****************************************************************************
//*****************************************************************************
//
// DisplayAudioDescriptor()
//
// CommonDesc - An Audio Class Descriptor
//
// bInterfaceSubClass - The SubClass of the Interface containing the descriptor
//
//*****************************************************************************
BOOL
DisplayAudioDescriptor (
PUSB_AUDIO_COMMON_DESCRIPTOR CommonDesc,
UCHAR bInterfaceSubClass
)
{
switch (CommonDesc->bDescriptorType)
{
case USB_AUDIO_CS_INTERFACE:
switch (bInterfaceSubClass)
{
case USB_AUDIO_SUBCLASS_AUDIOCONTROL:
switch (CommonDesc->bDescriptorSubtype)
{
case USB_AUDIO_AC_HEADER:
return DisplayACHeader((PUSB_AUDIO_AC_INTERFACE_HEADER_DESCRIPTOR)CommonDesc);
case USB_AUDIO_AC_INPUT_TERMINAL:
return DisplayACInputTerminal((PUSB_AUDIO_INPUT_TERMINAL_DESCRIPTOR)CommonDesc);
case USB_AUDIO_AC_OUTPUT_TERMINAL:
return DisplayACOutputTerminal((PUSB_AUDIO_OUTPUT_TERMINAL_DESCRIPTOR)CommonDesc);
case USB_AUDIO_AC_MIXER_UNIT:
return DisplayACMixerUnit((PUSB_AUDIO_MIXER_UNIT_DESCRIPTOR)CommonDesc);
case USB_AUDIO_AC_SELECTOR_UNIT:
return DisplayACSelectorUnit((PUSB_AUDIO_SELECTOR_UNIT_DESCRIPTOR)CommonDesc);
case USB_AUDIO_AC_FEATURE_UNIT:
return DisplayACFeatureUnit((PUSB_AUDIO_FEATURE_UNIT_DESCRIPTOR)CommonDesc);
case USB_AUDIO_AC_PROCESSING_UNIT:
return DisplayACProcessingUnit((PUSB_AUDIO_PROCESSING_UNIT_DESCRIPTOR)CommonDesc);
case USB_AUDIO_AC_EXTENSION_UNIT:
return DisplayACExtensionUnit((PUSB_AUDIO_EXTENSION_UNIT_DESCRIPTOR)CommonDesc);
default:
break;
}
break;
case USB_AUDIO_SUBCLASS_AUDIOSTREAMING:
switch (CommonDesc->bDescriptorSubtype)
{
case USB_AUDIO_AS_GENERAL:
return DisplayASGeneral((PUSB_AUDIO_GENERAL_DESCRIPTOR)CommonDesc);
case USB_AUDIO_AS_FORMAT_TYPE:
return DisplayASFormatType((PUSB_AUDIO_COMMON_FORMAT_DESCRIPTOR)CommonDesc);
break;
case USB_AUDIO_AS_FORMAT_SPECIFIC:
return DisplayASFormatSpecific(CommonDesc);
default:
break;
}
break;
default:
break;
}
break;
case USB_AUDIO_CS_ENDPOINT:
return DisplayCSEndpoint((PUSB_AUDIO_ENDPOINT_DESCRIPTOR)CommonDesc);
default:
break;
}
return FALSE;
}
//*****************************************************************************
//
// DisplayACHeader()
//
//*****************************************************************************
BOOL
DisplayACHeader (
PUSB_AUDIO_AC_INTERFACE_HEADER_DESCRIPTOR HeaderDesc
)
{
UINT i;
if (HeaderDesc->bLength < sizeof(USB_AUDIO_AC_INTERFACE_HEADER_DESCRIPTOR))
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Control Interface Header Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n", HeaderDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n", HeaderDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n", HeaderDesc->bDescriptorSubtype);
AppendTextBuffer("bcdADC: 0x%04X\r\n", HeaderDesc->bcdADC);
AppendTextBuffer("wTotalLength: 0x%04X\r\n", HeaderDesc->wTotalLength);
AppendTextBuffer("bInCollection: 0x%02X\r\n", HeaderDesc->bInCollection);
for (i=0; i<HeaderDesc->bInCollection; i++) {
AppendTextBuffer("baInterfaceNr[%d]: 0x%02X\r\n", i+1, HeaderDesc->baInterfaceNr[i]);
}
return TRUE;
}
//*****************************************************************************
//
// DisplayACInputTerminal()
//
//*****************************************************************************
BOOL
DisplayACInputTerminal (
PUSB_AUDIO_INPUT_TERMINAL_DESCRIPTOR ITDesc
)
{
PCHAR pStr;
if (ITDesc->bLength != sizeof(USB_AUDIO_INPUT_TERMINAL_DESCRIPTOR))
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Control Input Terminal Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n", ITDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n", ITDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n", ITDesc->bDescriptorSubtype);
AppendTextBuffer("bTerminalID: 0x%02X\r\n", ITDesc->bTerminalID);
AppendTextBuffer("wTerminalType: 0x%04X", ITDesc->wTerminalType);
pStr = TermTypeCodeToName(ITDesc->wTerminalType);
if (pStr) {
AppendTextBuffer(" (%s)\r\n",pStr);
}else{
AppendTextBuffer("\r\n");
}
AppendTextBuffer("bAssocTerminal: 0x%02X\r\n", ITDesc->bAssocTerminal);
AppendTextBuffer("bNrChannels: 0x%02X\r\n", ITDesc->bNrChannels);
AppendTextBuffer("wChannelConfig: 0x%04X\r\n", ITDesc->wChannelConfig);
AppendTextBuffer("iChannelNames: 0x%02X\r\n", ITDesc->iChannelNames);
AppendTextBuffer("iTerminal: 0x%02X\r\n", ITDesc->iTerminal);
return TRUE;
}
//*****************************************************************************
//
// DisplayACOutputTerminal()
//
//*****************************************************************************
BOOL
DisplayACOutputTerminal (
PUSB_AUDIO_OUTPUT_TERMINAL_DESCRIPTOR OTDesc
)
{
PCHAR pStr;
if (OTDesc->bLength != sizeof(USB_AUDIO_OUTPUT_TERMINAL_DESCRIPTOR))
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Control Output Terminal Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
OTDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
OTDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
OTDesc->bDescriptorSubtype);
AppendTextBuffer("bTerminalID: 0x%02X\r\n",
OTDesc->bTerminalID);
AppendTextBuffer("wTerminalType: 0x%04X",
OTDesc->wTerminalType);
pStr = TermTypeCodeToName(OTDesc->wTerminalType);
if (pStr)
{
AppendTextBuffer(" (%s)\r\n",
pStr);
}
else
{
AppendTextBuffer("\r\n");
}
AppendTextBuffer("bAssocTerminal: 0x%02X\r\n",
OTDesc->bAssocTerminal);
AppendTextBuffer("bSoruceID: 0x%02X\r\n",
OTDesc->bSoruceID);
AppendTextBuffer("iTerminal: 0x%02X\r\n",
OTDesc->iTerminal);
return TRUE;
}
//*****************************************************************************
//
// DisplayACMixerUnit()
//
//*****************************************************************************
BOOL
DisplayACMixerUnit (
PUSB_AUDIO_MIXER_UNIT_DESCRIPTOR MixerDesc
)
{
UCHAR i;
PUCHAR data;
if (MixerDesc->bLength < 10)
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Control Mixer Unit Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
MixerDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
MixerDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
MixerDesc->bDescriptorSubtype);
AppendTextBuffer("bUnitID: 0x%02X\r\n",
MixerDesc->bUnitID);
AppendTextBuffer("bNrInPins: 0x%02X\r\n",
MixerDesc->bNrInPins);
for (i=0; i<MixerDesc->bNrInPins; i++)
{
AppendTextBuffer("baSourceID[%d]: 0x%02X\r\n",
i+1,
MixerDesc->baSourceID[i]);
}
data = &MixerDesc->baSourceID[MixerDesc->bNrInPins];
AppendTextBuffer("bNrChannels: 0x%02X\r\n",
*data++);
AppendTextBuffer("wChannelConfig: 0x%04X\r\n",
*((PUSHORT)data)++);
AppendTextBuffer("iChannelNames: 0x%02X\r\n",
*data++);
AppendTextBuffer("bmControls:\r\n");
i = MixerDesc->bLength - 10 - MixerDesc->bNrInPins;
DisplayBytes(data, i);
data += i;
AppendTextBuffer("iMixer: 0x%02X\r\n",
*data);
return TRUE;
}
//*****************************************************************************
//
// DisplayACSelectorUnit()
//
//*****************************************************************************
BOOL
DisplayACSelectorUnit (
PUSB_AUDIO_SELECTOR_UNIT_DESCRIPTOR SelectorDesc
)
{
UCHAR i;
PUCHAR data;
if (SelectorDesc->bLength < 6)
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Control Selector Unit Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
SelectorDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
SelectorDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
SelectorDesc->bDescriptorSubtype);
AppendTextBuffer("bUnitID: 0x%02X\r\n",
SelectorDesc->bUnitID);
AppendTextBuffer("bNrInPins: 0x%02X\r\n",
SelectorDesc->bNrInPins);
for (i=0; i<SelectorDesc->bNrInPins; i++)
{
AppendTextBuffer("baSourceID[%d]: 0x%02X\r\n",
i+1,
SelectorDesc->baSourceID[i]);
}
data = &SelectorDesc->baSourceID[SelectorDesc->bNrInPins];
AppendTextBuffer("iSelector: 0x%02X\r\n",
*data);
return TRUE;
}
//*****************************************************************************
//
// DisplayACFeatureUnit()
//
//*****************************************************************************
BOOL
DisplayACFeatureUnit (
PUSB_AUDIO_FEATURE_UNIT_DESCRIPTOR FeatureDesc
)
{
UCHAR i, n, ch;
PUCHAR data;
if (FeatureDesc->bLength < 7)
{
OOPS();
return FALSE;
}
n = FeatureDesc->bControlSize;
ch = ((FeatureDesc->bLength - 7) / n) - 1;
if (FeatureDesc->bLength != (7 + (ch + 1) * n))
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Control Feature Unit Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
FeatureDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
FeatureDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
FeatureDesc->bDescriptorSubtype);
AppendTextBuffer("bUnitID: 0x%02X\r\n",
FeatureDesc->bUnitID);
AppendTextBuffer("bSourceID: 0x%02X\r\n",
FeatureDesc->bSourceID);
AppendTextBuffer("bControlSize: 0x%02X\r\n",
FeatureDesc->bControlSize);
data = &FeatureDesc->bmaControls[0];
for (i=0; i<=ch; i++)
{
AppendTextBuffer("bmaControls[%d]:\r\n",
i);
DisplayBytes(data, n);
data += n;
}
AppendTextBuffer("iFeature: 0x%02X\r\n",
*data);
return TRUE;
}
//*****************************************************************************
//
// DisplayACProcessingUnit()
//
//*****************************************************************************
BOOL
DisplayACProcessingUnit (
PUSB_AUDIO_PROCESSING_UNIT_DESCRIPTOR ProcessingDesc
)
{
UCHAR i;
PUCHAR data;
if (ProcessingDesc->bLength < sizeof(USB_AUDIO_PROCESSING_UNIT_DESCRIPTOR))
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Control Processing Unit Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
ProcessingDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
ProcessingDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
ProcessingDesc->bDescriptorSubtype);
AppendTextBuffer("bUnitID: 0x%02X\r\n",
ProcessingDesc->bUnitID);
AppendTextBuffer("wProcessType: 0x%04X",
ProcessingDesc->wProcessType);
switch (ProcessingDesc->wProcessType)
{
case USB_AUDIO_PROCESS_UNDEFINED:
AppendTextBuffer("(Undefined Process)\r\n");
break;
case USB_AUDIO_PROCESS_UPDOWNMIX:
AppendTextBuffer("(Up / Down Mix Process)\r\n");
break;
case USB_AUDIO_PROCESS_DOLBYPROLOGIC:
AppendTextBuffer("(Dolby Prologic Process)\r\n");
break;
case USB_AUDIO_PROCESS_3DSTEREOEXTENDER:
AppendTextBuffer("(3D-Stereo Extender Process)\r\n");
break;
case USB_AUDIO_PROCESS_REVERBERATION:
AppendTextBuffer("(Reverberation Process)\r\n");
break;
case USB_AUDIO_PROCESS_CHORUS:
AppendTextBuffer("(Chorus Process)\r\n");
break;
case USB_AUDIO_PROCESS_DYNRANGECOMP:
AppendTextBuffer("(Dynamic Range Compressor Process)\r\n");
break;
default:
AppendTextBuffer("\r\n");
break;
}
AppendTextBuffer("bNrInPins: 0x%02X\r\n",
ProcessingDesc->bNrInPins);
for (i=0; i<ProcessingDesc->bNrInPins; i++)
{
AppendTextBuffer("baSourceID[%d]: 0x%02X\r\n",
i+1,
ProcessingDesc->baSourceID[i]);
}
data = &ProcessingDesc->baSourceID[ProcessingDesc->bNrInPins];
AppendTextBuffer("bNrChannels: 0x%02X\r\n",
*data++);
AppendTextBuffer("wChannelConfig: 0x%04X\r\n",
*((PUSHORT)data)++);
AppendTextBuffer("iChannelNames: 0x%02X\r\n",
*data++);
i = *data++;
AppendTextBuffer("bControlSize: 0x%02X\r\n",
i);
AppendTextBuffer("bmControls:\r\n");
DisplayBytes(data, i);
data += i;
AppendTextBuffer("iProcessing: 0x%02X\r\n",
*data++);
i = ProcessingDesc->bLength - 13 - ProcessingDesc->bNrInPins - i;
if (i)
{
AppendTextBuffer("Process Specific:\r\n");
DisplayBytes(data, i);
}
return TRUE;
}
//*****************************************************************************
//
// DisplayACExtensionUnit()
//
//*****************************************************************************
BOOL
DisplayACExtensionUnit (
PUSB_AUDIO_EXTENSION_UNIT_DESCRIPTOR ExtensionDesc
)
{
UCHAR i;
PUCHAR data;
if (ExtensionDesc->bLength < 13)
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Control Extension Unit Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
ExtensionDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
ExtensionDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
ExtensionDesc->bDescriptorSubtype);
AppendTextBuffer("bUnitID: 0x%02X\r\n",
ExtensionDesc->bUnitID);
AppendTextBuffer("wExtensionCode: 0x%04X\r\n",
ExtensionDesc->wExtensionCode);
AppendTextBuffer("bNrInPins: 0x%02X\r\n",
ExtensionDesc->bNrInPins);
for (i=0; i<ExtensionDesc->bNrInPins; i++)
{
AppendTextBuffer("baSourceID[%d]: 0x%02X\r\n",
i+1,
ExtensionDesc->baSourceID[i]);
}
data = &ExtensionDesc->baSourceID[ExtensionDesc->bNrInPins];
AppendTextBuffer("bNrChannels: 0x%02X\r\n",
*data++);
AppendTextBuffer("wChannelConfig: 0x%04X\r\n",
*((PUSHORT)data)++);
AppendTextBuffer("iChannelNames: 0x%02X\r\n",
*data++);
i = *data++;
AppendTextBuffer("bControlSize: 0x%02X\r\n",
i);
AppendTextBuffer("bmControls:\r\n");
DisplayBytes(data, i);
data += i;
AppendTextBuffer("iExtension: 0x%02X\r\n",
*data);
return TRUE;
}
//*****************************************************************************
//
// DisplayASGeneral()
//
//*****************************************************************************
BOOL
DisplayASGeneral (
PUSB_AUDIO_GENERAL_DESCRIPTOR GeneralDesc
)
{
PCHAR pStr;
if (GeneralDesc->bLength != sizeof(USB_AUDIO_GENERAL_DESCRIPTOR))
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Streaming Class Specific Interface Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
GeneralDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
GeneralDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
GeneralDesc->bDescriptorSubtype);
AppendTextBuffer("bTerminalLink: 0x%02X\r\n",
GeneralDesc->bTerminalLink);
AppendTextBuffer("bDelay: 0x%02X\r\n",
GeneralDesc->bDelay);
AppendTextBuffer("wFormatTag: 0x%04X",
GeneralDesc->wFormatTag);
pStr = FormatTypeCodeToName(GeneralDesc->wFormatTag);
if (pStr)
{
AppendTextBuffer(" (%s)\r\n",
pStr);
}
else
{
AppendTextBuffer("\r\n");
}
return TRUE;
}
//*****************************************************************************
//
// DisplayCSEndpoint()
//
//*****************************************************************************
BOOL
DisplayCSEndpoint (
PUSB_AUDIO_ENDPOINT_DESCRIPTOR EndpointDesc
)
{
if (EndpointDesc->bLength != sizeof(USB_AUDIO_ENDPOINT_DESCRIPTOR))
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Streaming Class Specific Audio Data Endpoint Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
EndpointDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
EndpointDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
EndpointDesc->bDescriptorSubtype);
AppendTextBuffer("bmAttributes: 0x%02X\r\n",
EndpointDesc->bmAttributes);
AppendTextBuffer("bLockDelayUnits: 0x%02X\r\n",
EndpointDesc->bLockDelayUnits);
AppendTextBuffer("wLockDelay: 0x%04X\r\n",
EndpointDesc->wLockDelay);
return TRUE;
}
//*****************************************************************************
//
// DisplayASFormatType()
//
//*****************************************************************************
BOOL
DisplayASFormatType (
PUSB_AUDIO_COMMON_FORMAT_DESCRIPTOR FormatDesc
)
{
UCHAR i, n;
ULONG freq;
PUCHAR data;
if (FormatDesc->bLength < sizeof(USB_AUDIO_COMMON_FORMAT_DESCRIPTOR))
{
OOPS();
return FALSE;
}
AppendTextBuffer("\r\nAudio Streaming Format Type Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
FormatDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
FormatDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
FormatDesc->bDescriptorSubtype);
AppendTextBuffer("bFormatType: 0x%02X\r\n",
FormatDesc->bFormatType);
if (FormatDesc->bFormatType == 0x01 ||
FormatDesc->bFormatType == 0x03)
{
PUSB_AUDIO_TYPE_I_OR_III_FORMAT_DESCRIPTOR FormatI_IIIDesc;
FormatI_IIIDesc = (PUSB_AUDIO_TYPE_I_OR_III_FORMAT_DESCRIPTOR)FormatDesc;
AppendTextBuffer("bNrChannels: 0x%02X\r\n",
FormatI_IIIDesc->bNrChannels);
AppendTextBuffer("bSubframeSize: 0x%02X\r\n",
FormatI_IIIDesc->bSubframeSize);
AppendTextBuffer("bBitResolution: 0x%02X\r\n",
FormatI_IIIDesc->bBitResolution);
AppendTextBuffer("bSamFreqType: 0x%02X\r\n",
FormatI_IIIDesc->bSamFreqType);
data = (PUCHAR)(FormatI_IIIDesc + 1);
n = FormatI_IIIDesc->bSamFreqType;
}
else if (FormatDesc->bFormatType == 0x02)
{
PUSB_AUDIO_TYPE_II_FORMAT_DESCRIPTOR FormatIIDesc;
FormatIIDesc = (PUSB_AUDIO_TYPE_II_FORMAT_DESCRIPTOR)FormatDesc;
AppendTextBuffer("wMaxBitRate: 0x%04X\r\n",
FormatIIDesc->wMaxBitRate);
AppendTextBuffer("wSamplesPerFrame: 0x%04X\r\n",
FormatIIDesc->wSamplesPerFrame);
AppendTextBuffer("bSamFreqType: 0x%02X\r\n",
FormatIIDesc->bSamFreqType);
data = (PUCHAR)(FormatIIDesc + 1);
n = FormatIIDesc->bSamFreqType;
}
else
{
data = NULL;
}
if (data != NULL)
{
if (n == 0)
{
freq = (data[0]) + (data[1] << 8) + (data[2] << 16);
data += 3;
AppendTextBuffer("tLowerSamFreq: 0x%06X (%d Hz)\r\n",
freq,
freq);
freq = (data[0]) + (data[1] << 8) + (data[2] << 16);
data += 3;
AppendTextBuffer("tUpperSamFreq: 0x%06X (%d Hz)\r\n",
freq,
freq);
}
else
{
for (i=0; i<n; i++)
{
freq = (data[0]) + (data[1] << 8) + (data[2] << 16);
data += 3;
AppendTextBuffer("tSamFreq[%d]: 0x%06X (%d Hz)\r\n",
i+1,
freq,
freq);
}
}
}
return TRUE;
}
//*****************************************************************************
//
// DisplayASFormatSpecific()
//
//*****************************************************************************
BOOL
DisplayASFormatSpecific (
PUSB_AUDIO_COMMON_DESCRIPTOR CommonDesc
)
{
AppendTextBuffer("\r\nAudio Streaming Format Specific Descriptor:\r\n");
AppendTextBuffer("bLength: 0x%02X\r\n",
CommonDesc->bLength);
AppendTextBuffer("bDescriptorType: 0x%02X\r\n",
CommonDesc->bDescriptorType);
AppendTextBuffer("bDescriptorSubtype: 0x%02X\r\n",
CommonDesc->bDescriptorSubtype);
DisplayBytes((PUCHAR)(CommonDesc + 1),
CommonDesc->bLength);
return TRUE;
}
//*****************************************************************************
//
// DisplayBytes()
//
//*****************************************************************************
VOID
DisplayBytes (
PUCHAR Data,
USHORT Len
)
{
USHORT i;
for (i = 0; i < Len; i++)
{
AppendTextBuffer("%02X ",
Data[i]);
if (i % 16 == 15)
{
AppendTextBuffer("\r\n");
}
}
if (i % 16 != 0)
{
AppendTextBuffer("\r\n");
}
}
//*****************************************************************************
//
// TermTypeCodeToName()
//
//*****************************************************************************
PCHAR
TermTypeCodeToName (
USHORT TermTypeCode
)
{
PTERMTYPE termType;
for (termType=TermTypes; termType->TermTypeName; termType++)
{
if (termType->TermTypeCode == TermTypeCode)
{
break;
}
}
return termType->TermTypeName;
}
//*****************************************************************************
//
// FormatTypeCodeToName()
//
//*****************************************************************************
PCHAR
FormatTypeCodeToName (
USHORT FormatTypeCode
)
{
PFORMATTYPE formatType;
for (formatType=FormatTypes; formatType->FormatTypeName; formatType++)
{
if (formatType->FormatTypeCode == FormatTypeCode)
{
break;
}
}
return formatType->FormatTypeName;
}
Detected encoding: ASCII (7 bit) | 2
|