Hi everyone,
Firstly, I know UAC 2.0 USB Audio isn’t supported on Haiku yet, and that my Focusrite Scarletts aren’t going to work! My question is about trying to get a little closer to getting them working. I’d love to be able to listen to music on proper speakers & headphones, not my laptop’s terrible audio chip!
I know listusb is the first stop for detecting a device and its attributes, but I seem to have found bugs that mean UAC 2.0 audio devices aren’t showing correct bit depth. It’s also listing totally garbled sample rates, because it’s assuming UAC 1.0 data and reading beyond the end of the data structure. It also seems we would need someone to update USB_audio.h with structs from the UAC 2.0 specifications, in order to get closer to things really working properly?
I’ve managed to make a couple of fixes to listusb so that it at least shows the correct Bit Resolution for FORMAT_TYPE_I, and omit displaying the broken sample rates. But I have no idea how to contribute this! I thought I’d paste here in case it helps:
- Move
static uint16 bcd_release_no;out ofDumpAudioControlCSInterfaceDescriptorand to the top of usb_audio.cpp, so that the UAC Audio version is available to all functions that need it - Replace
DumpGeneralASInterfaceDescriptorwith this:
voidDumpGeneralASInterfaceDescriptor(const usb_audio_streaming_interface_descriptor* descriptor) {
printf(" Subtype … %u (AS_GENERAL)\n",descriptor->descriptor_subtype);
printf(" Terminal link … %u\n",descriptor->terminal_link);
if (bcd_release_no < USB_AUDIO_CLASS_VERSION_2) {
printf(" Delay ............. %u\n",
descriptor->r1.delay);
printf(" Format tag ........ %u\n",
descriptor->r1.format_tag);
} else {
// Audio 2.0
printf(" bm Controls ....... 0x%02x\n",
descriptor->r2.bm_controls);
printf(" Format Type ....... %u\n",
descriptor->r2.format_type);
printf(" bm Formats ........ 0x%08" B_PRIx32 "\n",
descriptor->r2.bm_formats);
printf(" Num Channels ...... %u\n",
descriptor->r2.num_output_pins);
printf(" Channel Config .... 0x%08" B_PRIx32 "\n",
descriptor->r2.channel_config);
printf(" Channel Names ..... %u\n",
descriptor->r2.channel_names);
}
}
- And then replace the whole of DumpASFormatTypeI with this, so that it takes into account UAC 2.0:
void
DumpASFormatTypeI(const usb_audio_format_descriptor* descriptor)
{
if (bcd_release_no < USB_AUDIO_CLASS_VERSION_2) {
printf(" Subtype ........... %u (FORMAT_TYPE)\n",
descriptor->descriptor_subtype);
printf(" Format Type ....... %u (FORMAT_TYPE_I)\n",
descriptor->format_type);
printf(" Channels .......... %u\n",
descriptor->typeI.nr_channels);
printf(" Subframe size ..... %u\n",
descriptor->typeI.subframe_size);
printf(" Bit resolution .... %u\n",
descriptor->typeI.bit_resolution);
DumpSamplingFrequencies(descriptor->typeI.sam_freq_type,
descriptor->typeI.sam_freqs);
} else {
// Assume Audio 2.0
// UAC2 (Audio 2) structs are missing from USB_audio.h
// so we define the struct below:
// UAC2 Type I format descriptor layout
struct {
uint8 length;
uint8 descriptor_type;
uint8 descriptor_subtype;
uint8 format_type;
uint8 sub_slot_size;
uint8 bit_resolution;
} _PACKED *uac2fmt = (decltype(uac2fmt))descriptor;
printf(" Subtype ........... %u (FORMAT_TYPE)\n",
uac2fmt->descriptor_subtype);
printf(" Format Type ....... %u (FORMAT_TYPE_I)\n",
uac2fmt->format_type);
printf(" Sub Slot Size ..... %u\n",
uac2fmt->sub_slot_size);
printf(" Bit Resolution .... %u\n",
uac2fmt->bit_resolution);
printf(" (Sample rates via Clock Source)\n");
}
}
To get that second function to work I had to add the struct into the function, but it would obviously need to be in USB_audio.h itself.
I realize this doesn’t get us much closer to USB 2.0 Audio support for the Scarlett or any other devices that use it. But I assume we would need more contributions along these lines to get us closer to having it working?
And I realize diffs via forum are terrible… what’s the best way I should submit something like this, if it’s helpful? Last night I also made edits to the StreamRadio code so I could get it to compile (trying to fix some audio crackling issues), seems every call to fStreamUrl.SetUrlString needed to be updated because of changes to the API requiring either BUrl or BString to have an encoding parameter added.
Apologies for the extremely newbie post, but I’d love to see the Focusrite Scarlett range working in Haiku!