diff options
Diffstat (limited to 'sound/usb/stream.c')
| -rw-r--r-- | sound/usb/stream.c | 23 | 
1 files changed, 14 insertions, 9 deletions
diff --git a/sound/usb/stream.c b/sound/usb/stream.c index ad181d538bd..7db2f8958e7 100644 --- a/sound/usb/stream.c +++ b/sound/usb/stream.c @@ -42,12 +42,11 @@   */  static void free_substream(struct snd_usb_substream *subs)  { -	struct list_head *p, *n; +	struct audioformat *fp, *n;  	if (!subs->num_formats)  		return; /* not initialized */ -	list_for_each_safe(p, n, &subs->fmt_list) { -		struct audioformat *fp = list_entry(p, struct audioformat, list); +	list_for_each_entry_safe(fp, n, &subs->fmt_list, list) {  		kfree(fp->rate_table);  		kfree(fp->chmap);  		kfree(fp); @@ -94,6 +93,7 @@ static void snd_usb_init_substream(struct snd_usb_stream *as,  	subs->dev = as->chip->dev;  	subs->txfr_quirk = as->chip->txfr_quirk;  	subs->speed = snd_usb_get_speed(subs->dev); +	subs->pkt_offset_adj = 0;  	snd_usb_set_pcm_ops(as->pcm, stream); @@ -313,14 +313,12 @@ int snd_usb_add_audio_stream(struct snd_usb_audio *chip,  			     int stream,  			     struct audioformat *fp)  { -	struct list_head *p;  	struct snd_usb_stream *as;  	struct snd_usb_substream *subs;  	struct snd_pcm *pcm;  	int err; -	list_for_each(p, &chip->pcm_list) { -		as = list_entry(p, struct snd_usb_stream, list); +	list_for_each_entry(as, &chip->pcm_list, list) {  		if (as->fmt_type != fp->fmt_type)  			continue;  		subs = &as->substream[stream]; @@ -332,8 +330,7 @@ int snd_usb_add_audio_stream(struct snd_usb_audio *chip,  		}  	}  	/* look for an empty stream */ -	list_for_each(p, &chip->pcm_list) { -		as = list_entry(p, struct snd_usb_stream, list); +	list_for_each_entry(as, &chip->pcm_list, list) {  		if (as->fmt_type != fp->fmt_type)  			continue;  		subs = &as->substream[stream]; @@ -396,6 +393,14 @@ static int parse_uac_endpoint_attributes(struct snd_usb_audio *chip,  	if (!csep && altsd->bNumEndpoints >= 2)  		csep = snd_usb_find_desc(alts->endpoint[1].extra, alts->endpoint[1].extralen, NULL, USB_DT_CS_ENDPOINT); +	/* +	 * If we can't locate the USB_DT_CS_ENDPOINT descriptor in the extra +	 * bytes after the first endpoint, go search the entire interface. +	 * Some devices have it directly *before* the standard endpoint. +	 */ +	if (!csep) +		csep = snd_usb_find_desc(alts->extra, alts->extralen, NULL, USB_DT_CS_ENDPOINT); +  	if (!csep || csep->bLength < 7 ||  	    csep->bDescriptorSubtype != UAC_EP_GENERAL) {  		snd_printk(KERN_WARNING "%d:%u:%d : no or invalid" @@ -463,7 +468,7 @@ int snd_usb_parse_audio_interface(struct snd_usb_audio *chip, int iface_no)  	struct usb_host_interface *alts;  	struct usb_interface_descriptor *altsd;  	int i, altno, err, stream; -	int format = 0, num_channels = 0; +	unsigned int format = 0, num_channels = 0;  	struct audioformat *fp = NULL;  	int num, protocol, clock = 0;  	struct uac_format_type_i_continuous_descriptor *fmt;  |