Playing audio through USB ADC?

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
rdos
Member
Member
Posts: 3297
Joined: Wed Oct 01, 2008 1:55 pm

Re: Playing audio through USB ADC?

Post by rdos »

I still don't understand the whole purpose of the project. AFAIK, you want to do some audio function with UEFI. For such a project to be useful, you need to support hardware platforms that exist, and not just QEMU or some odd configurations of real machines. I don't think many real PCs have the basic USB audio hardware. They typically have HDA and an USB AV camera. Motherboards typically have HDA too, and no camera. When you add a web-camera, it will be network based or USB AV.
Korona
Member
Member
Posts: 1000
Joined: Thu May 17, 2007 1:27 pm
Contact:

Re: Playing audio through USB ADC?

Post by Korona »

Guys, read the OP.

Presumably, people who need the hardware can just buy it and attach it.
Ethin wrote:As a part of Google Summer of Code I'm working on an audio output protocol for UEFI. This is in an effort to standardize UEFI accessibility for people with disabilities like myself.
managarm: Microkernel-based OS capable of running a Wayland desktop (Discord: https://discord.gg/7WB6Ur3). My OS-dev projects: [mlibc: Portable C library for managarm, qword, Linux, Sigma, ...] [LAI: AML interpreter] [xbstrap: Build system for OS distributions].
rdos
Member
Member
Posts: 3297
Joined: Wed Oct 01, 2008 1:55 pm

Re: Playing audio through USB ADC?

Post by rdos »

Korona wrote:Guys, read the OP.

Presumably, people who need the hardware can just buy it and attach it.
Ethin wrote:As a part of Google Summer of Code I'm working on an audio output protocol for UEFI. This is in an effort to standardize UEFI accessibility for people with disabilities like myself.
I'm not sure that you really can buy these devices at all. The basic USB audio standard is a bit dated, and I don't think many companies manufactured devices using it. In the Wikipedia entry about sound cards, it's claimed that many USB audio devices require proprietary drivers. The OP also claimed that his USB analyser had unknown (and thus proprietary) USB messages.

It's simple enough to retrieve the USB descriptors for the device and then confirm which protocol it uses. The vendor & product usually is also indicative of which hardware we are dealing with.

I mean, the OP needs a device that has descriptors for the basic audio interface, and if it doesn't, it cannot be used with that standard. If a device has an USB AV interface only, it doesn't support the basic audio interface.

Additionally, it seems like many simple USB audio devices implement control functions with USB HID, and implementing HID is just as complex as USB AV.
Ethin
Member
Member
Posts: 625
Joined: Sun Jun 23, 2019 5:36 pm
Location: North Dakota, United States

Re: Playing audio through USB ADC?

Post by Ethin »

rdos wrote:
Korona wrote:Guys, read the OP.

Presumably, people who need the hardware can just buy it and attach it.
Ethin wrote:As a part of Google Summer of Code I'm working on an audio output protocol for UEFI. This is in an effort to standardize UEFI accessibility for people with disabilities like myself.
I'm not sure that you really can buy these devices at all. The basic USB audio standard is a bit dated, and I don't think many companies manufactured devices using it. In the Wikipedia entry about sound cards, it's claimed that many USB audio devices require proprietary drivers. The OP also claimed that his USB analyser had unknown (and thus proprietary) USB messages.

It's simple enough to retrieve the USB descriptors for the device and then confirm which protocol it uses. The vendor & product usually is also indicative of which hardware we are dealing with.

I mean, the OP needs a device that has descriptors for the basic audio interface, and if it doesn't, it cannot be used with that standard. If a device has an USB AV interface only, it doesn't support the basic audio interface.

Additionally, it seems like many simple USB audio devices implement control functions with USB HID, and implementing HID is just as complex as USB AV.
Do you have any evidence for this? That USB AV is required? The packet dump was not mine; it was from somebody else. This specifically applies to USB audio, not USB AV, which is a completely different standard for encapsulating audio/video devices. The EFI audio output protocol is explicitly designed, for now, for audio-only devices. In the future we plan to extend it with HDA and VirtIO support, and maybe in the future it will contain support for USB AV (if only the audio portion of it), but at the moment USB AV is overkill. If there is sufficient evidence to suggest that USB-based audio devices register themselves as not USB audio device classes but USB audio/video device classes instead, then that will definitely make that a priority. But remember that this is not an operating system. We are attempting to support a wide range of devices, but EDK II is not going to provide every single driver for every single device class/subclass combination in existence. The vendor will need to pull their own weight as well. According to Wikipedia, the large majority of USB ADC-compliant audio devices are USB ADC 1.0 compliant and not any future revision, primarily because it took Windows over a decade to adopt USB ADC 2.0 and 3.0, so blame Microsoft for that. As such, we're targeting the most common devices first. HDA should cover 99 percent of laptops, VirtIO should cover (some) virtual machine hypervisors, and if USB ADC 1.0, HDA and VirtIO doesn't cover the entire device space, we'll implement support for other audio device classes/standards.
Korona
Member
Member
Posts: 1000
Joined: Thu May 17, 2007 1:27 pm
Contact:

Re: Playing audio through USB ADC?

Post by Korona »

I just checked two of my devices, an affordable wireless USB headset and a semi-professional USB microphone (in the ~$300 range). They both use the USB audio class (lsusb on Linux shows class 1, subclasses 1 and 2). Indeed, the use the HID class for controls, but supporting HID should not be that hard either (Managarm's driver is 750 sloc).
managarm: Microkernel-based OS capable of running a Wayland desktop (Discord: https://discord.gg/7WB6Ur3). My OS-dev projects: [mlibc: Portable C library for managarm, qword, Linux, Sigma, ...] [LAI: AML interpreter] [xbstrap: Build system for OS distributions].
Ethin
Member
Member
Posts: 625
Joined: Sun Jun 23, 2019 5:36 pm
Location: North Dakota, United States

Re: Playing audio through USB ADC?

Post by Ethin »

Korona wrote:I just checked two of my devices, an affordable wireless USB headset and a semi-professional USB microphone (in the ~$300 range). They both use the USB audio class (lsusb on Linux shows class 1, subclasses 1 and 2). Indeed, the use the HID class for controls, but supporting HID should not be that hard either (Managarm's driver is 750 sloc).
Thank you for illustrating my point. Class 1 is the audio class, subclass 1 is audio control and subclass 2 is audio streaming. I assume that BcdAdc was 0x0100 or at least less than 0x0200/0x0300?
rdos
Member
Member
Posts: 3297
Joined: Wed Oct 01, 2008 1:55 pm

Re: Playing audio through USB ADC?

Post by rdos »

Korona wrote:I just checked two of my devices, an affordable wireless USB headset and a semi-professional USB microphone (in the ~$300 range). They both use the USB audio class (lsusb on Linux shows class 1, subclasses 1 and 2). Indeed, the use the HID class for controls, but supporting HID should not be that hard either (Managarm's driver is 750 sloc).
I think you refer to legacy HID, which is not that hard to support. However, legacy HID only works with standard keyboards & mice, not controls on an audio class, which will require a full-blown HID implementation.
rdos
Member
Member
Posts: 3297
Joined: Wed Oct 01, 2008 1:55 pm

Re: Playing audio through USB ADC?

Post by rdos »

I have checked the audio implementation on many motherboards & portable computers, and basically all of them use HDA. Portables will implement the camera (but not audio) with USB AV. None of them will use the USB audio class.

Also, basically all portable computers and motherboards comes with HDA audio, so few users will need to use external USB audio devices, and more likely will use either the built-in speaker & microphone or plug in speaker & microphones with jacks into the built-in audio card.
nullplan
Member
Member
Posts: 1790
Joined: Wed Aug 30, 2017 8:24 am

Re: Playing audio through USB ADC?

Post by nullplan »

rdos wrote:I think you refer to legacy HID, which is not that hard to support. However, legacy HID only works with standard keyboards & mice, not controls on an audio class, which will require a full-blown HID implementation.
I have noticed this about you lately, you tend to have a bit of a condescending attitude towards people. I didn't want to believe myself that one could implement the HID spec in 750 lines, but man saying it can't be done should not interrupt man doing it. Even if the specific buttons the audio controls are using are not supported, adding them will be less than 100 lines. Less if setInputTranslation() were refactored to turn the large switches into maps or something.
rdos wrote:I have checked the audio implementation on many motherboards & portable computers, and basically all of them use HDA. Portables will implement the camera (but not audio) with USB AV. None of them will use the USB audio class.

Also, basically all portable computers and motherboards comes with HDA audio, so few users will need to use external USB audio devices, and more likely will use speaker & microphones that are plugged with jacks into the built-in audio card.
What is the purpose of these statements? Ethin wants to build a USB audio driver. Who are you to discourage that? You are condescending and dismissive towards anything that is not part of your little world, as if you cannot possibly fathom that people would use different hardware at different times. Or do things differently from you.
Carpe diem!
Korona
Member
Member
Posts: 1000
Joined: Thu May 17, 2007 1:27 pm
Contact:

Re: Playing audio through USB ADC?

Post by Korona »

rdos wrote:I think you refer to legacy HID, which is not that hard to support. However, legacy HID only works with standard keyboards & mice, not controls on an audio class, which will require a full-blown HID implementation.
No, I mean a report-descriptor-based HID parser. The boot protocol requires much less than 750 sloc (the boot protocol mandates a fixed layout for HID reports).
rdos wrote:Also, basically all portable computers and motherboards comes with HDA audio, so few users will need to use external USB audio devices, and more likely will use either the built-in speaker & microphone or plug in speaker & microphones with jacks into the built-in audio card.
Yes, all mainboards also support HDA. However, the HDA implementation are not sufficient if you want high quality sound. Additionally, audio jacks do support wireless headsets, these are almost always connected over USB (or Bluetooth for cheaper / more portable ones). High quality microphones/monitors need preamplifiers that are typically connected over USB, too.
managarm: Microkernel-based OS capable of running a Wayland desktop (Discord: https://discord.gg/7WB6Ur3). My OS-dev projects: [mlibc: Portable C library for managarm, qword, Linux, Sigma, ...] [LAI: AML interpreter] [xbstrap: Build system for OS distributions].
rdos
Member
Member
Posts: 3297
Joined: Wed Oct 01, 2008 1:55 pm

Re: Playing audio through USB ADC?

Post by rdos »

Korona wrote:
rdos wrote:I think you refer to legacy HID, which is not that hard to support. However, legacy HID only works with standard keyboards & mice, not controls on an audio class, which will require a full-blown HID implementation.
No, I mean a report-descriptor-based HID parser. The boot protocol requires much less than 750 sloc (the boot protocol mandates a fixed layout for HID reports).
Possibly, but implementing the HDA codec is not more complex than implementing HID, so I still think it is a sub-optimal decision to implement USB audio instead of HDA.
Korona wrote: Additionally, audio jacks do support wireless headsets, these are almost always connected over USB (or Bluetooth for cheaper / more portable ones). High quality microphones/monitors need preamplifiers that are typically connected over USB, too.
I think Bluetooth is more popular, and it uses completely different hardware.

However, at least you showed that there is still a market for USB audio, presumably when implementing high quality devices.
rdos
Member
Member
Posts: 3297
Joined: Wed Oct 01, 2008 1:55 pm

Re: Playing audio through USB ADC?

Post by rdos »

nullplan wrote:
rdos wrote:I think you refer to legacy HID, which is not that hard to support. However, legacy HID only works with standard keyboards & mice, not controls on an audio class, which will require a full-blown HID implementation.
I have noticed this about you lately, you tend to have a bit of a condescending attitude towards people. I didn't want to believe myself that one could implement the HID spec in 750 lines, but man saying it can't be done should not interrupt man doing it. Even if the specific buttons the audio controls are using are not supported, adding them will be less than 100 lines. Less if setInputTranslation() were refactored to turn the large switches into maps or something.
I've done both the HID (descriptor based), including supporting touch screens and the HDA & HDA codec, and so I think I have a good idea which is easiest to support, and it is HDA. How many lines it requires is not that interesting and will depend on how much you want to abstract it. 750 lines seems like something that has no abstraction. If people want to code like that, fine, but that's not my preference. My basic HID driver is a couple of thousand lines of C code, and this doesn't include keyboard, mouse or touch.
nullplan wrote:
rdos wrote:I have checked the audio implementation on many motherboards & portable computers, and basically all of them use HDA. Portables will implement the camera (but not audio) with USB AV. None of them will use the USB audio class.

Also, basically all portable computers and motherboards comes with HDA audio, so few users will need to use external USB audio devices, and more likely will use speaker & microphones that are plugged with jacks into the built-in audio card.
What is the purpose of these statements? Ethin wants to build a USB audio driver. Who are you to discourage that? You are condescending and dismissive towards anything that is not part of your little world, as if you cannot possibly fathom that people would use different hardware at different times. Or do things differently from you.
If you had read the whole thread you would have noticed that he wanted to implement the easiest driver, and then concluded this was USB audio, which I think was a mistake. However, if he insists on implementing USB audio, then I have no problem with that.
Ethin
Member
Member
Posts: 625
Joined: Sun Jun 23, 2019 5:36 pm
Location: North Dakota, United States

Re: Playing audio through USB ADC?

Post by Ethin »

There has and always will be a market for USB audio devices. USB AV is used only for cameras and other visual input devices (and perhaps some USB monitors with speakers). USB audio is used for USB headphones, speakers, mixers, microphones, and pretty much every other kind of audio-only input/output device. Yes, HDA is used on practically all computers nowadays, but that in no way implies that USB ADC has no purpose. By that logic, I shouldn't support VirtIO, and neither should any other OS, because its only used on VMs. And yet Linux has VirtIO support, Windows has it through external drivers, MacOS does, the BSDs do... I could go on.
Here's an example of a USB ADC device. By your logic, UEFI shouldn't support it:
Bus 001 Device 004: ID 08bb:2902 Texas Instruments PCM2902 Audio Codec
Device Descriptor:
bLength 18
bDescriptorType 1
bcdUSB 1.10
bDeviceClass 0
bDeviceSubClass 0
bDeviceProtocol 0
bMaxPacketSize0 8
idVendor 0x08bb Texas Instruments
idProduct 0x2902 PCM2902 Audio Codec
bcdDevice 1.00
iManufacturer 1 Burr-Brown from TI
iProduct 2 USB Audio CODEC
iSerial 0
bNumConfigurations 1
Configuration Descriptor:
bLength 9
bDescriptorType 2
wTotalLength 0x04a7
bNumInterfaces 4
bConfigurationValue 1
iConfiguration 0
bmAttributes 0x80
(Bus Powered)
MaxPower 100mA
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 10
bDescriptorType 36
bDescriptorSubtype 1 (HEADER)
bcdADC 1.00
wTotalLength 0x003e
bInCollection 2
baInterfaceNr(0) 1
baInterfaceNr(1) 2
[snipped]
rdos, Please stop being condescending. It doesn't make you look very good IMO and isn't helpful to this topic. You develop what you want to support, I'll do the same. I'd prefer that you be helpful than condescending like you are being right now. Just because one bit of tech is used predominently over another doesn't mean the other is useless.
Technology is developed for a reason. It is implemented in OSes for a reason. It is implemented in firmware for a reason. The aim of this project is to eventually support as many audio devices (not AV devices, but audio devices) as possible. That means supporting USB ADC, regardless of what your opinion is. The above device information was, by the way, from my Mixer, and, as indicated, its an audio device class. Not a USB AV class. (Also, USB AV doesn't support surround sound devices, effects processors and such.) You will find that USB ADC is used a lot more than you think. Go buy any pair of USB headphones and you'll see exactly what Korona and I are saying -- they are *all* USB ADC, or nearly all of them are.
Ethin
Member
Member
Posts: 625
Joined: Sun Jun 23, 2019 5:36 pm
Location: North Dakota, United States

Re: Playing audio through USB ADC?

Post by Ethin »

Suffering a bit of a problem (and the USB trace events aren't very helpful in QEMU). I do the following but each time I do, I get a USB stall:
  1. Read two (2) bytes from the descriptor to get its length and descriptor type (called n)
  2. Read n bytes to read the full descriptor header
  3. read n[total length] to read the descriptor header and all descriptors that follow
I do this using a single 64K buffer because its easier than allocating multiple smaller buffers and I can just reuse it each time. My code is thus:

Code: Select all

    UINT8* Header = 0;
        status = st->BootServices->AllocatePool(EfiBootServicesData, 65536, (void*)&Header);
    if (EFI_ERROR(status))
      goto failed;

    EFI_USB_DEVICE_REQUEST req = {0};
    req.RequestType = (USB_DEV_GET_DESCRIPTOR_REQ_TYPE | USB_REQ_TYPE_CLASS);
    req.Request = USB_REQ_GET_DESCRIPTOR;
    req.Value = (0x24 << 8);
    req.Index = interfaceDescriptor.InterfaceNumber;
    req.Length = 2;
    status = UsbIo->UsbControlTransfer(UsbIo, &req, EfiUsbDataIn, PcdGet32 (PcdUsbTransferTimeoutValue), &Header, req.Length, &UsbStatus);
    if (EFI_ERROR(status)) {
      st->BootServices->FreePool(Header);
      goto failed;
}
    req.Length = Header[0];
    status = UsbIo->UsbControlTransfer(UsbIo, &req, EfiUsbDataIn, PcdGet32 (PcdUsbTransferTimeoutValue), &Header, req.Length, &UsbStatus);
    if (EFI_ERROR(status)) {
      st->BootServices->FreePool(Header);
      goto failed;
}
  req.Length = (Header[6] << 8) | Header[5];
    status = UsbIo->UsbControlTransfer(UsbIo, &req, EfiUsbDataIn, PcdGet32 (PcdUsbTransferTimeoutValue), &Header, req.Length, &UsbStatus);
    if (EFI_ERROR(status)) {
      st->BootServices->FreePool(Header);
      goto failed;
    }
      Print(L"Length is %d, total length is %d, USB ADC version is %04x, %d interfaces in collection\n", Header[0], req.Length, Header[3], Header[7]);
All I'm trying to do is read the descriptor -- if I can do that I feel like everything else will naturally fall into place. I'm not really sure what I'm doing wrong, so I consulted the list of available qemu trace events (https://github.com/qemu/qemu/blob/maste ... ace-events). However, using the usb_xfer_* glob to match all transfer events didn't really help me much. All they give me is this, from what I can tell:
usb_xhci_oper_read off 0x0004, ret 0x00000008
usb_xhci_oper_read off 0x0004, ret 0x00000008
usb_xhci_doorbell_write off 0x0004, val 0x00000001
usb_xhci_ep_kick slotid 1, epid 1, streamid 0
usb_xhci_fetch_trb addr 0x000000007ede86e0, TR_SETUP, p 0x00020000240006a0, s 0x00000008, c 0x00030861
usb_xhci_fetch_trb addr 0x000000007ede86f0, TR_DATA, p 0x000000007ff15330, s 0x00000002, c 0x00010c25
usb_xhci_fetch_trb addr 0x000000007ede8700, TR_STATUS, p 0x0000000000000000, s 0x00000000, c 0x00001021
usb_xhci_xfer_start 0x7fd5500723f0: slotid 1, epid 1, streamid 0
usb_packet_state_change bus 1, port 1, ep 0, packet 0x7fd5500723f8, state undef -> setup
usb_packet_state_change bus 1, port 1, ep 0, packet 0x7fd5500723f8, state setup -> complete
usb_xhci_xfer_error 0x7fd5500723f0: ret -3
So I'm quite confused as to what I'm doing wrong here. Ideas/thoughts?
rdos
Member
Member
Posts: 3297
Joined: Wed Oct 01, 2008 1:55 pm

Re: Playing audio through USB ADC?

Post by rdos »

I once engaged in this thread because I thought it was an interesting project, but I have changed my mind. This seems to be just another emulator or odd non-standard hardware project, and so I have lost interest. The inability to have a civil discussion without insults & personal attacks doesn't help. IOW, I'm going ignore this project completely from now on, as I feel I will only waste my time.
Post Reply