mirror of
https://github.com/torvalds/linux.git
synced 2024-12-28 22:02:28 +00:00
ALSA: usx2y: Avoid camelCase
For improving readability, convert camelCase fields, variables and functions to the plain names with underscore. Also align the macros to be capital letters. All done via sed, no functional changes. Note that you'll still see many coding style issues even after this patch; the fixes will follow. Link: https://lore.kernel.org/r/20210517131545.27252-2-tiwai@suse.de Signed-off-by: Takashi Iwai <tiwai@suse.de>
This commit is contained in:
parent
08fdced60c
commit
bae3ce4942
@ -29,7 +29,7 @@ static vm_fault_t snd_us428ctls_vm_fault(struct vm_fault *vmf)
|
||||
vmf->pgoff);
|
||||
|
||||
offset = vmf->pgoff << PAGE_SHIFT;
|
||||
vaddr = (char *)((struct usX2Ydev *)vmf->vma->vm_private_data)->us428ctls_sharedmem + offset;
|
||||
vaddr = (char *)((struct usx2ydev *)vmf->vma->vm_private_data)->us428ctls_sharedmem + offset;
|
||||
page = virt_to_page(vaddr);
|
||||
get_page(page);
|
||||
vmf->page = page;
|
||||
@ -47,7 +47,7 @@ static const struct vm_operations_struct us428ctls_vm_ops = {
|
||||
static int snd_us428ctls_mmap(struct snd_hwdep * hw, struct file *filp, struct vm_area_struct *area)
|
||||
{
|
||||
unsigned long size = (unsigned long)(area->vm_end - area->vm_start);
|
||||
struct usX2Ydev *us428 = hw->private_data;
|
||||
struct usx2ydev *us428 = hw->private_data;
|
||||
|
||||
// FIXME this hwdep interface is used twice: fpga download and mmap for controlling Lights etc. Maybe better using 2 hwdep devs?
|
||||
// so as long as the device isn't fully initialised yet we return -EBUSY here.
|
||||
@ -66,7 +66,7 @@ static int snd_us428ctls_mmap(struct snd_hwdep * hw, struct file *filp, struct v
|
||||
if (!us428->us428ctls_sharedmem)
|
||||
return -ENOMEM;
|
||||
memset(us428->us428ctls_sharedmem, -1, sizeof(struct us428ctls_sharedmem));
|
||||
us428->us428ctls_sharedmem->CtlSnapShotLast = -2;
|
||||
us428->us428ctls_sharedmem->ctl_snapshot_last = -2;
|
||||
}
|
||||
area->vm_ops = &us428ctls_vm_ops;
|
||||
area->vm_flags |= VM_DONTEXPAND | VM_DONTDUMP;
|
||||
@ -77,21 +77,21 @@ static int snd_us428ctls_mmap(struct snd_hwdep * hw, struct file *filp, struct v
|
||||
static __poll_t snd_us428ctls_poll(struct snd_hwdep *hw, struct file *file, poll_table *wait)
|
||||
{
|
||||
__poll_t mask = 0;
|
||||
struct usX2Ydev *us428 = hw->private_data;
|
||||
struct usx2ydev *us428 = hw->private_data;
|
||||
struct us428ctls_sharedmem *shm = us428->us428ctls_sharedmem;
|
||||
if (us428->chip_status & USX2Y_STAT_CHIP_HUP)
|
||||
return EPOLLHUP;
|
||||
|
||||
poll_wait(file, &us428->us428ctls_wait_queue_head, wait);
|
||||
|
||||
if (shm != NULL && shm->CtlSnapShotLast != shm->CtlSnapShotRed)
|
||||
if (shm != NULL && shm->ctl_snapshot_last != shm->ctl_snapshot_red)
|
||||
mask |= EPOLLIN;
|
||||
|
||||
return mask;
|
||||
}
|
||||
|
||||
|
||||
static int snd_usX2Y_hwdep_dsp_status(struct snd_hwdep *hw,
|
||||
static int snd_usx2y_hwdep_dsp_status(struct snd_hwdep *hw,
|
||||
struct snd_hwdep_dsp_status *info)
|
||||
{
|
||||
static const char * const type_ids[USX2Y_TYPE_NUMS] = {
|
||||
@ -99,7 +99,7 @@ static int snd_usX2Y_hwdep_dsp_status(struct snd_hwdep *hw,
|
||||
[USX2Y_TYPE_224] = "us224",
|
||||
[USX2Y_TYPE_428] = "us428",
|
||||
};
|
||||
struct usX2Ydev *us428 = hw->private_data;
|
||||
struct usx2ydev *us428 = hw->private_data;
|
||||
int id = -1;
|
||||
|
||||
switch (le16_to_cpu(us428->dev->descriptor.idProduct)) {
|
||||
@ -124,7 +124,7 @@ static int snd_usX2Y_hwdep_dsp_status(struct snd_hwdep *hw,
|
||||
}
|
||||
|
||||
|
||||
static int usX2Y_create_usbmidi(struct snd_card *card)
|
||||
static int usx2y_create_usbmidi(struct snd_card *card)
|
||||
{
|
||||
static const struct snd_usb_midi_endpoint_info quirk_data_1 = {
|
||||
.out_ep = 0x06,
|
||||
@ -152,28 +152,28 @@ static int usX2Y_create_usbmidi(struct snd_card *card)
|
||||
.type = QUIRK_MIDI_FIXED_ENDPOINT,
|
||||
.data = &quirk_data_2
|
||||
};
|
||||
struct usb_device *dev = usX2Y(card)->dev;
|
||||
struct usb_device *dev = usx2y(card)->dev;
|
||||
struct usb_interface *iface = usb_ifnum_to_if(dev, 0);
|
||||
const struct snd_usb_audio_quirk *quirk =
|
||||
le16_to_cpu(dev->descriptor.idProduct) == USB_ID_US428 ?
|
||||
&quirk_2 : &quirk_1;
|
||||
|
||||
snd_printdd("usX2Y_create_usbmidi \n");
|
||||
return snd_usbmidi_create(card, iface, &usX2Y(card)->midi_list, quirk);
|
||||
snd_printdd("usx2y_create_usbmidi \n");
|
||||
return snd_usbmidi_create(card, iface, &usx2y(card)->midi_list, quirk);
|
||||
}
|
||||
|
||||
static int usX2Y_create_alsa_devices(struct snd_card *card)
|
||||
static int usx2y_create_alsa_devices(struct snd_card *card)
|
||||
{
|
||||
int err;
|
||||
|
||||
do {
|
||||
if ((err = usX2Y_create_usbmidi(card)) < 0) {
|
||||
snd_printk(KERN_ERR "usX2Y_create_alsa_devices: usX2Y_create_usbmidi error %i \n", err);
|
||||
if ((err = usx2y_create_usbmidi(card)) < 0) {
|
||||
snd_printk(KERN_ERR "usx2y_create_alsa_devices: usx2y_create_usbmidi error %i \n", err);
|
||||
break;
|
||||
}
|
||||
if ((err = usX2Y_audio_create(card)) < 0)
|
||||
if ((err = usx2y_audio_create(card)) < 0)
|
||||
break;
|
||||
if ((err = usX2Y_hwdep_pcm_new(card)) < 0)
|
||||
if ((err = usx2y_hwdep_pcm_new(card)) < 0)
|
||||
break;
|
||||
if ((err = snd_card_register(card)) < 0)
|
||||
break;
|
||||
@ -182,10 +182,10 @@ static int usX2Y_create_alsa_devices(struct snd_card *card)
|
||||
return err;
|
||||
}
|
||||
|
||||
static int snd_usX2Y_hwdep_dsp_load(struct snd_hwdep *hw,
|
||||
static int snd_usx2y_hwdep_dsp_load(struct snd_hwdep *hw,
|
||||
struct snd_hwdep_dsp_image *dsp)
|
||||
{
|
||||
struct usX2Ydev *priv = hw->private_data;
|
||||
struct usx2ydev *priv = hw->private_data;
|
||||
struct usb_device* dev = priv->dev;
|
||||
int lret, err;
|
||||
char *buf;
|
||||
@ -206,19 +206,19 @@ static int snd_usX2Y_hwdep_dsp_load(struct snd_hwdep *hw,
|
||||
return err;
|
||||
if (dsp->index == 1) {
|
||||
msleep(250); // give the device some time
|
||||
err = usX2Y_AsyncSeq04_init(priv);
|
||||
err = usx2y_async_seq04_init(priv);
|
||||
if (err) {
|
||||
snd_printk(KERN_ERR "usX2Y_AsyncSeq04_init error \n");
|
||||
snd_printk(KERN_ERR "usx2y_async_seq04_init error \n");
|
||||
return err;
|
||||
}
|
||||
err = usX2Y_In04_init(priv);
|
||||
err = usx2y_in04_init(priv);
|
||||
if (err) {
|
||||
snd_printk(KERN_ERR "usX2Y_In04_init error \n");
|
||||
snd_printk(KERN_ERR "usx2y_in04_init error \n");
|
||||
return err;
|
||||
}
|
||||
err = usX2Y_create_alsa_devices(hw->card);
|
||||
err = usx2y_create_alsa_devices(hw->card);
|
||||
if (err) {
|
||||
snd_printk(KERN_ERR "usX2Y_create_alsa_devices error %i \n", err);
|
||||
snd_printk(KERN_ERR "usx2y_create_alsa_devices error %i \n", err);
|
||||
snd_card_free(hw->card);
|
||||
return err;
|
||||
}
|
||||
@ -229,7 +229,7 @@ static int snd_usX2Y_hwdep_dsp_load(struct snd_hwdep *hw,
|
||||
}
|
||||
|
||||
|
||||
int usX2Y_hwdep_new(struct snd_card *card, struct usb_device* device)
|
||||
int usx2y_hwdep_new(struct snd_card *card, struct usb_device* device)
|
||||
{
|
||||
int err;
|
||||
struct snd_hwdep *hw;
|
||||
@ -238,9 +238,9 @@ int usX2Y_hwdep_new(struct snd_card *card, struct usb_device* device)
|
||||
return err;
|
||||
|
||||
hw->iface = SNDRV_HWDEP_IFACE_USX2Y;
|
||||
hw->private_data = usX2Y(card);
|
||||
hw->ops.dsp_status = snd_usX2Y_hwdep_dsp_status;
|
||||
hw->ops.dsp_load = snd_usX2Y_hwdep_dsp_load;
|
||||
hw->private_data = usx2y(card);
|
||||
hw->ops.dsp_status = snd_usx2y_hwdep_dsp_status;
|
||||
hw->ops.dsp_load = snd_usx2y_hwdep_dsp_load;
|
||||
hw->ops.mmap = snd_us428ctls_mmap;
|
||||
hw->ops.poll = snd_us428ctls_poll;
|
||||
hw->exclusive = 1;
|
||||
|
@ -2,6 +2,6 @@
|
||||
#ifndef USX2YHWDEP_H
|
||||
#define USX2YHWDEP_H
|
||||
|
||||
int usX2Y_hwdep_new(struct snd_card *card, struct usb_device* device);
|
||||
int usx2y_hwdep_new(struct snd_card *card, struct usb_device* device);
|
||||
|
||||
#endif
|
||||
|
@ -4,28 +4,28 @@
|
||||
* Copyright (c) 2003 by Karsten Wiese <annabellesgarden@yahoo.de>
|
||||
*/
|
||||
|
||||
enum E_In84{
|
||||
eFader0 = 0,
|
||||
eFader1,
|
||||
eFader2,
|
||||
eFader3,
|
||||
eFader4,
|
||||
eFader5,
|
||||
eFader6,
|
||||
eFader7,
|
||||
eFaderM,
|
||||
eTransport,
|
||||
eModifier = 10,
|
||||
eFilterSelect,
|
||||
eSelect,
|
||||
eMute,
|
||||
enum E_IN84 {
|
||||
E_FADER_0 = 0,
|
||||
E_FADER_1,
|
||||
E_FADER_2,
|
||||
E_FADER_3,
|
||||
E_FADER_4,
|
||||
E_FADER_5,
|
||||
E_FADER_6,
|
||||
E_FADER_7,
|
||||
E_FADER_M,
|
||||
E_TRANSPORT,
|
||||
E_MODIFIER = 10,
|
||||
E_FILTER_SELECT,
|
||||
E_SELECT,
|
||||
E_MUTE,
|
||||
|
||||
eSwitch = 15,
|
||||
eWheelGain,
|
||||
eWheelFreq,
|
||||
eWheelQ,
|
||||
eWheelPan,
|
||||
eWheel = 20
|
||||
E_SWITCH = 15,
|
||||
E_WHEEL_GAIN,
|
||||
E_WHEEL_FREQ,
|
||||
E_WHEEL_Q,
|
||||
E_WHEEL_PAN,
|
||||
E_WHEEL = 20
|
||||
};
|
||||
|
||||
#define T_RECORD 1
|
||||
@ -39,53 +39,53 @@ enum E_In84{
|
||||
|
||||
|
||||
struct us428_ctls {
|
||||
unsigned char Fader[9];
|
||||
unsigned char Transport;
|
||||
unsigned char Modifier;
|
||||
unsigned char FilterSelect;
|
||||
unsigned char Select;
|
||||
unsigned char Mute;
|
||||
unsigned char UNKNOWN;
|
||||
unsigned char Switch;
|
||||
unsigned char Wheel[5];
|
||||
unsigned char fader[9];
|
||||
unsigned char transport;
|
||||
unsigned char modifier;
|
||||
unsigned char filters_elect;
|
||||
unsigned char select;
|
||||
unsigned char mute;
|
||||
unsigned char unknown;
|
||||
unsigned char wswitch;
|
||||
unsigned char wheel[5];
|
||||
};
|
||||
|
||||
struct us428_setByte {
|
||||
unsigned char Offset,
|
||||
Value;
|
||||
struct us428_set_byte {
|
||||
unsigned char offset,
|
||||
value;
|
||||
};
|
||||
|
||||
enum {
|
||||
eLT_Volume = 0,
|
||||
eLT_Light
|
||||
ELT_VOLUME = 0,
|
||||
ELT_LIGHT
|
||||
};
|
||||
|
||||
struct usX2Y_volume {
|
||||
unsigned char Channel,
|
||||
LH,
|
||||
LL,
|
||||
RH,
|
||||
RL;
|
||||
struct usx2y_volume {
|
||||
unsigned char channel,
|
||||
lh,
|
||||
ll,
|
||||
rh,
|
||||
rl;
|
||||
};
|
||||
|
||||
struct us428_lights {
|
||||
struct us428_setByte Light[7];
|
||||
struct us428_set_byte light[7];
|
||||
};
|
||||
|
||||
struct us428_p4out {
|
||||
char type;
|
||||
union {
|
||||
struct usX2Y_volume vol;
|
||||
struct usx2y_volume vol;
|
||||
struct us428_lights lights;
|
||||
} val;
|
||||
};
|
||||
|
||||
#define N_us428_ctl_BUFS 16
|
||||
#define N_us428_p4out_BUFS 16
|
||||
struct us428ctls_sharedmem{
|
||||
struct us428_ctls CtlSnapShot[N_us428_ctl_BUFS];
|
||||
int CtlSnapShotDiffersAt[N_us428_ctl_BUFS];
|
||||
int CtlSnapShotLast, CtlSnapShotRed;
|
||||
struct us428_p4out p4out[N_us428_p4out_BUFS];
|
||||
int p4outLast, p4outSent;
|
||||
#define N_US428_CTL_BUFS 16
|
||||
#define N_US428_P4OUT_BUFS 16
|
||||
struct us428ctls_sharedmem {
|
||||
struct us428_ctls ctl_snapshot[N_US428_CTL_BUFS];
|
||||
int ctl_snapshot_differs_at[N_US428_CTL_BUFS];
|
||||
int ctl_snapshot_last, ctl_snapshot_red;
|
||||
struct us428_p4out p4out[N_US428_P4OUT_BUFS];
|
||||
int p4out_last, p4out_sent;
|
||||
};
|
||||
|
@ -17,7 +17,7 @@
|
||||
|
||||
2004-10-26 Karsten Wiese
|
||||
Version 0.8.6:
|
||||
wake_up() process waiting in usX2Y_urbs_start() on error.
|
||||
wake_up() process waiting in usx2y_urbs_start() on error.
|
||||
|
||||
2004-10-21 Karsten Wiese
|
||||
Version 0.8.5:
|
||||
@ -48,7 +48,7 @@
|
||||
2004-06-12 Karsten Wiese
|
||||
Version 0.6.3:
|
||||
Made it thus the following rule is enforced:
|
||||
"All pcm substreams of one usX2Y have to operate at the same rate & format."
|
||||
"All pcm substreams of one usx2y have to operate at the same rate & format."
|
||||
|
||||
2004-04-06 Karsten Wiese
|
||||
Version 0.6.0:
|
||||
@ -150,161 +150,161 @@ module_param_array(enable, bool, NULL, 0444);
|
||||
MODULE_PARM_DESC(enable, "Enable "NAME_ALLCAPS".");
|
||||
|
||||
|
||||
static int snd_usX2Y_card_used[SNDRV_CARDS];
|
||||
static int snd_usx2y_card_used[SNDRV_CARDS];
|
||||
|
||||
static void usX2Y_usb_disconnect(struct usb_device* usb_device, void* ptr);
|
||||
static void snd_usX2Y_card_private_free(struct snd_card *card);
|
||||
static void usx2y_usb_disconnect(struct usb_device* usb_device, void* ptr);
|
||||
static void snd_usx2y_card_private_free(struct snd_card *card);
|
||||
|
||||
/*
|
||||
* pipe 4 is used for switching the lamps, setting samplerate, volumes ....
|
||||
*/
|
||||
static void i_usX2Y_Out04Int(struct urb *urb)
|
||||
static void i_usx2y_out04_int(struct urb *urb)
|
||||
{
|
||||
#ifdef CONFIG_SND_DEBUG
|
||||
if (urb->status) {
|
||||
int i;
|
||||
struct usX2Ydev *usX2Y = urb->context;
|
||||
for (i = 0; i < 10 && usX2Y->AS04.urb[i] != urb; i++);
|
||||
snd_printdd("i_usX2Y_Out04Int() urb %i status=%i\n", i, urb->status);
|
||||
struct usx2ydev *usx2y = urb->context;
|
||||
for (i = 0; i < 10 && usx2y->as04.urb[i] != urb; i++);
|
||||
snd_printdd("i_usx2y_out04_int() urb %i status=%i\n", i, urb->status);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
static void i_usX2Y_In04Int(struct urb *urb)
|
||||
static void i_usx2y_in04_int(struct urb *urb)
|
||||
{
|
||||
int err = 0;
|
||||
struct usX2Ydev *usX2Y = urb->context;
|
||||
struct us428ctls_sharedmem *us428ctls = usX2Y->us428ctls_sharedmem;
|
||||
struct usx2ydev *usx2y = urb->context;
|
||||
struct us428ctls_sharedmem *us428ctls = usx2y->us428ctls_sharedmem;
|
||||
|
||||
usX2Y->In04IntCalls++;
|
||||
usx2y->in04_int_calls++;
|
||||
|
||||
if (urb->status) {
|
||||
snd_printdd("Interrupt Pipe 4 came back with status=%i\n", urb->status);
|
||||
return;
|
||||
}
|
||||
|
||||
// printk("%i:0x%02X ", 8, (int)((unsigned char*)usX2Y->In04Buf)[8]); Master volume shows 0 here if fader is at max during boot ?!?
|
||||
// printk("%i:0x%02X ", 8, (int)((unsigned char*)usx2y->in04_buf)[8]); Master volume shows 0 here if fader is at max during boot ?!?
|
||||
if (us428ctls) {
|
||||
int diff = -1;
|
||||
if (-2 == us428ctls->CtlSnapShotLast) {
|
||||
if (-2 == us428ctls->ctl_snapshot_last) {
|
||||
diff = 0;
|
||||
memcpy(usX2Y->In04Last, usX2Y->In04Buf, sizeof(usX2Y->In04Last));
|
||||
us428ctls->CtlSnapShotLast = -1;
|
||||
memcpy(usx2y->in04_last, usx2y->in04_buf, sizeof(usx2y->in04_last));
|
||||
us428ctls->ctl_snapshot_last = -1;
|
||||
} else {
|
||||
int i;
|
||||
for (i = 0; i < 21; i++) {
|
||||
if (usX2Y->In04Last[i] != ((char*)usX2Y->In04Buf)[i]) {
|
||||
if (usx2y->in04_last[i] != ((char*)usx2y->in04_buf)[i]) {
|
||||
if (diff < 0)
|
||||
diff = i;
|
||||
usX2Y->In04Last[i] = ((char*)usX2Y->In04Buf)[i];
|
||||
usx2y->in04_last[i] = ((char*)usx2y->in04_buf)[i];
|
||||
}
|
||||
}
|
||||
}
|
||||
if (0 <= diff) {
|
||||
int n = us428ctls->CtlSnapShotLast + 1;
|
||||
if (n >= N_us428_ctl_BUFS || n < 0)
|
||||
int n = us428ctls->ctl_snapshot_last + 1;
|
||||
if (n >= N_US428_CTL_BUFS || n < 0)
|
||||
n = 0;
|
||||
memcpy(us428ctls->CtlSnapShot + n, usX2Y->In04Buf, sizeof(us428ctls->CtlSnapShot[0]));
|
||||
us428ctls->CtlSnapShotDiffersAt[n] = diff;
|
||||
us428ctls->CtlSnapShotLast = n;
|
||||
wake_up(&usX2Y->us428ctls_wait_queue_head);
|
||||
memcpy(us428ctls->ctl_snapshot + n, usx2y->in04_buf, sizeof(us428ctls->ctl_snapshot[0]));
|
||||
us428ctls->ctl_snapshot_differs_at[n] = diff;
|
||||
us428ctls->ctl_snapshot_last = n;
|
||||
wake_up(&usx2y->us428ctls_wait_queue_head);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (usX2Y->US04) {
|
||||
if (0 == usX2Y->US04->submitted)
|
||||
if (usx2y->us04) {
|
||||
if (0 == usx2y->us04->submitted)
|
||||
do {
|
||||
err = usb_submit_urb(usX2Y->US04->urb[usX2Y->US04->submitted++], GFP_ATOMIC);
|
||||
} while (!err && usX2Y->US04->submitted < usX2Y->US04->len);
|
||||
err = usb_submit_urb(usx2y->us04->urb[usx2y->us04->submitted++], GFP_ATOMIC);
|
||||
} while (!err && usx2y->us04->submitted < usx2y->us04->len);
|
||||
} else
|
||||
if (us428ctls && us428ctls->p4outLast >= 0 && us428ctls->p4outLast < N_us428_p4out_BUFS) {
|
||||
if (us428ctls->p4outLast != us428ctls->p4outSent) {
|
||||
int j, send = us428ctls->p4outSent + 1;
|
||||
if (send >= N_us428_p4out_BUFS)
|
||||
if (us428ctls && us428ctls->p4out_last >= 0 && us428ctls->p4out_last < N_US428_P4OUT_BUFS) {
|
||||
if (us428ctls->p4out_last != us428ctls->p4out_sent) {
|
||||
int j, send = us428ctls->p4out_sent + 1;
|
||||
if (send >= N_US428_P4OUT_BUFS)
|
||||
send = 0;
|
||||
for (j = 0; j < URBS_AsyncSeq && !err; ++j)
|
||||
if (0 == usX2Y->AS04.urb[j]->status) {
|
||||
for (j = 0; j < URBS_ASYNC_SEQ && !err; ++j)
|
||||
if (0 == usx2y->as04.urb[j]->status) {
|
||||
struct us428_p4out *p4out = us428ctls->p4out + send; // FIXME if more than 1 p4out is new, 1 gets lost.
|
||||
usb_fill_bulk_urb(usX2Y->AS04.urb[j], usX2Y->dev,
|
||||
usb_sndbulkpipe(usX2Y->dev, 0x04), &p4out->val.vol,
|
||||
p4out->type == eLT_Light ? sizeof(struct us428_lights) : 5,
|
||||
i_usX2Y_Out04Int, usX2Y);
|
||||
err = usb_submit_urb(usX2Y->AS04.urb[j], GFP_ATOMIC);
|
||||
us428ctls->p4outSent = send;
|
||||
usb_fill_bulk_urb(usx2y->as04.urb[j], usx2y->dev,
|
||||
usb_sndbulkpipe(usx2y->dev, 0x04), &p4out->val.vol,
|
||||
p4out->type == ELT_LIGHT ? sizeof(struct us428_lights) : 5,
|
||||
i_usx2y_out04_int, usx2y);
|
||||
err = usb_submit_urb(usx2y->as04.urb[j], GFP_ATOMIC);
|
||||
us428ctls->p4out_sent = send;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (err)
|
||||
snd_printk(KERN_ERR "In04Int() usb_submit_urb err=%i\n", err);
|
||||
snd_printk(KERN_ERR "in04_int() usb_submit_urb err=%i\n", err);
|
||||
|
||||
urb->dev = usX2Y->dev;
|
||||
urb->dev = usx2y->dev;
|
||||
usb_submit_urb(urb, GFP_ATOMIC);
|
||||
}
|
||||
|
||||
/*
|
||||
* Prepare some urbs
|
||||
*/
|
||||
int usX2Y_AsyncSeq04_init(struct usX2Ydev *usX2Y)
|
||||
int usx2y_async_seq04_init(struct usx2ydev *usx2y)
|
||||
{
|
||||
int err = 0,
|
||||
i;
|
||||
|
||||
usX2Y->AS04.buffer = kmalloc_array(URBS_AsyncSeq,
|
||||
URB_DataLen_AsyncSeq, GFP_KERNEL);
|
||||
if (NULL == usX2Y->AS04.buffer) {
|
||||
usx2y->as04.buffer = kmalloc_array(URBS_ASYNC_SEQ,
|
||||
URB_DATA_LEN_ASYNC_SEQ, GFP_KERNEL);
|
||||
if (NULL == usx2y->as04.buffer) {
|
||||
err = -ENOMEM;
|
||||
} else
|
||||
for (i = 0; i < URBS_AsyncSeq; ++i) {
|
||||
if (NULL == (usX2Y->AS04.urb[i] = usb_alloc_urb(0, GFP_KERNEL))) {
|
||||
for (i = 0; i < URBS_ASYNC_SEQ; ++i) {
|
||||
if (NULL == (usx2y->as04.urb[i] = usb_alloc_urb(0, GFP_KERNEL))) {
|
||||
err = -ENOMEM;
|
||||
break;
|
||||
}
|
||||
usb_fill_bulk_urb( usX2Y->AS04.urb[i], usX2Y->dev,
|
||||
usb_sndbulkpipe(usX2Y->dev, 0x04),
|
||||
usX2Y->AS04.buffer + URB_DataLen_AsyncSeq*i, 0,
|
||||
i_usX2Y_Out04Int, usX2Y
|
||||
usb_fill_bulk_urb( usx2y->as04.urb[i], usx2y->dev,
|
||||
usb_sndbulkpipe(usx2y->dev, 0x04),
|
||||
usx2y->as04.buffer + URB_DATA_LEN_ASYNC_SEQ*i, 0,
|
||||
i_usx2y_out04_int, usx2y
|
||||
);
|
||||
err = usb_urb_ep_type_check(usX2Y->AS04.urb[i]);
|
||||
err = usb_urb_ep_type_check(usx2y->as04.urb[i]);
|
||||
if (err < 0)
|
||||
break;
|
||||
}
|
||||
return err;
|
||||
}
|
||||
|
||||
int usX2Y_In04_init(struct usX2Ydev *usX2Y)
|
||||
int usx2y_in04_init(struct usx2ydev *usx2y)
|
||||
{
|
||||
if (! (usX2Y->In04urb = usb_alloc_urb(0, GFP_KERNEL)))
|
||||
if (! (usx2y->in04_urb = usb_alloc_urb(0, GFP_KERNEL)))
|
||||
return -ENOMEM;
|
||||
|
||||
if (! (usX2Y->In04Buf = kmalloc(21, GFP_KERNEL)))
|
||||
if (! (usx2y->in04_buf = kmalloc(21, GFP_KERNEL)))
|
||||
return -ENOMEM;
|
||||
|
||||
init_waitqueue_head(&usX2Y->In04WaitQueue);
|
||||
usb_fill_int_urb(usX2Y->In04urb, usX2Y->dev, usb_rcvintpipe(usX2Y->dev, 0x4),
|
||||
usX2Y->In04Buf, 21,
|
||||
i_usX2Y_In04Int, usX2Y,
|
||||
init_waitqueue_head(&usx2y->in04_wait_queue);
|
||||
usb_fill_int_urb(usx2y->in04_urb, usx2y->dev, usb_rcvintpipe(usx2y->dev, 0x4),
|
||||
usx2y->in04_buf, 21,
|
||||
i_usx2y_in04_int, usx2y,
|
||||
10);
|
||||
if (usb_urb_ep_type_check(usX2Y->In04urb))
|
||||
if (usb_urb_ep_type_check(usx2y->in04_urb))
|
||||
return -EINVAL;
|
||||
return usb_submit_urb(usX2Y->In04urb, GFP_KERNEL);
|
||||
return usb_submit_urb(usx2y->in04_urb, GFP_KERNEL);
|
||||
}
|
||||
|
||||
static void usX2Y_unlinkSeq(struct snd_usX2Y_AsyncSeq *S)
|
||||
static void usx2y_unlinkseq(struct snd_usx2y_async_seq *s)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < URBS_AsyncSeq; ++i) {
|
||||
usb_kill_urb(S->urb[i]);
|
||||
usb_free_urb(S->urb[i]);
|
||||
S->urb[i] = NULL;
|
||||
for (i = 0; i < URBS_ASYNC_SEQ; ++i) {
|
||||
usb_kill_urb(s->urb[i]);
|
||||
usb_free_urb(s->urb[i]);
|
||||
s->urb[i] = NULL;
|
||||
}
|
||||
kfree(S->buffer);
|
||||
kfree(s->buffer);
|
||||
}
|
||||
|
||||
|
||||
static const struct usb_device_id snd_usX2Y_usb_id_table[] = {
|
||||
static const struct usb_device_id snd_usx2y_usb_id_table[] = {
|
||||
{
|
||||
.match_flags = USB_DEVICE_ID_MATCH_DEVICE,
|
||||
.idVendor = 0x1604,
|
||||
@ -323,7 +323,7 @@ static const struct usb_device_id snd_usX2Y_usb_id_table[] = {
|
||||
{ /* terminator */ }
|
||||
};
|
||||
|
||||
static int usX2Y_create_card(struct usb_device *device,
|
||||
static int usx2y_create_card(struct usb_device *device,
|
||||
struct usb_interface *intf,
|
||||
struct snd_card **cardp)
|
||||
{
|
||||
@ -332,20 +332,20 @@ static int usX2Y_create_card(struct usb_device *device,
|
||||
int err;
|
||||
|
||||
for (dev = 0; dev < SNDRV_CARDS; ++dev)
|
||||
if (enable[dev] && !snd_usX2Y_card_used[dev])
|
||||
if (enable[dev] && !snd_usx2y_card_used[dev])
|
||||
break;
|
||||
if (dev >= SNDRV_CARDS)
|
||||
return -ENODEV;
|
||||
err = snd_card_new(&intf->dev, index[dev], id[dev], THIS_MODULE,
|
||||
sizeof(struct usX2Ydev), &card);
|
||||
sizeof(struct usx2ydev), &card);
|
||||
if (err < 0)
|
||||
return err;
|
||||
snd_usX2Y_card_used[usX2Y(card)->card_index = dev] = 1;
|
||||
card->private_free = snd_usX2Y_card_private_free;
|
||||
usX2Y(card)->dev = device;
|
||||
init_waitqueue_head(&usX2Y(card)->prepare_wait_queue);
|
||||
mutex_init(&usX2Y(card)->pcm_mutex);
|
||||
INIT_LIST_HEAD(&usX2Y(card)->midi_list);
|
||||
snd_usx2y_card_used[usx2y(card)->card_index = dev] = 1;
|
||||
card->private_free = snd_usx2y_card_private_free;
|
||||
usx2y(card)->dev = device;
|
||||
init_waitqueue_head(&usx2y(card)->prepare_wait_queue);
|
||||
mutex_init(&usx2y(card)->pcm_mutex);
|
||||
INIT_LIST_HEAD(&usx2y(card)->midi_list);
|
||||
strcpy(card->driver, "USB "NAME_ALLCAPS"");
|
||||
sprintf(card->shortname, "TASCAM "NAME_ALLCAPS"");
|
||||
sprintf(card->longname, "%s (%x:%x if %d at %03d/%03d)",
|
||||
@ -353,14 +353,14 @@ static int usX2Y_create_card(struct usb_device *device,
|
||||
le16_to_cpu(device->descriptor.idVendor),
|
||||
le16_to_cpu(device->descriptor.idProduct),
|
||||
0,//us428(card)->usbmidi.ifnum,
|
||||
usX2Y(card)->dev->bus->busnum, usX2Y(card)->dev->devnum
|
||||
usx2y(card)->dev->bus->busnum, usx2y(card)->dev->devnum
|
||||
);
|
||||
*cardp = card;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int usX2Y_usb_probe(struct usb_device *device,
|
||||
static int usx2y_usb_probe(struct usb_device *device,
|
||||
struct usb_interface *intf,
|
||||
const struct usb_device_id *device_id,
|
||||
struct snd_card **cardp)
|
||||
@ -375,10 +375,10 @@ static int usX2Y_usb_probe(struct usb_device *device,
|
||||
le16_to_cpu(device->descriptor.idProduct) != USB_ID_US428))
|
||||
return -EINVAL;
|
||||
|
||||
err = usX2Y_create_card(device, intf, &card);
|
||||
err = usx2y_create_card(device, intf, &card);
|
||||
if (err < 0)
|
||||
return err;
|
||||
if ((err = usX2Y_hwdep_new(card, device)) < 0 ||
|
||||
if ((err = usx2y_hwdep_new(card, device)) < 0 ||
|
||||
(err = snd_card_register(card)) < 0) {
|
||||
snd_card_free(card);
|
||||
return err;
|
||||
@ -390,64 +390,64 @@ static int usX2Y_usb_probe(struct usb_device *device,
|
||||
/*
|
||||
* new 2.5 USB kernel API
|
||||
*/
|
||||
static int snd_usX2Y_probe(struct usb_interface *intf, const struct usb_device_id *id)
|
||||
static int snd_usx2y_probe(struct usb_interface *intf, const struct usb_device_id *id)
|
||||
{
|
||||
struct snd_card *card;
|
||||
int err;
|
||||
|
||||
err = usX2Y_usb_probe(interface_to_usbdev(intf), intf, id, &card);
|
||||
err = usx2y_usb_probe(interface_to_usbdev(intf), intf, id, &card);
|
||||
if (err < 0)
|
||||
return err;
|
||||
dev_set_drvdata(&intf->dev, card);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void snd_usX2Y_disconnect(struct usb_interface *intf)
|
||||
static void snd_usx2y_disconnect(struct usb_interface *intf)
|
||||
{
|
||||
usX2Y_usb_disconnect(interface_to_usbdev(intf),
|
||||
usx2y_usb_disconnect(interface_to_usbdev(intf),
|
||||
usb_get_intfdata(intf));
|
||||
}
|
||||
|
||||
MODULE_DEVICE_TABLE(usb, snd_usX2Y_usb_id_table);
|
||||
static struct usb_driver snd_usX2Y_usb_driver = {
|
||||
MODULE_DEVICE_TABLE(usb, snd_usx2y_usb_id_table);
|
||||
static struct usb_driver snd_usx2y_usb_driver = {
|
||||
.name = "snd-usb-usx2y",
|
||||
.probe = snd_usX2Y_probe,
|
||||
.disconnect = snd_usX2Y_disconnect,
|
||||
.id_table = snd_usX2Y_usb_id_table,
|
||||
.probe = snd_usx2y_probe,
|
||||
.disconnect = snd_usx2y_disconnect,
|
||||
.id_table = snd_usx2y_usb_id_table,
|
||||
};
|
||||
|
||||
static void snd_usX2Y_card_private_free(struct snd_card *card)
|
||||
static void snd_usx2y_card_private_free(struct snd_card *card)
|
||||
{
|
||||
kfree(usX2Y(card)->In04Buf);
|
||||
usb_free_urb(usX2Y(card)->In04urb);
|
||||
if (usX2Y(card)->us428ctls_sharedmem)
|
||||
free_pages_exact(usX2Y(card)->us428ctls_sharedmem,
|
||||
sizeof(*usX2Y(card)->us428ctls_sharedmem));
|
||||
if (usX2Y(card)->card_index >= 0 && usX2Y(card)->card_index < SNDRV_CARDS)
|
||||
snd_usX2Y_card_used[usX2Y(card)->card_index] = 0;
|
||||
kfree(usx2y(card)->in04_buf);
|
||||
usb_free_urb(usx2y(card)->in04_urb);
|
||||
if (usx2y(card)->us428ctls_sharedmem)
|
||||
free_pages_exact(usx2y(card)->us428ctls_sharedmem,
|
||||
sizeof(*usx2y(card)->us428ctls_sharedmem));
|
||||
if (usx2y(card)->card_index >= 0 && usx2y(card)->card_index < SNDRV_CARDS)
|
||||
snd_usx2y_card_used[usx2y(card)->card_index] = 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Frees the device.
|
||||
*/
|
||||
static void usX2Y_usb_disconnect(struct usb_device *device, void* ptr)
|
||||
static void usx2y_usb_disconnect(struct usb_device *device, void* ptr)
|
||||
{
|
||||
if (ptr) {
|
||||
struct snd_card *card = ptr;
|
||||
struct usX2Ydev *usX2Y = usX2Y(card);
|
||||
struct usx2ydev *usx2y = usx2y(card);
|
||||
struct list_head *p;
|
||||
usX2Y->chip_status = USX2Y_STAT_CHIP_HUP;
|
||||
usX2Y_unlinkSeq(&usX2Y->AS04);
|
||||
usb_kill_urb(usX2Y->In04urb);
|
||||
usx2y->chip_status = USX2Y_STAT_CHIP_HUP;
|
||||
usx2y_unlinkseq(&usx2y->as04);
|
||||
usb_kill_urb(usx2y->in04_urb);
|
||||
snd_card_disconnect(card);
|
||||
/* release the midi resources */
|
||||
list_for_each(p, &usX2Y->midi_list) {
|
||||
list_for_each(p, &usx2y->midi_list) {
|
||||
snd_usbmidi_disconnect(p);
|
||||
}
|
||||
if (usX2Y->us428ctls_sharedmem)
|
||||
wake_up(&usX2Y->us428ctls_wait_queue_head);
|
||||
if (usx2y->us428ctls_sharedmem)
|
||||
wake_up(&usx2y->us428ctls_wait_queue_head);
|
||||
snd_card_free(card);
|
||||
}
|
||||
}
|
||||
|
||||
module_usb_driver(snd_usX2Y_usb_driver);
|
||||
module_usb_driver(snd_usx2y_usb_driver);
|
||||
|
@ -8,14 +8,14 @@
|
||||
#define NRURBS 2
|
||||
|
||||
|
||||
#define URBS_AsyncSeq 10
|
||||
#define URB_DataLen_AsyncSeq 32
|
||||
struct snd_usX2Y_AsyncSeq {
|
||||
struct urb *urb[URBS_AsyncSeq];
|
||||
#define URBS_ASYNC_SEQ 10
|
||||
#define URB_DATA_LEN_ASYNC_SEQ 32
|
||||
struct snd_usx2y_async_seq {
|
||||
struct urb *urb[URBS_ASYNC_SEQ];
|
||||
char *buffer;
|
||||
};
|
||||
|
||||
struct snd_usX2Y_urbSeq {
|
||||
struct snd_usx2y_urb_seq {
|
||||
int submitted;
|
||||
int len;
|
||||
struct urb *urb[];
|
||||
@ -23,17 +23,17 @@ struct snd_usX2Y_urbSeq {
|
||||
|
||||
#include "usx2yhwdeppcm.h"
|
||||
|
||||
struct usX2Ydev {
|
||||
struct usx2ydev {
|
||||
struct usb_device *dev;
|
||||
int card_index;
|
||||
int stride;
|
||||
struct urb *In04urb;
|
||||
void *In04Buf;
|
||||
char In04Last[24];
|
||||
unsigned In04IntCalls;
|
||||
struct snd_usX2Y_urbSeq *US04;
|
||||
wait_queue_head_t In04WaitQueue;
|
||||
struct snd_usX2Y_AsyncSeq AS04;
|
||||
struct urb *in04_urb;
|
||||
void *in04_buf;
|
||||
char in04_last[24];
|
||||
unsigned in04_int_calls;
|
||||
struct snd_usx2y_urb_seq *us04;
|
||||
wait_queue_head_t in04_wait_queue;
|
||||
struct snd_usx2y_async_seq as04;
|
||||
unsigned int rate,
|
||||
format;
|
||||
int chip_status;
|
||||
@ -41,9 +41,9 @@ struct usX2Ydev {
|
||||
struct us428ctls_sharedmem *us428ctls_sharedmem;
|
||||
int wait_iso_frame;
|
||||
wait_queue_head_t us428ctls_wait_queue_head;
|
||||
struct snd_usX2Y_hwdep_pcm_shm *hwdep_pcm_shm;
|
||||
struct snd_usX2Y_substream *subs[4];
|
||||
struct snd_usX2Y_substream * volatile prepare_subs;
|
||||
struct snd_usx2y_hwdep_pcm_shm *hwdep_pcm_shm;
|
||||
struct snd_usx2y_substream *subs[4];
|
||||
struct snd_usx2y_substream * volatile prepare_subs;
|
||||
wait_queue_head_t prepare_wait_queue;
|
||||
struct list_head midi_list;
|
||||
struct list_head pcm_list;
|
||||
@ -51,21 +51,21 @@ struct usX2Ydev {
|
||||
};
|
||||
|
||||
|
||||
struct snd_usX2Y_substream {
|
||||
struct usX2Ydev *usX2Y;
|
||||
struct snd_usx2y_substream {
|
||||
struct usx2ydev *usx2y;
|
||||
struct snd_pcm_substream *pcm_substream;
|
||||
|
||||
int endpoint;
|
||||
unsigned int maxpacksize; /* max packet size in bytes */
|
||||
|
||||
atomic_t state;
|
||||
#define state_STOPPED 0
|
||||
#define state_STARTING1 1
|
||||
#define state_STARTING2 2
|
||||
#define state_STARTING3 3
|
||||
#define state_PREPARED 4
|
||||
#define state_PRERUNNING 6
|
||||
#define state_RUNNING 8
|
||||
#define STATE_STOPPED 0
|
||||
#define STATE_STARTING1 1
|
||||
#define STATE_STARTING2 2
|
||||
#define STATE_STARTING3 3
|
||||
#define STATE_PREPARED 4
|
||||
#define STATE_PRERUNNING 6
|
||||
#define STATE_RUNNING 8
|
||||
|
||||
int hwptr; /* free frame position in the buffer (only for playback) */
|
||||
int hwptr_done; /* processed frame position in the buffer */
|
||||
@ -77,12 +77,12 @@ struct snd_usX2Y_substream {
|
||||
};
|
||||
|
||||
|
||||
#define usX2Y(c) ((struct usX2Ydev *)(c)->private_data)
|
||||
#define usx2y(c) ((struct usx2ydev *)(c)->private_data)
|
||||
|
||||
int usX2Y_audio_create(struct snd_card *card);
|
||||
int usx2y_audio_create(struct snd_card *card);
|
||||
|
||||
int usX2Y_AsyncSeq04_init(struct usX2Ydev *usX2Y);
|
||||
int usX2Y_In04_init(struct usX2Ydev *usX2Y);
|
||||
int usx2y_async_seq04_init(struct usx2ydev *usx2y);
|
||||
int usx2y_in04_init(struct usx2ydev *usx2y);
|
||||
|
||||
#define NAME_ALLCAPS "US-X2Y"
|
||||
|
||||
|
@ -54,13 +54,13 @@
|
||||
#endif
|
||||
|
||||
|
||||
static int usX2Y_urb_capt_retire(struct snd_usX2Y_substream *subs)
|
||||
static int usx2y_urb_capt_retire(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
struct urb *urb = subs->completed_urb;
|
||||
struct snd_pcm_runtime *runtime = subs->pcm_substream->runtime;
|
||||
unsigned char *cp;
|
||||
int i, len, lens = 0, hwptr_done = subs->hwptr_done;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
|
||||
for (i = 0; i < nr_of_packs(); i++) {
|
||||
cp = (unsigned char*)urb->transfer_buffer + urb->iso_frame_desc[i].offset;
|
||||
@ -70,7 +70,7 @@ static int usX2Y_urb_capt_retire(struct snd_usX2Y_substream *subs)
|
||||
urb->iso_frame_desc[i].status);
|
||||
return urb->iso_frame_desc[i].status;
|
||||
}
|
||||
len = urb->iso_frame_desc[i].actual_length / usX2Y->stride;
|
||||
len = urb->iso_frame_desc[i].actual_length / usx2y->stride;
|
||||
if (! len) {
|
||||
snd_printd("0 == len ERROR!\n");
|
||||
continue;
|
||||
@ -79,12 +79,12 @@ static int usX2Y_urb_capt_retire(struct snd_usX2Y_substream *subs)
|
||||
/* copy a data chunk */
|
||||
if ((hwptr_done + len) > runtime->buffer_size) {
|
||||
int cnt = runtime->buffer_size - hwptr_done;
|
||||
int blen = cnt * usX2Y->stride;
|
||||
memcpy(runtime->dma_area + hwptr_done * usX2Y->stride, cp, blen);
|
||||
memcpy(runtime->dma_area, cp + blen, len * usX2Y->stride - blen);
|
||||
int blen = cnt * usx2y->stride;
|
||||
memcpy(runtime->dma_area + hwptr_done * usx2y->stride, cp, blen);
|
||||
memcpy(runtime->dma_area, cp + blen, len * usx2y->stride - blen);
|
||||
} else {
|
||||
memcpy(runtime->dma_area + hwptr_done * usX2Y->stride, cp,
|
||||
len * usX2Y->stride);
|
||||
memcpy(runtime->dma_area + hwptr_done * usx2y->stride, cp,
|
||||
len * usx2y->stride);
|
||||
}
|
||||
lens += len;
|
||||
if ((hwptr_done += len) >= runtime->buffer_size)
|
||||
@ -110,18 +110,18 @@ static int usX2Y_urb_capt_retire(struct snd_usX2Y_substream *subs)
|
||||
* it directly from the buffer. thus the data is once copied to
|
||||
* a temporary buffer and urb points to that.
|
||||
*/
|
||||
static int usX2Y_urb_play_prepare(struct snd_usX2Y_substream *subs,
|
||||
static int usx2y_urb_play_prepare(struct snd_usx2y_substream *subs,
|
||||
struct urb *cap_urb,
|
||||
struct urb *urb)
|
||||
{
|
||||
int count, counts, pack;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
struct snd_pcm_runtime *runtime = subs->pcm_substream->runtime;
|
||||
|
||||
count = 0;
|
||||
for (pack = 0; pack < nr_of_packs(); pack++) {
|
||||
/* calculate the size of a packet */
|
||||
counts = cap_urb->iso_frame_desc[pack].actual_length / usX2Y->stride;
|
||||
counts = cap_urb->iso_frame_desc[pack].actual_length / usx2y->stride;
|
||||
count += counts;
|
||||
if (counts < 43 || counts > 50) {
|
||||
snd_printk(KERN_ERR "should not be here with counts=%i\n", counts);
|
||||
@ -134,7 +134,7 @@ static int usX2Y_urb_play_prepare(struct snd_usX2Y_substream *subs,
|
||||
0;
|
||||
urb->iso_frame_desc[pack].length = cap_urb->iso_frame_desc[pack].actual_length;
|
||||
}
|
||||
if (atomic_read(&subs->state) >= state_PRERUNNING)
|
||||
if (atomic_read(&subs->state) >= STATE_PRERUNNING)
|
||||
if (subs->hwptr + count > runtime->buffer_size) {
|
||||
/* err, the transferred area goes over buffer boundary.
|
||||
* copy the data to the temp buffer.
|
||||
@ -143,20 +143,20 @@ static int usX2Y_urb_play_prepare(struct snd_usX2Y_substream *subs,
|
||||
len = runtime->buffer_size - subs->hwptr;
|
||||
urb->transfer_buffer = subs->tmpbuf;
|
||||
memcpy(subs->tmpbuf, runtime->dma_area +
|
||||
subs->hwptr * usX2Y->stride, len * usX2Y->stride);
|
||||
memcpy(subs->tmpbuf + len * usX2Y->stride,
|
||||
runtime->dma_area, (count - len) * usX2Y->stride);
|
||||
subs->hwptr * usx2y->stride, len * usx2y->stride);
|
||||
memcpy(subs->tmpbuf + len * usx2y->stride,
|
||||
runtime->dma_area, (count - len) * usx2y->stride);
|
||||
subs->hwptr += count;
|
||||
subs->hwptr -= runtime->buffer_size;
|
||||
} else {
|
||||
/* set the buffer pointer */
|
||||
urb->transfer_buffer = runtime->dma_area + subs->hwptr * usX2Y->stride;
|
||||
urb->transfer_buffer = runtime->dma_area + subs->hwptr * usx2y->stride;
|
||||
if ((subs->hwptr += count) >= runtime->buffer_size)
|
||||
subs->hwptr -= runtime->buffer_size;
|
||||
}
|
||||
else
|
||||
urb->transfer_buffer = subs->tmpbuf;
|
||||
urb->transfer_buffer_length = count * usX2Y->stride;
|
||||
urb->transfer_buffer_length = count * usx2y->stride;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -165,10 +165,10 @@ static int usX2Y_urb_play_prepare(struct snd_usX2Y_substream *subs,
|
||||
*
|
||||
* update the current position and call callback if a period is processed.
|
||||
*/
|
||||
static void usX2Y_urb_play_retire(struct snd_usX2Y_substream *subs, struct urb *urb)
|
||||
static void usx2y_urb_play_retire(struct snd_usx2y_substream *subs, struct urb *urb)
|
||||
{
|
||||
struct snd_pcm_runtime *runtime = subs->pcm_substream->runtime;
|
||||
int len = urb->actual_length / subs->usX2Y->stride;
|
||||
int len = urb->actual_length / subs->usx2y->stride;
|
||||
|
||||
subs->transfer_done += len;
|
||||
subs->hwptr_done += len;
|
||||
@ -180,14 +180,14 @@ static void usX2Y_urb_play_retire(struct snd_usX2Y_substream *subs, struct urb *
|
||||
}
|
||||
}
|
||||
|
||||
static int usX2Y_urb_submit(struct snd_usX2Y_substream *subs, struct urb *urb, int frame)
|
||||
static int usx2y_urb_submit(struct snd_usx2y_substream *subs, struct urb *urb, int frame)
|
||||
{
|
||||
int err;
|
||||
if (!urb)
|
||||
return -ENODEV;
|
||||
urb->start_frame = (frame + NRURBS * nr_of_packs()); // let hcd do rollover sanity checks
|
||||
urb->hcpriv = NULL;
|
||||
urb->dev = subs->usX2Y->dev; /* we need to set this at each time */
|
||||
urb->dev = subs->usx2y->dev; /* we need to set this at each time */
|
||||
if ((err = usb_submit_urb(urb, GFP_ATOMIC)) < 0) {
|
||||
snd_printk(KERN_ERR "usb_submit_urb() returned %i\n", err);
|
||||
return err;
|
||||
@ -195,8 +195,8 @@ static int usX2Y_urb_submit(struct snd_usX2Y_substream *subs, struct urb *urb, i
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline int usX2Y_usbframe_complete(struct snd_usX2Y_substream *capsubs,
|
||||
struct snd_usX2Y_substream *playbacksubs,
|
||||
static inline int usx2y_usbframe_complete(struct snd_usx2y_substream *capsubs,
|
||||
struct snd_usx2y_substream *playbacksubs,
|
||||
int frame)
|
||||
{
|
||||
int err, state;
|
||||
@ -204,25 +204,25 @@ static inline int usX2Y_usbframe_complete(struct snd_usX2Y_substream *capsubs,
|
||||
|
||||
state = atomic_read(&playbacksubs->state);
|
||||
if (NULL != urb) {
|
||||
if (state == state_RUNNING)
|
||||
usX2Y_urb_play_retire(playbacksubs, urb);
|
||||
else if (state >= state_PRERUNNING)
|
||||
if (state == STATE_RUNNING)
|
||||
usx2y_urb_play_retire(playbacksubs, urb);
|
||||
else if (state >= STATE_PRERUNNING)
|
||||
atomic_inc(&playbacksubs->state);
|
||||
} else {
|
||||
switch (state) {
|
||||
case state_STARTING1:
|
||||
case STATE_STARTING1:
|
||||
urb = playbacksubs->urb[0];
|
||||
atomic_inc(&playbacksubs->state);
|
||||
break;
|
||||
case state_STARTING2:
|
||||
case STATE_STARTING2:
|
||||
urb = playbacksubs->urb[1];
|
||||
atomic_inc(&playbacksubs->state);
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (urb) {
|
||||
if ((err = usX2Y_urb_play_prepare(playbacksubs, capsubs->completed_urb, urb)) ||
|
||||
(err = usX2Y_urb_submit(playbacksubs, urb, frame))) {
|
||||
if ((err = usx2y_urb_play_prepare(playbacksubs, capsubs->completed_urb, urb)) ||
|
||||
(err = usx2y_urb_submit(playbacksubs, urb, frame))) {
|
||||
return err;
|
||||
}
|
||||
}
|
||||
@ -230,13 +230,13 @@ static inline int usX2Y_usbframe_complete(struct snd_usX2Y_substream *capsubs,
|
||||
playbacksubs->completed_urb = NULL;
|
||||
|
||||
state = atomic_read(&capsubs->state);
|
||||
if (state >= state_PREPARED) {
|
||||
if (state == state_RUNNING) {
|
||||
if ((err = usX2Y_urb_capt_retire(capsubs)))
|
||||
if (state >= STATE_PREPARED) {
|
||||
if (state == STATE_RUNNING) {
|
||||
if ((err = usx2y_urb_capt_retire(capsubs)))
|
||||
return err;
|
||||
} else if (state >= state_PRERUNNING)
|
||||
} else if (state >= STATE_PRERUNNING)
|
||||
atomic_inc(&capsubs->state);
|
||||
if ((err = usX2Y_urb_submit(capsubs, capsubs->completed_urb, frame)))
|
||||
if ((err = usx2y_urb_submit(capsubs, capsubs->completed_urb, frame)))
|
||||
return err;
|
||||
}
|
||||
capsubs->completed_urb = NULL;
|
||||
@ -244,21 +244,21 @@ static inline int usX2Y_usbframe_complete(struct snd_usX2Y_substream *capsubs,
|
||||
}
|
||||
|
||||
|
||||
static void usX2Y_clients_stop(struct usX2Ydev *usX2Y)
|
||||
static void usx2y_clients_stop(struct usx2ydev *usx2y)
|
||||
{
|
||||
int s, u;
|
||||
|
||||
for (s = 0; s < 4; s++) {
|
||||
struct snd_usX2Y_substream *subs = usX2Y->subs[s];
|
||||
struct snd_usx2y_substream *subs = usx2y->subs[s];
|
||||
if (subs) {
|
||||
snd_printdd("%i %p state=%i\n", s, subs, atomic_read(&subs->state));
|
||||
atomic_set(&subs->state, state_STOPPED);
|
||||
atomic_set(&subs->state, STATE_STOPPED);
|
||||
}
|
||||
}
|
||||
for (s = 0; s < 4; s++) {
|
||||
struct snd_usX2Y_substream *subs = usX2Y->subs[s];
|
||||
struct snd_usx2y_substream *subs = usx2y->subs[s];
|
||||
if (subs) {
|
||||
if (atomic_read(&subs->state) >= state_PRERUNNING)
|
||||
if (atomic_read(&subs->state) >= STATE_PRERUNNING)
|
||||
snd_pcm_stop_xrun(subs->pcm_substream);
|
||||
for (u = 0; u < NRURBS; u++) {
|
||||
struct urb *urb = subs->urb[u];
|
||||
@ -268,60 +268,60 @@ static void usX2Y_clients_stop(struct usX2Ydev *usX2Y)
|
||||
}
|
||||
}
|
||||
}
|
||||
usX2Y->prepare_subs = NULL;
|
||||
wake_up(&usX2Y->prepare_wait_queue);
|
||||
usx2y->prepare_subs = NULL;
|
||||
wake_up(&usx2y->prepare_wait_queue);
|
||||
}
|
||||
|
||||
static void usX2Y_error_urb_status(struct usX2Ydev *usX2Y,
|
||||
struct snd_usX2Y_substream *subs, struct urb *urb)
|
||||
static void usx2y_error_urb_status(struct usx2ydev *usx2y,
|
||||
struct snd_usx2y_substream *subs, struct urb *urb)
|
||||
{
|
||||
snd_printk(KERN_ERR "ep=%i stalled with status=%i\n", subs->endpoint, urb->status);
|
||||
urb->status = 0;
|
||||
usX2Y_clients_stop(usX2Y);
|
||||
usx2y_clients_stop(usx2y);
|
||||
}
|
||||
|
||||
static void i_usX2Y_urb_complete(struct urb *urb)
|
||||
static void i_usx2y_urb_complete(struct urb *urb)
|
||||
{
|
||||
struct snd_usX2Y_substream *subs = urb->context;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct snd_usx2y_substream *subs = urb->context;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
|
||||
if (unlikely(atomic_read(&subs->state) < state_PREPARED)) {
|
||||
if (unlikely(atomic_read(&subs->state) < STATE_PREPARED)) {
|
||||
snd_printdd("hcd_frame=%i ep=%i%s status=%i start_frame=%i\n",
|
||||
usb_get_current_frame_number(usX2Y->dev),
|
||||
usb_get_current_frame_number(usx2y->dev),
|
||||
subs->endpoint, usb_pipein(urb->pipe) ? "in" : "out",
|
||||
urb->status, urb->start_frame);
|
||||
return;
|
||||
}
|
||||
if (unlikely(urb->status)) {
|
||||
usX2Y_error_urb_status(usX2Y, subs, urb);
|
||||
usx2y_error_urb_status(usx2y, subs, urb);
|
||||
return;
|
||||
}
|
||||
|
||||
subs->completed_urb = urb;
|
||||
|
||||
{
|
||||
struct snd_usX2Y_substream *capsubs = usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE],
|
||||
*playbacksubs = usX2Y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
struct snd_usx2y_substream *capsubs = usx2y->subs[SNDRV_PCM_STREAM_CAPTURE],
|
||||
*playbacksubs = usx2y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
if (capsubs->completed_urb &&
|
||||
atomic_read(&capsubs->state) >= state_PREPARED &&
|
||||
atomic_read(&capsubs->state) >= STATE_PREPARED &&
|
||||
(playbacksubs->completed_urb ||
|
||||
atomic_read(&playbacksubs->state) < state_PREPARED)) {
|
||||
if (!usX2Y_usbframe_complete(capsubs, playbacksubs, urb->start_frame))
|
||||
usX2Y->wait_iso_frame += nr_of_packs();
|
||||
atomic_read(&playbacksubs->state) < STATE_PREPARED)) {
|
||||
if (!usx2y_usbframe_complete(capsubs, playbacksubs, urb->start_frame))
|
||||
usx2y->wait_iso_frame += nr_of_packs();
|
||||
else {
|
||||
snd_printdd("\n");
|
||||
usX2Y_clients_stop(usX2Y);
|
||||
usx2y_clients_stop(usx2y);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void usX2Y_urbs_set_complete(struct usX2Ydev * usX2Y,
|
||||
static void usx2y_urbs_set_complete(struct usx2ydev * usx2y,
|
||||
void (*complete)(struct urb *))
|
||||
{
|
||||
int s, u;
|
||||
for (s = 0; s < 4; s++) {
|
||||
struct snd_usX2Y_substream *subs = usX2Y->subs[s];
|
||||
struct snd_usx2y_substream *subs = usx2y->subs[s];
|
||||
if (NULL != subs)
|
||||
for (u = 0; u < NRURBS; u++) {
|
||||
struct urb * urb = subs->urb[u];
|
||||
@ -331,30 +331,30 @@ static void usX2Y_urbs_set_complete(struct usX2Ydev * usX2Y,
|
||||
}
|
||||
}
|
||||
|
||||
static void usX2Y_subs_startup_finish(struct usX2Ydev * usX2Y)
|
||||
static void usx2y_subs_startup_finish(struct usx2ydev * usx2y)
|
||||
{
|
||||
usX2Y_urbs_set_complete(usX2Y, i_usX2Y_urb_complete);
|
||||
usX2Y->prepare_subs = NULL;
|
||||
usx2y_urbs_set_complete(usx2y, i_usx2y_urb_complete);
|
||||
usx2y->prepare_subs = NULL;
|
||||
}
|
||||
|
||||
static void i_usX2Y_subs_startup(struct urb *urb)
|
||||
static void i_usx2y_subs_startup(struct urb *urb)
|
||||
{
|
||||
struct snd_usX2Y_substream *subs = urb->context;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct snd_usX2Y_substream *prepare_subs = usX2Y->prepare_subs;
|
||||
struct snd_usx2y_substream *subs = urb->context;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
struct snd_usx2y_substream *prepare_subs = usx2y->prepare_subs;
|
||||
if (NULL != prepare_subs)
|
||||
if (urb->start_frame == prepare_subs->urb[0]->start_frame) {
|
||||
usX2Y_subs_startup_finish(usX2Y);
|
||||
usx2y_subs_startup_finish(usx2y);
|
||||
atomic_inc(&prepare_subs->state);
|
||||
wake_up(&usX2Y->prepare_wait_queue);
|
||||
wake_up(&usx2y->prepare_wait_queue);
|
||||
}
|
||||
|
||||
i_usX2Y_urb_complete(urb);
|
||||
i_usx2y_urb_complete(urb);
|
||||
}
|
||||
|
||||
static void usX2Y_subs_prepare(struct snd_usX2Y_substream *subs)
|
||||
static void usx2y_subs_prepare(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
snd_printdd("usX2Y_substream_prepare(%p) ep=%i urb0=%p urb1=%p\n",
|
||||
snd_printdd("usx2y_substream_prepare(%p) ep=%i urb0=%p urb1=%p\n",
|
||||
subs, subs->endpoint, subs->urb[0], subs->urb[1]);
|
||||
/* reset the pointer */
|
||||
subs->hwptr = 0;
|
||||
@ -363,7 +363,7 @@ static void usX2Y_subs_prepare(struct snd_usX2Y_substream *subs)
|
||||
}
|
||||
|
||||
|
||||
static void usX2Y_urb_release(struct urb **urb, int free_tb)
|
||||
static void usx2y_urb_release(struct urb **urb, int free_tb)
|
||||
{
|
||||
if (*urb) {
|
||||
usb_kill_urb(*urb);
|
||||
@ -376,13 +376,13 @@ static void usX2Y_urb_release(struct urb **urb, int free_tb)
|
||||
/*
|
||||
* release a substreams urbs
|
||||
*/
|
||||
static void usX2Y_urbs_release(struct snd_usX2Y_substream *subs)
|
||||
static void usx2y_urbs_release(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
int i;
|
||||
snd_printdd("usX2Y_urbs_release() %i\n", subs->endpoint);
|
||||
snd_printdd("usx2y_urbs_release() %i\n", subs->endpoint);
|
||||
for (i = 0; i < NRURBS; i++)
|
||||
usX2Y_urb_release(subs->urb + i,
|
||||
subs != subs->usX2Y->subs[SNDRV_PCM_STREAM_PLAYBACK]);
|
||||
usx2y_urb_release(subs->urb + i,
|
||||
subs != subs->usx2y->subs[SNDRV_PCM_STREAM_PLAYBACK]);
|
||||
|
||||
kfree(subs->tmpbuf);
|
||||
subs->tmpbuf = NULL;
|
||||
@ -390,12 +390,12 @@ static void usX2Y_urbs_release(struct snd_usX2Y_substream *subs)
|
||||
/*
|
||||
* initialize a substream's urbs
|
||||
*/
|
||||
static int usX2Y_urbs_allocate(struct snd_usX2Y_substream *subs)
|
||||
static int usx2y_urbs_allocate(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
int i;
|
||||
unsigned int pipe;
|
||||
int is_playback = subs == subs->usX2Y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
struct usb_device *dev = subs->usX2Y->dev;
|
||||
int is_playback = subs == subs->usx2y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
struct usb_device *dev = subs->usx2y->dev;
|
||||
|
||||
pipe = is_playback ? usb_sndisocpipe(dev, subs->endpoint) :
|
||||
usb_rcvisocpipe(dev, subs->endpoint);
|
||||
@ -417,7 +417,7 @@ static int usX2Y_urbs_allocate(struct snd_usX2Y_substream *subs)
|
||||
}
|
||||
*purb = usb_alloc_urb(nr_of_packs(), GFP_KERNEL);
|
||||
if (NULL == *purb) {
|
||||
usX2Y_urbs_release(subs);
|
||||
usx2y_urbs_release(subs);
|
||||
return -ENOMEM;
|
||||
}
|
||||
if (!is_playback && !(*purb)->transfer_buffer) {
|
||||
@ -426,7 +426,7 @@ static int usX2Y_urbs_allocate(struct snd_usX2Y_substream *subs)
|
||||
kmalloc_array(subs->maxpacksize,
|
||||
nr_of_packs(), GFP_KERNEL);
|
||||
if (NULL == (*purb)->transfer_buffer) {
|
||||
usX2Y_urbs_release(subs);
|
||||
usx2y_urbs_release(subs);
|
||||
return -ENOMEM;
|
||||
}
|
||||
}
|
||||
@ -435,43 +435,43 @@ static int usX2Y_urbs_allocate(struct snd_usX2Y_substream *subs)
|
||||
(*purb)->number_of_packets = nr_of_packs();
|
||||
(*purb)->context = subs;
|
||||
(*purb)->interval = 1;
|
||||
(*purb)->complete = i_usX2Y_subs_startup;
|
||||
(*purb)->complete = i_usx2y_subs_startup;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void usX2Y_subs_startup(struct snd_usX2Y_substream *subs)
|
||||
static void usx2y_subs_startup(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
usX2Y->prepare_subs = subs;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
usx2y->prepare_subs = subs;
|
||||
subs->urb[0]->start_frame = -1;
|
||||
wmb();
|
||||
usX2Y_urbs_set_complete(usX2Y, i_usX2Y_subs_startup);
|
||||
usx2y_urbs_set_complete(usx2y, i_usx2y_subs_startup);
|
||||
}
|
||||
|
||||
static int usX2Y_urbs_start(struct snd_usX2Y_substream *subs)
|
||||
static int usx2y_urbs_start(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
int i, err;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
|
||||
if ((err = usX2Y_urbs_allocate(subs)) < 0)
|
||||
if ((err = usx2y_urbs_allocate(subs)) < 0)
|
||||
return err;
|
||||
subs->completed_urb = NULL;
|
||||
for (i = 0; i < 4; i++) {
|
||||
struct snd_usX2Y_substream *subs = usX2Y->subs[i];
|
||||
if (subs != NULL && atomic_read(&subs->state) >= state_PREPARED)
|
||||
struct snd_usx2y_substream *subs = usx2y->subs[i];
|
||||
if (subs != NULL && atomic_read(&subs->state) >= STATE_PREPARED)
|
||||
goto start;
|
||||
}
|
||||
|
||||
start:
|
||||
usX2Y_subs_startup(subs);
|
||||
usx2y_subs_startup(subs);
|
||||
for (i = 0; i < NRURBS; i++) {
|
||||
struct urb *urb = subs->urb[i];
|
||||
if (usb_pipein(urb->pipe)) {
|
||||
unsigned long pack;
|
||||
if (0 == i)
|
||||
atomic_set(&subs->state, state_STARTING3);
|
||||
urb->dev = usX2Y->dev;
|
||||
atomic_set(&subs->state, STATE_STARTING3);
|
||||
urb->dev = usx2y->dev;
|
||||
for (pack = 0; pack < nr_of_packs(); pack++) {
|
||||
urb->iso_frame_desc[pack].offset = subs->maxpacksize * pack;
|
||||
urb->iso_frame_desc[pack].length = subs->maxpacksize;
|
||||
@ -483,22 +483,22 @@ static int usX2Y_urbs_start(struct snd_usX2Y_substream *subs)
|
||||
goto cleanup;
|
||||
} else
|
||||
if (i == 0)
|
||||
usX2Y->wait_iso_frame = urb->start_frame;
|
||||
usx2y->wait_iso_frame = urb->start_frame;
|
||||
urb->transfer_flags = 0;
|
||||
} else {
|
||||
atomic_set(&subs->state, state_STARTING1);
|
||||
atomic_set(&subs->state, STATE_STARTING1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
err = 0;
|
||||
wait_event(usX2Y->prepare_wait_queue, NULL == usX2Y->prepare_subs);
|
||||
if (atomic_read(&subs->state) != state_PREPARED)
|
||||
wait_event(usx2y->prepare_wait_queue, NULL == usx2y->prepare_subs);
|
||||
if (atomic_read(&subs->state) != STATE_PREPARED)
|
||||
err = -EPIPE;
|
||||
|
||||
cleanup:
|
||||
if (err) {
|
||||
usX2Y_subs_startup_finish(usX2Y);
|
||||
usX2Y_clients_stop(usX2Y); // something is completely wroong > stop evrything
|
||||
usx2y_subs_startup_finish(usx2y);
|
||||
usx2y_clients_stop(usx2y); // something is completely wroong > stop evrything
|
||||
}
|
||||
return err;
|
||||
}
|
||||
@ -506,33 +506,33 @@ static int usX2Y_urbs_start(struct snd_usX2Y_substream *subs)
|
||||
/*
|
||||
* return the current pcm pointer. just return the hwptr_done value.
|
||||
*/
|
||||
static snd_pcm_uframes_t snd_usX2Y_pcm_pointer(struct snd_pcm_substream *substream)
|
||||
static snd_pcm_uframes_t snd_usx2y_pcm_pointer(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_usX2Y_substream *subs = substream->runtime->private_data;
|
||||
struct snd_usx2y_substream *subs = substream->runtime->private_data;
|
||||
return subs->hwptr_done;
|
||||
}
|
||||
/*
|
||||
* start/stop substream
|
||||
*/
|
||||
static int snd_usX2Y_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
|
||||
static int snd_usx2y_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
|
||||
{
|
||||
struct snd_usX2Y_substream *subs = substream->runtime->private_data;
|
||||
struct snd_usx2y_substream *subs = substream->runtime->private_data;
|
||||
|
||||
switch (cmd) {
|
||||
case SNDRV_PCM_TRIGGER_START:
|
||||
snd_printdd("snd_usX2Y_pcm_trigger(START)\n");
|
||||
if (atomic_read(&subs->state) == state_PREPARED &&
|
||||
atomic_read(&subs->usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE]->state) >= state_PREPARED) {
|
||||
atomic_set(&subs->state, state_PRERUNNING);
|
||||
snd_printdd("snd_usx2y_pcm_trigger(START)\n");
|
||||
if (atomic_read(&subs->state) == STATE_PREPARED &&
|
||||
atomic_read(&subs->usx2y->subs[SNDRV_PCM_STREAM_CAPTURE]->state) >= STATE_PREPARED) {
|
||||
atomic_set(&subs->state, STATE_PRERUNNING);
|
||||
} else {
|
||||
snd_printdd("\n");
|
||||
return -EPIPE;
|
||||
}
|
||||
break;
|
||||
case SNDRV_PCM_TRIGGER_STOP:
|
||||
snd_printdd("snd_usX2Y_pcm_trigger(STOP)\n");
|
||||
if (atomic_read(&subs->state) >= state_PRERUNNING)
|
||||
atomic_set(&subs->state, state_PREPARED);
|
||||
snd_printdd("snd_usx2y_pcm_trigger(STOP)\n");
|
||||
if (atomic_read(&subs->state) >= STATE_PRERUNNING)
|
||||
atomic_set(&subs->state, STATE_PREPARED);
|
||||
break;
|
||||
default:
|
||||
return -EINVAL;
|
||||
@ -553,7 +553,7 @@ static const struct s_c2
|
||||
{
|
||||
char c1, c2;
|
||||
}
|
||||
SetRate44100[] =
|
||||
setrate_44100[] =
|
||||
{
|
||||
{ 0x14, 0x08}, // this line sets 44100, well actually a little less
|
||||
{ 0x18, 0x40}, // only tascam / frontier design knows the further lines .......
|
||||
@ -589,7 +589,7 @@ static const struct s_c2
|
||||
{ 0x18, 0x7C},
|
||||
{ 0x18, 0x7E}
|
||||
};
|
||||
static const struct s_c2 SetRate48000[] =
|
||||
static const struct s_c2 setrate_48000[] =
|
||||
{
|
||||
{ 0x14, 0x09}, // this line sets 48000, well actually a little less
|
||||
{ 0x18, 0x40}, // only tascam / frontier design knows the further lines .......
|
||||
@ -625,26 +625,26 @@ static const struct s_c2 SetRate48000[] =
|
||||
{ 0x18, 0x7C},
|
||||
{ 0x18, 0x7E}
|
||||
};
|
||||
#define NOOF_SETRATE_URBS ARRAY_SIZE(SetRate48000)
|
||||
#define NOOF_SETRATE_URBS ARRAY_SIZE(setrate_48000)
|
||||
|
||||
static void i_usX2Y_04Int(struct urb *urb)
|
||||
static void i_usx2y_04int(struct urb *urb)
|
||||
{
|
||||
struct usX2Ydev *usX2Y = urb->context;
|
||||
struct usx2ydev *usx2y = urb->context;
|
||||
|
||||
if (urb->status)
|
||||
snd_printk(KERN_ERR "snd_usX2Y_04Int() urb->status=%i\n", urb->status);
|
||||
if (0 == --usX2Y->US04->len)
|
||||
wake_up(&usX2Y->In04WaitQueue);
|
||||
snd_printk(KERN_ERR "snd_usx2y_04int() urb->status=%i\n", urb->status);
|
||||
if (0 == --usx2y->us04->len)
|
||||
wake_up(&usx2y->in04_wait_queue);
|
||||
}
|
||||
|
||||
static int usX2Y_rate_set(struct usX2Ydev *usX2Y, int rate)
|
||||
static int usx2y_rate_set(struct usx2ydev *usx2y, int rate)
|
||||
{
|
||||
int err = 0, i;
|
||||
struct snd_usX2Y_urbSeq *us = NULL;
|
||||
struct snd_usx2y_urb_seq *us = NULL;
|
||||
int *usbdata = NULL;
|
||||
const struct s_c2 *ra = rate == 48000 ? SetRate48000 : SetRate44100;
|
||||
const struct s_c2 *ra = rate == 48000 ? setrate_48000 : setrate_44100;
|
||||
|
||||
if (usX2Y->rate != rate) {
|
||||
if (usx2y->rate != rate) {
|
||||
us = kzalloc(sizeof(*us) + sizeof(struct urb*) * NOOF_SETRATE_URBS, GFP_KERNEL);
|
||||
if (NULL == us) {
|
||||
err = -ENOMEM;
|
||||
@ -663,17 +663,17 @@ static int usX2Y_rate_set(struct usX2Ydev *usX2Y, int rate)
|
||||
}
|
||||
((char*)(usbdata + i))[0] = ra[i].c1;
|
||||
((char*)(usbdata + i))[1] = ra[i].c2;
|
||||
usb_fill_bulk_urb(us->urb[i], usX2Y->dev, usb_sndbulkpipe(usX2Y->dev, 4),
|
||||
usbdata + i, 2, i_usX2Y_04Int, usX2Y);
|
||||
usb_fill_bulk_urb(us->urb[i], usx2y->dev, usb_sndbulkpipe(usx2y->dev, 4),
|
||||
usbdata + i, 2, i_usx2y_04int, usx2y);
|
||||
}
|
||||
err = usb_urb_ep_type_check(us->urb[0]);
|
||||
if (err < 0)
|
||||
goto cleanup;
|
||||
us->submitted = 0;
|
||||
us->len = NOOF_SETRATE_URBS;
|
||||
usX2Y->US04 = us;
|
||||
wait_event_timeout(usX2Y->In04WaitQueue, 0 == us->len, HZ);
|
||||
usX2Y->US04 = NULL;
|
||||
usx2y->us04 = us;
|
||||
wait_event_timeout(usx2y->in04_wait_queue, 0 == us->len, HZ);
|
||||
usx2y->us04 = NULL;
|
||||
if (us->len)
|
||||
err = -ENODEV;
|
||||
cleanup:
|
||||
@ -690,11 +690,11 @@ static int usX2Y_rate_set(struct usX2Ydev *usX2Y, int rate)
|
||||
}
|
||||
usb_free_urb(urb);
|
||||
}
|
||||
usX2Y->US04 = NULL;
|
||||
usx2y->us04 = NULL;
|
||||
kfree(usbdata);
|
||||
kfree(us);
|
||||
if (!err)
|
||||
usX2Y->rate = rate;
|
||||
usx2y->rate = rate;
|
||||
}
|
||||
}
|
||||
|
||||
@ -702,53 +702,53 @@ static int usX2Y_rate_set(struct usX2Ydev *usX2Y, int rate)
|
||||
}
|
||||
|
||||
|
||||
static int usX2Y_format_set(struct usX2Ydev *usX2Y, snd_pcm_format_t format)
|
||||
static int usx2y_format_set(struct usx2ydev *usx2y, snd_pcm_format_t format)
|
||||
{
|
||||
int alternate, err;
|
||||
struct list_head* p;
|
||||
if (format == SNDRV_PCM_FORMAT_S24_3LE) {
|
||||
alternate = 2;
|
||||
usX2Y->stride = 6;
|
||||
usx2y->stride = 6;
|
||||
} else {
|
||||
alternate = 1;
|
||||
usX2Y->stride = 4;
|
||||
usx2y->stride = 4;
|
||||
}
|
||||
list_for_each(p, &usX2Y->midi_list) {
|
||||
list_for_each(p, &usx2y->midi_list) {
|
||||
snd_usbmidi_input_stop(p);
|
||||
}
|
||||
usb_kill_urb(usX2Y->In04urb);
|
||||
if ((err = usb_set_interface(usX2Y->dev, 0, alternate))) {
|
||||
usb_kill_urb(usx2y->in04_urb);
|
||||
if ((err = usb_set_interface(usx2y->dev, 0, alternate))) {
|
||||
snd_printk(KERN_ERR "usb_set_interface error \n");
|
||||
return err;
|
||||
}
|
||||
usX2Y->In04urb->dev = usX2Y->dev;
|
||||
err = usb_submit_urb(usX2Y->In04urb, GFP_KERNEL);
|
||||
list_for_each(p, &usX2Y->midi_list) {
|
||||
usx2y->in04_urb->dev = usx2y->dev;
|
||||
err = usb_submit_urb(usx2y->in04_urb, GFP_KERNEL);
|
||||
list_for_each(p, &usx2y->midi_list) {
|
||||
snd_usbmidi_input_start(p);
|
||||
}
|
||||
usX2Y->format = format;
|
||||
usX2Y->rate = 0;
|
||||
usx2y->format = format;
|
||||
usx2y->rate = 0;
|
||||
return err;
|
||||
}
|
||||
|
||||
|
||||
static int snd_usX2Y_pcm_hw_params(struct snd_pcm_substream *substream,
|
||||
static int snd_usx2y_pcm_hw_params(struct snd_pcm_substream *substream,
|
||||
struct snd_pcm_hw_params *hw_params)
|
||||
{
|
||||
int err = 0;
|
||||
unsigned int rate = params_rate(hw_params);
|
||||
snd_pcm_format_t format = params_format(hw_params);
|
||||
struct snd_card *card = substream->pstr->pcm->card;
|
||||
struct usX2Ydev *dev = usX2Y(card);
|
||||
struct usx2ydev *dev = usx2y(card);
|
||||
int i;
|
||||
|
||||
mutex_lock(&usX2Y(card)->pcm_mutex);
|
||||
snd_printdd("snd_usX2Y_hw_params(%p, %p)\n", substream, hw_params);
|
||||
/* all pcm substreams off one usX2Y have to operate at the same
|
||||
mutex_lock(&usx2y(card)->pcm_mutex);
|
||||
snd_printdd("snd_usx2y_hw_params(%p, %p)\n", substream, hw_params);
|
||||
/* all pcm substreams off one usx2y have to operate at the same
|
||||
* rate & format
|
||||
*/
|
||||
for (i = 0; i < dev->pcm_devs * 2; i++) {
|
||||
struct snd_usX2Y_substream *subs = dev->subs[i];
|
||||
struct snd_usx2y_substream *subs = dev->subs[i];
|
||||
struct snd_pcm_substream *test_substream;
|
||||
|
||||
if (!subs)
|
||||
@ -767,39 +767,39 @@ static int snd_usX2Y_pcm_hw_params(struct snd_pcm_substream *substream,
|
||||
}
|
||||
|
||||
error:
|
||||
mutex_unlock(&usX2Y(card)->pcm_mutex);
|
||||
mutex_unlock(&usx2y(card)->pcm_mutex);
|
||||
return err;
|
||||
}
|
||||
|
||||
/*
|
||||
* free the buffer
|
||||
*/
|
||||
static int snd_usX2Y_pcm_hw_free(struct snd_pcm_substream *substream)
|
||||
static int snd_usx2y_pcm_hw_free(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
struct snd_usX2Y_substream *subs = runtime->private_data;
|
||||
mutex_lock(&subs->usX2Y->pcm_mutex);
|
||||
snd_printdd("snd_usX2Y_hw_free(%p)\n", substream);
|
||||
struct snd_usx2y_substream *subs = runtime->private_data;
|
||||
mutex_lock(&subs->usx2y->pcm_mutex);
|
||||
snd_printdd("snd_usx2y_hw_free(%p)\n", substream);
|
||||
|
||||
if (SNDRV_PCM_STREAM_PLAYBACK == substream->stream) {
|
||||
struct snd_usX2Y_substream *cap_subs = subs->usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
atomic_set(&subs->state, state_STOPPED);
|
||||
usX2Y_urbs_release(subs);
|
||||
struct snd_usx2y_substream *cap_subs = subs->usx2y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
atomic_set(&subs->state, STATE_STOPPED);
|
||||
usx2y_urbs_release(subs);
|
||||
if (!cap_subs->pcm_substream ||
|
||||
!cap_subs->pcm_substream->runtime ||
|
||||
!cap_subs->pcm_substream->runtime->status ||
|
||||
cap_subs->pcm_substream->runtime->status->state < SNDRV_PCM_STATE_PREPARED) {
|
||||
atomic_set(&cap_subs->state, state_STOPPED);
|
||||
usX2Y_urbs_release(cap_subs);
|
||||
atomic_set(&cap_subs->state, STATE_STOPPED);
|
||||
usx2y_urbs_release(cap_subs);
|
||||
}
|
||||
} else {
|
||||
struct snd_usX2Y_substream *playback_subs = subs->usX2Y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
if (atomic_read(&playback_subs->state) < state_PREPARED) {
|
||||
atomic_set(&subs->state, state_STOPPED);
|
||||
usX2Y_urbs_release(subs);
|
||||
struct snd_usx2y_substream *playback_subs = subs->usx2y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
if (atomic_read(&playback_subs->state) < STATE_PREPARED) {
|
||||
atomic_set(&subs->state, STATE_STOPPED);
|
||||
usx2y_urbs_release(subs);
|
||||
}
|
||||
}
|
||||
mutex_unlock(&subs->usX2Y->pcm_mutex);
|
||||
mutex_unlock(&subs->usx2y->pcm_mutex);
|
||||
return 0;
|
||||
}
|
||||
/*
|
||||
@ -807,40 +807,40 @@ static int snd_usX2Y_pcm_hw_free(struct snd_pcm_substream *substream)
|
||||
*
|
||||
* set format and initialize urbs
|
||||
*/
|
||||
static int snd_usX2Y_pcm_prepare(struct snd_pcm_substream *substream)
|
||||
static int snd_usx2y_pcm_prepare(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
struct snd_usX2Y_substream *subs = runtime->private_data;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct snd_usX2Y_substream *capsubs = subs->usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
struct snd_usx2y_substream *subs = runtime->private_data;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
struct snd_usx2y_substream *capsubs = subs->usx2y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
int err = 0;
|
||||
snd_printdd("snd_usX2Y_pcm_prepare(%p)\n", substream);
|
||||
snd_printdd("snd_usx2y_pcm_prepare(%p)\n", substream);
|
||||
|
||||
mutex_lock(&usX2Y->pcm_mutex);
|
||||
usX2Y_subs_prepare(subs);
|
||||
mutex_lock(&usx2y->pcm_mutex);
|
||||
usx2y_subs_prepare(subs);
|
||||
// Start hardware streams
|
||||
// SyncStream first....
|
||||
if (atomic_read(&capsubs->state) < state_PREPARED) {
|
||||
if (usX2Y->format != runtime->format)
|
||||
if ((err = usX2Y_format_set(usX2Y, runtime->format)) < 0)
|
||||
if (atomic_read(&capsubs->state) < STATE_PREPARED) {
|
||||
if (usx2y->format != runtime->format)
|
||||
if ((err = usx2y_format_set(usx2y, runtime->format)) < 0)
|
||||
goto up_prepare_mutex;
|
||||
if (usX2Y->rate != runtime->rate)
|
||||
if ((err = usX2Y_rate_set(usX2Y, runtime->rate)) < 0)
|
||||
if (usx2y->rate != runtime->rate)
|
||||
if ((err = usx2y_rate_set(usx2y, runtime->rate)) < 0)
|
||||
goto up_prepare_mutex;
|
||||
snd_printdd("starting capture pipe for %s\n", subs == capsubs ? "self" : "playpipe");
|
||||
if (0 > (err = usX2Y_urbs_start(capsubs)))
|
||||
if (0 > (err = usx2y_urbs_start(capsubs)))
|
||||
goto up_prepare_mutex;
|
||||
}
|
||||
|
||||
if (subs != capsubs && atomic_read(&subs->state) < state_PREPARED)
|
||||
err = usX2Y_urbs_start(subs);
|
||||
if (subs != capsubs && atomic_read(&subs->state) < STATE_PREPARED)
|
||||
err = usx2y_urbs_start(subs);
|
||||
|
||||
up_prepare_mutex:
|
||||
mutex_unlock(&usX2Y->pcm_mutex);
|
||||
mutex_unlock(&usx2y->pcm_mutex);
|
||||
return err;
|
||||
}
|
||||
|
||||
static const struct snd_pcm_hardware snd_usX2Y_2c =
|
||||
static const struct snd_pcm_hardware snd_usx2y_2c =
|
||||
{
|
||||
.info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
|
||||
SNDRV_PCM_INFO_BLOCK_TRANSFER |
|
||||
@ -862,16 +862,16 @@ static const struct snd_pcm_hardware snd_usX2Y_2c =
|
||||
|
||||
|
||||
|
||||
static int snd_usX2Y_pcm_open(struct snd_pcm_substream *substream)
|
||||
static int snd_usx2y_pcm_open(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_usX2Y_substream *subs = ((struct snd_usX2Y_substream **)
|
||||
struct snd_usx2y_substream *subs = ((struct snd_usx2y_substream **)
|
||||
snd_pcm_substream_chip(substream))[substream->stream];
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
|
||||
if (subs->usX2Y->chip_status & USX2Y_STAT_CHIP_MMAP_PCM_URBS)
|
||||
if (subs->usx2y->chip_status & USX2Y_STAT_CHIP_MMAP_PCM_URBS)
|
||||
return -EBUSY;
|
||||
|
||||
runtime->hw = snd_usX2Y_2c;
|
||||
runtime->hw = snd_usx2y_2c;
|
||||
runtime->private_data = subs;
|
||||
subs->pcm_substream = substream;
|
||||
snd_pcm_hw_constraint_minmax(runtime, SNDRV_PCM_HW_PARAM_PERIOD_TIME, 1000, 200000);
|
||||
@ -880,10 +880,10 @@ static int snd_usX2Y_pcm_open(struct snd_pcm_substream *substream)
|
||||
|
||||
|
||||
|
||||
static int snd_usX2Y_pcm_close(struct snd_pcm_substream *substream)
|
||||
static int snd_usx2y_pcm_close(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
struct snd_usX2Y_substream *subs = runtime->private_data;
|
||||
struct snd_usx2y_substream *subs = runtime->private_data;
|
||||
|
||||
subs->pcm_substream = NULL;
|
||||
|
||||
@ -891,75 +891,75 @@ static int snd_usX2Y_pcm_close(struct snd_pcm_substream *substream)
|
||||
}
|
||||
|
||||
|
||||
static const struct snd_pcm_ops snd_usX2Y_pcm_ops =
|
||||
static const struct snd_pcm_ops snd_usx2y_pcm_ops =
|
||||
{
|
||||
.open = snd_usX2Y_pcm_open,
|
||||
.close = snd_usX2Y_pcm_close,
|
||||
.hw_params = snd_usX2Y_pcm_hw_params,
|
||||
.hw_free = snd_usX2Y_pcm_hw_free,
|
||||
.prepare = snd_usX2Y_pcm_prepare,
|
||||
.trigger = snd_usX2Y_pcm_trigger,
|
||||
.pointer = snd_usX2Y_pcm_pointer,
|
||||
.open = snd_usx2y_pcm_open,
|
||||
.close = snd_usx2y_pcm_close,
|
||||
.hw_params = snd_usx2y_pcm_hw_params,
|
||||
.hw_free = snd_usx2y_pcm_hw_free,
|
||||
.prepare = snd_usx2y_pcm_prepare,
|
||||
.trigger = snd_usx2y_pcm_trigger,
|
||||
.pointer = snd_usx2y_pcm_pointer,
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* free a usb stream instance
|
||||
*/
|
||||
static void usX2Y_audio_stream_free(struct snd_usX2Y_substream **usX2Y_substream)
|
||||
static void usx2y_audio_stream_free(struct snd_usx2y_substream **usx2y_substream)
|
||||
{
|
||||
int stream;
|
||||
|
||||
for_each_pcm_streams(stream) {
|
||||
kfree(usX2Y_substream[stream]);
|
||||
usX2Y_substream[stream] = NULL;
|
||||
kfree(usx2y_substream[stream]);
|
||||
usx2y_substream[stream] = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
static void snd_usX2Y_pcm_private_free(struct snd_pcm *pcm)
|
||||
static void snd_usx2y_pcm_private_free(struct snd_pcm *pcm)
|
||||
{
|
||||
struct snd_usX2Y_substream **usX2Y_stream = pcm->private_data;
|
||||
if (usX2Y_stream)
|
||||
usX2Y_audio_stream_free(usX2Y_stream);
|
||||
struct snd_usx2y_substream **usx2y_stream = pcm->private_data;
|
||||
if (usx2y_stream)
|
||||
usx2y_audio_stream_free(usx2y_stream);
|
||||
}
|
||||
|
||||
static int usX2Y_audio_stream_new(struct snd_card *card, int playback_endpoint, int capture_endpoint)
|
||||
static int usx2y_audio_stream_new(struct snd_card *card, int playback_endpoint, int capture_endpoint)
|
||||
{
|
||||
struct snd_pcm *pcm;
|
||||
int err, i;
|
||||
struct snd_usX2Y_substream **usX2Y_substream =
|
||||
usX2Y(card)->subs + 2 * usX2Y(card)->pcm_devs;
|
||||
struct snd_usx2y_substream **usx2y_substream =
|
||||
usx2y(card)->subs + 2 * usx2y(card)->pcm_devs;
|
||||
|
||||
for (i = playback_endpoint ? SNDRV_PCM_STREAM_PLAYBACK : SNDRV_PCM_STREAM_CAPTURE;
|
||||
i <= SNDRV_PCM_STREAM_CAPTURE; ++i) {
|
||||
usX2Y_substream[i] = kzalloc(sizeof(struct snd_usX2Y_substream), GFP_KERNEL);
|
||||
if (!usX2Y_substream[i])
|
||||
usx2y_substream[i] = kzalloc(sizeof(struct snd_usx2y_substream), GFP_KERNEL);
|
||||
if (!usx2y_substream[i])
|
||||
return -ENOMEM;
|
||||
|
||||
usX2Y_substream[i]->usX2Y = usX2Y(card);
|
||||
usx2y_substream[i]->usx2y = usx2y(card);
|
||||
}
|
||||
|
||||
if (playback_endpoint)
|
||||
usX2Y_substream[SNDRV_PCM_STREAM_PLAYBACK]->endpoint = playback_endpoint;
|
||||
usX2Y_substream[SNDRV_PCM_STREAM_CAPTURE]->endpoint = capture_endpoint;
|
||||
usx2y_substream[SNDRV_PCM_STREAM_PLAYBACK]->endpoint = playback_endpoint;
|
||||
usx2y_substream[SNDRV_PCM_STREAM_CAPTURE]->endpoint = capture_endpoint;
|
||||
|
||||
err = snd_pcm_new(card, NAME_ALLCAPS" Audio", usX2Y(card)->pcm_devs,
|
||||
err = snd_pcm_new(card, NAME_ALLCAPS" Audio", usx2y(card)->pcm_devs,
|
||||
playback_endpoint ? 1 : 0, 1,
|
||||
&pcm);
|
||||
if (err < 0) {
|
||||
usX2Y_audio_stream_free(usX2Y_substream);
|
||||
usx2y_audio_stream_free(usx2y_substream);
|
||||
return err;
|
||||
}
|
||||
|
||||
if (playback_endpoint)
|
||||
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, &snd_usX2Y_pcm_ops);
|
||||
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE, &snd_usX2Y_pcm_ops);
|
||||
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, &snd_usx2y_pcm_ops);
|
||||
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE, &snd_usx2y_pcm_ops);
|
||||
|
||||
pcm->private_data = usX2Y_substream;
|
||||
pcm->private_free = snd_usX2Y_pcm_private_free;
|
||||
pcm->private_data = usx2y_substream;
|
||||
pcm->private_free = snd_usx2y_pcm_private_free;
|
||||
pcm->info_flags = 0;
|
||||
|
||||
sprintf(pcm->name, NAME_ALLCAPS" Audio #%d", usX2Y(card)->pcm_devs);
|
||||
sprintf(pcm->name, NAME_ALLCAPS" Audio #%d", usx2y(card)->pcm_devs);
|
||||
|
||||
if (playback_endpoint) {
|
||||
snd_pcm_set_managed_buffer(pcm->streams[SNDRV_PCM_STREAM_PLAYBACK].substream,
|
||||
@ -972,7 +972,7 @@ static int usX2Y_audio_stream_new(struct snd_card *card, int playback_endpoint,
|
||||
SNDRV_DMA_TYPE_CONTINUOUS,
|
||||
NULL,
|
||||
64*1024, 128*1024);
|
||||
usX2Y(card)->pcm_devs++;
|
||||
usx2y(card)->pcm_devs++;
|
||||
|
||||
return 0;
|
||||
}
|
||||
@ -980,18 +980,18 @@ static int usX2Y_audio_stream_new(struct snd_card *card, int playback_endpoint,
|
||||
/*
|
||||
* create a chip instance and set its names.
|
||||
*/
|
||||
int usX2Y_audio_create(struct snd_card *card)
|
||||
int usx2y_audio_create(struct snd_card *card)
|
||||
{
|
||||
int err = 0;
|
||||
|
||||
INIT_LIST_HEAD(&usX2Y(card)->pcm_list);
|
||||
INIT_LIST_HEAD(&usx2y(card)->pcm_list);
|
||||
|
||||
if (0 > (err = usX2Y_audio_stream_new(card, 0xA, 0x8)))
|
||||
if (0 > (err = usx2y_audio_stream_new(card, 0xA, 0x8)))
|
||||
return err;
|
||||
if (le16_to_cpu(usX2Y(card)->dev->descriptor.idProduct) == USB_ID_US428)
|
||||
if (0 > (err = usX2Y_audio_stream_new(card, 0, 0xA)))
|
||||
if (le16_to_cpu(usx2y(card)->dev->descriptor.idProduct) == USB_ID_US428)
|
||||
if (0 > (err = usx2y_audio_stream_new(card, 0, 0xA)))
|
||||
return err;
|
||||
if (le16_to_cpu(usX2Y(card)->dev->descriptor.idProduct) != USB_ID_US122)
|
||||
err = usX2Y_rate_set(usX2Y(card), 44100); // Lets us428 recognize output-volume settings, disturbs us122.
|
||||
if (le16_to_cpu(usx2y(card)->dev->descriptor.idProduct) != USB_ID_US122)
|
||||
err = usx2y_rate_set(usx2y(card), 44100); // Lets us428 recognize output-volume settings, disturbs us122.
|
||||
return err;
|
||||
}
|
||||
|
@ -47,17 +47,17 @@
|
||||
#include <sound/hwdep.h>
|
||||
|
||||
|
||||
static int usX2Y_usbpcm_urb_capt_retire(struct snd_usX2Y_substream *subs)
|
||||
static int usx2y_usbpcm_urb_capt_retire(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
struct urb *urb = subs->completed_urb;
|
||||
struct snd_pcm_runtime *runtime = subs->pcm_substream->runtime;
|
||||
int i, lens = 0, hwptr_done = subs->hwptr_done;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
if (0 > usX2Y->hwdep_pcm_shm->capture_iso_start) { //FIXME
|
||||
int head = usX2Y->hwdep_pcm_shm->captured_iso_head + 1;
|
||||
if (head >= ARRAY_SIZE(usX2Y->hwdep_pcm_shm->captured_iso))
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
if (0 > usx2y->hwdep_pcm_shm->capture_iso_start) { //FIXME
|
||||
int head = usx2y->hwdep_pcm_shm->captured_iso_head + 1;
|
||||
if (head >= ARRAY_SIZE(usx2y->hwdep_pcm_shm->captured_iso))
|
||||
head = 0;
|
||||
usX2Y->hwdep_pcm_shm->capture_iso_start = head;
|
||||
usx2y->hwdep_pcm_shm->capture_iso_start = head;
|
||||
snd_printdd("cap start %i\n", head);
|
||||
}
|
||||
for (i = 0; i < nr_of_packs(); i++) {
|
||||
@ -65,7 +65,7 @@ static int usX2Y_usbpcm_urb_capt_retire(struct snd_usX2Y_substream *subs)
|
||||
snd_printk(KERN_ERR "active frame status %i. Most probably some hardware problem.\n", urb->iso_frame_desc[i].status);
|
||||
return urb->iso_frame_desc[i].status;
|
||||
}
|
||||
lens += urb->iso_frame_desc[i].actual_length / usX2Y->stride;
|
||||
lens += urb->iso_frame_desc[i].actual_length / usx2y->stride;
|
||||
}
|
||||
if ((hwptr_done += lens) >= runtime->buffer_size)
|
||||
hwptr_done -= runtime->buffer_size;
|
||||
@ -79,10 +79,10 @@ static int usX2Y_usbpcm_urb_capt_retire(struct snd_usX2Y_substream *subs)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline int usX2Y_iso_frames_per_buffer(struct snd_pcm_runtime *runtime,
|
||||
struct usX2Ydev * usX2Y)
|
||||
static inline int usx2y_iso_frames_per_buffer(struct snd_pcm_runtime *runtime,
|
||||
struct usx2ydev * usx2y)
|
||||
{
|
||||
return (runtime->buffer_size * 1000) / usX2Y->rate + 1; //FIXME: so far only correct period_size == 2^x ?
|
||||
return (runtime->buffer_size * 1000) / usx2y->rate + 1; //FIXME: so far only correct period_size == 2^x ?
|
||||
}
|
||||
|
||||
/*
|
||||
@ -95,17 +95,17 @@ static inline int usX2Y_iso_frames_per_buffer(struct snd_pcm_runtime *runtime,
|
||||
* it directly from the buffer. thus the data is once copied to
|
||||
* a temporary buffer and urb points to that.
|
||||
*/
|
||||
static int usX2Y_hwdep_urb_play_prepare(struct snd_usX2Y_substream *subs,
|
||||
static int usx2y_hwdep_urb_play_prepare(struct snd_usx2y_substream *subs,
|
||||
struct urb *urb)
|
||||
{
|
||||
int count, counts, pack;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct snd_usX2Y_hwdep_pcm_shm *shm = usX2Y->hwdep_pcm_shm;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
struct snd_usx2y_hwdep_pcm_shm *shm = usx2y->hwdep_pcm_shm;
|
||||
struct snd_pcm_runtime *runtime = subs->pcm_substream->runtime;
|
||||
|
||||
if (0 > shm->playback_iso_start) {
|
||||
shm->playback_iso_start = shm->captured_iso_head -
|
||||
usX2Y_iso_frames_per_buffer(runtime, usX2Y);
|
||||
usx2y_iso_frames_per_buffer(runtime, usx2y);
|
||||
if (0 > shm->playback_iso_start)
|
||||
shm->playback_iso_start += ARRAY_SIZE(shm->captured_iso);
|
||||
shm->playback_iso_head = shm->playback_iso_start;
|
||||
@ -114,7 +114,7 @@ static int usX2Y_hwdep_urb_play_prepare(struct snd_usX2Y_substream *subs,
|
||||
count = 0;
|
||||
for (pack = 0; pack < nr_of_packs(); pack++) {
|
||||
/* calculate the size of a packet */
|
||||
counts = shm->captured_iso[shm->playback_iso_head].length / usX2Y->stride;
|
||||
counts = shm->captured_iso[shm->playback_iso_head].length / usx2y->stride;
|
||||
if (counts < 43 || counts > 50) {
|
||||
snd_printk(KERN_ERR "should not be here with counts=%i\n", counts);
|
||||
return -EPIPE;
|
||||
@ -122,26 +122,26 @@ static int usX2Y_hwdep_urb_play_prepare(struct snd_usX2Y_substream *subs,
|
||||
/* set up descriptor */
|
||||
urb->iso_frame_desc[pack].offset = shm->captured_iso[shm->playback_iso_head].offset;
|
||||
urb->iso_frame_desc[pack].length = shm->captured_iso[shm->playback_iso_head].length;
|
||||
if (atomic_read(&subs->state) != state_RUNNING)
|
||||
if (atomic_read(&subs->state) != STATE_RUNNING)
|
||||
memset((char *)urb->transfer_buffer + urb->iso_frame_desc[pack].offset, 0,
|
||||
urb->iso_frame_desc[pack].length);
|
||||
if (++shm->playback_iso_head >= ARRAY_SIZE(shm->captured_iso))
|
||||
shm->playback_iso_head = 0;
|
||||
count += counts;
|
||||
}
|
||||
urb->transfer_buffer_length = count * usX2Y->stride;
|
||||
urb->transfer_buffer_length = count * usx2y->stride;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static inline void usX2Y_usbpcm_urb_capt_iso_advance(struct snd_usX2Y_substream *subs,
|
||||
static inline void usx2y_usbpcm_urb_capt_iso_advance(struct snd_usx2y_substream *subs,
|
||||
struct urb *urb)
|
||||
{
|
||||
int pack;
|
||||
for (pack = 0; pack < nr_of_packs(); ++pack) {
|
||||
struct usb_iso_packet_descriptor *desc = urb->iso_frame_desc + pack;
|
||||
if (NULL != subs) {
|
||||
struct snd_usX2Y_hwdep_pcm_shm *shm = subs->usX2Y->hwdep_pcm_shm;
|
||||
struct snd_usx2y_hwdep_pcm_shm *shm = subs->usx2y->hwdep_pcm_shm;
|
||||
int head = shm->captured_iso_head + 1;
|
||||
if (head >= ARRAY_SIZE(shm->captured_iso))
|
||||
head = 0;
|
||||
@ -157,9 +157,9 @@ static inline void usX2Y_usbpcm_urb_capt_iso_advance(struct snd_usX2Y_substream
|
||||
}
|
||||
}
|
||||
|
||||
static inline int usX2Y_usbpcm_usbframe_complete(struct snd_usX2Y_substream *capsubs,
|
||||
struct snd_usX2Y_substream *capsubs2,
|
||||
struct snd_usX2Y_substream *playbacksubs,
|
||||
static inline int usx2y_usbpcm_usbframe_complete(struct snd_usx2y_substream *capsubs,
|
||||
struct snd_usx2y_substream *capsubs2,
|
||||
struct snd_usx2y_substream *playbacksubs,
|
||||
int frame)
|
||||
{
|
||||
int err, state;
|
||||
@ -167,25 +167,25 @@ static inline int usX2Y_usbpcm_usbframe_complete(struct snd_usX2Y_substream *cap
|
||||
|
||||
state = atomic_read(&playbacksubs->state);
|
||||
if (NULL != urb) {
|
||||
if (state == state_RUNNING)
|
||||
usX2Y_urb_play_retire(playbacksubs, urb);
|
||||
else if (state >= state_PRERUNNING)
|
||||
if (state == STATE_RUNNING)
|
||||
usx2y_urb_play_retire(playbacksubs, urb);
|
||||
else if (state >= STATE_PRERUNNING)
|
||||
atomic_inc(&playbacksubs->state);
|
||||
} else {
|
||||
switch (state) {
|
||||
case state_STARTING1:
|
||||
case STATE_STARTING1:
|
||||
urb = playbacksubs->urb[0];
|
||||
atomic_inc(&playbacksubs->state);
|
||||
break;
|
||||
case state_STARTING2:
|
||||
case STATE_STARTING2:
|
||||
urb = playbacksubs->urb[1];
|
||||
atomic_inc(&playbacksubs->state);
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (urb) {
|
||||
if ((err = usX2Y_hwdep_urb_play_prepare(playbacksubs, urb)) ||
|
||||
(err = usX2Y_urb_submit(playbacksubs, urb, frame))) {
|
||||
if ((err = usx2y_hwdep_urb_play_prepare(playbacksubs, urb)) ||
|
||||
(err = usx2y_urb_submit(playbacksubs, urb, frame))) {
|
||||
return err;
|
||||
}
|
||||
}
|
||||
@ -193,19 +193,19 @@ static inline int usX2Y_usbpcm_usbframe_complete(struct snd_usX2Y_substream *cap
|
||||
playbacksubs->completed_urb = NULL;
|
||||
|
||||
state = atomic_read(&capsubs->state);
|
||||
if (state >= state_PREPARED) {
|
||||
if (state == state_RUNNING) {
|
||||
if ((err = usX2Y_usbpcm_urb_capt_retire(capsubs)))
|
||||
if (state >= STATE_PREPARED) {
|
||||
if (state == STATE_RUNNING) {
|
||||
if ((err = usx2y_usbpcm_urb_capt_retire(capsubs)))
|
||||
return err;
|
||||
} else if (state >= state_PRERUNNING)
|
||||
} else if (state >= STATE_PRERUNNING)
|
||||
atomic_inc(&capsubs->state);
|
||||
usX2Y_usbpcm_urb_capt_iso_advance(capsubs, capsubs->completed_urb);
|
||||
usx2y_usbpcm_urb_capt_iso_advance(capsubs, capsubs->completed_urb);
|
||||
if (NULL != capsubs2)
|
||||
usX2Y_usbpcm_urb_capt_iso_advance(NULL, capsubs2->completed_urb);
|
||||
if ((err = usX2Y_urb_submit(capsubs, capsubs->completed_urb, frame)))
|
||||
usx2y_usbpcm_urb_capt_iso_advance(NULL, capsubs2->completed_urb);
|
||||
if ((err = usx2y_urb_submit(capsubs, capsubs->completed_urb, frame)))
|
||||
return err;
|
||||
if (NULL != capsubs2)
|
||||
if ((err = usX2Y_urb_submit(capsubs2, capsubs2->completed_urb, frame)))
|
||||
if ((err = usx2y_urb_submit(capsubs2, capsubs2->completed_urb, frame)))
|
||||
return err;
|
||||
}
|
||||
capsubs->completed_urb = NULL;
|
||||
@ -215,42 +215,42 @@ static inline int usX2Y_usbpcm_usbframe_complete(struct snd_usX2Y_substream *cap
|
||||
}
|
||||
|
||||
|
||||
static void i_usX2Y_usbpcm_urb_complete(struct urb *urb)
|
||||
static void i_usx2y_usbpcm_urb_complete(struct urb *urb)
|
||||
{
|
||||
struct snd_usX2Y_substream *subs = urb->context;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct snd_usX2Y_substream *capsubs, *capsubs2, *playbacksubs;
|
||||
struct snd_usx2y_substream *subs = urb->context;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
struct snd_usx2y_substream *capsubs, *capsubs2, *playbacksubs;
|
||||
|
||||
if (unlikely(atomic_read(&subs->state) < state_PREPARED)) {
|
||||
if (unlikely(atomic_read(&subs->state) < STATE_PREPARED)) {
|
||||
snd_printdd("hcd_frame=%i ep=%i%s status=%i start_frame=%i\n",
|
||||
usb_get_current_frame_number(usX2Y->dev),
|
||||
usb_get_current_frame_number(usx2y->dev),
|
||||
subs->endpoint, usb_pipein(urb->pipe) ? "in" : "out",
|
||||
urb->status, urb->start_frame);
|
||||
return;
|
||||
}
|
||||
if (unlikely(urb->status)) {
|
||||
usX2Y_error_urb_status(usX2Y, subs, urb);
|
||||
usx2y_error_urb_status(usx2y, subs, urb);
|
||||
return;
|
||||
}
|
||||
|
||||
subs->completed_urb = urb;
|
||||
capsubs = usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
capsubs2 = usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE + 2];
|
||||
playbacksubs = usX2Y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
if (capsubs->completed_urb && atomic_read(&capsubs->state) >= state_PREPARED &&
|
||||
capsubs = usx2y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
capsubs2 = usx2y->subs[SNDRV_PCM_STREAM_CAPTURE + 2];
|
||||
playbacksubs = usx2y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
if (capsubs->completed_urb && atomic_read(&capsubs->state) >= STATE_PREPARED &&
|
||||
(NULL == capsubs2 || capsubs2->completed_urb) &&
|
||||
(playbacksubs->completed_urb || atomic_read(&playbacksubs->state) < state_PREPARED)) {
|
||||
if (!usX2Y_usbpcm_usbframe_complete(capsubs, capsubs2, playbacksubs, urb->start_frame))
|
||||
usX2Y->wait_iso_frame += nr_of_packs();
|
||||
(playbacksubs->completed_urb || atomic_read(&playbacksubs->state) < STATE_PREPARED)) {
|
||||
if (!usx2y_usbpcm_usbframe_complete(capsubs, capsubs2, playbacksubs, urb->start_frame))
|
||||
usx2y->wait_iso_frame += nr_of_packs();
|
||||
else {
|
||||
snd_printdd("\n");
|
||||
usX2Y_clients_stop(usX2Y);
|
||||
usx2y_clients_stop(usx2y);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void usX2Y_hwdep_urb_release(struct urb **urb)
|
||||
static void usx2y_hwdep_urb_release(struct urb **urb)
|
||||
{
|
||||
usb_kill_urb(*urb);
|
||||
usb_free_urb(*urb);
|
||||
@ -260,49 +260,49 @@ static void usX2Y_hwdep_urb_release(struct urb **urb)
|
||||
/*
|
||||
* release a substream
|
||||
*/
|
||||
static void usX2Y_usbpcm_urbs_release(struct snd_usX2Y_substream *subs)
|
||||
static void usx2y_usbpcm_urbs_release(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
int i;
|
||||
snd_printdd("snd_usX2Y_urbs_release() %i\n", subs->endpoint);
|
||||
snd_printdd("snd_usx2y_urbs_release() %i\n", subs->endpoint);
|
||||
for (i = 0; i < NRURBS; i++)
|
||||
usX2Y_hwdep_urb_release(subs->urb + i);
|
||||
usx2y_hwdep_urb_release(subs->urb + i);
|
||||
}
|
||||
|
||||
static void usX2Y_usbpcm_subs_startup_finish(struct usX2Ydev * usX2Y)
|
||||
static void usx2y_usbpcm_subs_startup_finish(struct usx2ydev * usx2y)
|
||||
{
|
||||
usX2Y_urbs_set_complete(usX2Y, i_usX2Y_usbpcm_urb_complete);
|
||||
usX2Y->prepare_subs = NULL;
|
||||
usx2y_urbs_set_complete(usx2y, i_usx2y_usbpcm_urb_complete);
|
||||
usx2y->prepare_subs = NULL;
|
||||
}
|
||||
|
||||
static void i_usX2Y_usbpcm_subs_startup(struct urb *urb)
|
||||
static void i_usx2y_usbpcm_subs_startup(struct urb *urb)
|
||||
{
|
||||
struct snd_usX2Y_substream *subs = urb->context;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct snd_usX2Y_substream *prepare_subs = usX2Y->prepare_subs;
|
||||
struct snd_usx2y_substream *subs = urb->context;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
struct snd_usx2y_substream *prepare_subs = usx2y->prepare_subs;
|
||||
if (NULL != prepare_subs &&
|
||||
urb->start_frame == prepare_subs->urb[0]->start_frame) {
|
||||
atomic_inc(&prepare_subs->state);
|
||||
if (prepare_subs == usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE]) {
|
||||
struct snd_usX2Y_substream *cap_subs2 = usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE + 2];
|
||||
if (prepare_subs == usx2y->subs[SNDRV_PCM_STREAM_CAPTURE]) {
|
||||
struct snd_usx2y_substream *cap_subs2 = usx2y->subs[SNDRV_PCM_STREAM_CAPTURE + 2];
|
||||
if (cap_subs2 != NULL)
|
||||
atomic_inc(&cap_subs2->state);
|
||||
}
|
||||
usX2Y_usbpcm_subs_startup_finish(usX2Y);
|
||||
wake_up(&usX2Y->prepare_wait_queue);
|
||||
usx2y_usbpcm_subs_startup_finish(usx2y);
|
||||
wake_up(&usx2y->prepare_wait_queue);
|
||||
}
|
||||
|
||||
i_usX2Y_usbpcm_urb_complete(urb);
|
||||
i_usx2y_usbpcm_urb_complete(urb);
|
||||
}
|
||||
|
||||
/*
|
||||
* initialize a substream's urbs
|
||||
*/
|
||||
static int usX2Y_usbpcm_urbs_allocate(struct snd_usX2Y_substream *subs)
|
||||
static int usx2y_usbpcm_urbs_allocate(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
int i;
|
||||
unsigned int pipe;
|
||||
int is_playback = subs == subs->usX2Y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
struct usb_device *dev = subs->usX2Y->dev;
|
||||
int is_playback = subs == subs->usx2y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
struct usb_device *dev = subs->usx2y->dev;
|
||||
|
||||
pipe = is_playback ? usb_sndisocpipe(dev, subs->endpoint) :
|
||||
usb_rcvisocpipe(dev, subs->endpoint);
|
||||
@ -319,21 +319,21 @@ static int usX2Y_usbpcm_urbs_allocate(struct snd_usX2Y_substream *subs)
|
||||
}
|
||||
*purb = usb_alloc_urb(nr_of_packs(), GFP_KERNEL);
|
||||
if (NULL == *purb) {
|
||||
usX2Y_usbpcm_urbs_release(subs);
|
||||
usx2y_usbpcm_urbs_release(subs);
|
||||
return -ENOMEM;
|
||||
}
|
||||
(*purb)->transfer_buffer = is_playback ?
|
||||
subs->usX2Y->hwdep_pcm_shm->playback : (
|
||||
subs->usx2y->hwdep_pcm_shm->playback : (
|
||||
subs->endpoint == 0x8 ?
|
||||
subs->usX2Y->hwdep_pcm_shm->capture0x8 :
|
||||
subs->usX2Y->hwdep_pcm_shm->capture0xA);
|
||||
subs->usx2y->hwdep_pcm_shm->capture0x8 :
|
||||
subs->usx2y->hwdep_pcm_shm->capture0xA);
|
||||
|
||||
(*purb)->dev = dev;
|
||||
(*purb)->pipe = pipe;
|
||||
(*purb)->number_of_packets = nr_of_packs();
|
||||
(*purb)->context = subs;
|
||||
(*purb)->interval = 1;
|
||||
(*purb)->complete = i_usX2Y_usbpcm_subs_startup;
|
||||
(*purb)->complete = i_usx2y_usbpcm_subs_startup;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@ -341,91 +341,91 @@ static int usX2Y_usbpcm_urbs_allocate(struct snd_usX2Y_substream *subs)
|
||||
/*
|
||||
* free the buffer
|
||||
*/
|
||||
static int snd_usX2Y_usbpcm_hw_free(struct snd_pcm_substream *substream)
|
||||
static int snd_usx2y_usbpcm_hw_free(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
struct snd_usX2Y_substream *subs = runtime->private_data,
|
||||
*cap_subs2 = subs->usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE + 2];
|
||||
mutex_lock(&subs->usX2Y->pcm_mutex);
|
||||
snd_printdd("snd_usX2Y_usbpcm_hw_free(%p)\n", substream);
|
||||
struct snd_usx2y_substream *subs = runtime->private_data,
|
||||
*cap_subs2 = subs->usx2y->subs[SNDRV_PCM_STREAM_CAPTURE + 2];
|
||||
mutex_lock(&subs->usx2y->pcm_mutex);
|
||||
snd_printdd("snd_usx2y_usbpcm_hw_free(%p)\n", substream);
|
||||
|
||||
if (SNDRV_PCM_STREAM_PLAYBACK == substream->stream) {
|
||||
struct snd_usX2Y_substream *cap_subs = subs->usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
atomic_set(&subs->state, state_STOPPED);
|
||||
usX2Y_usbpcm_urbs_release(subs);
|
||||
struct snd_usx2y_substream *cap_subs = subs->usx2y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
atomic_set(&subs->state, STATE_STOPPED);
|
||||
usx2y_usbpcm_urbs_release(subs);
|
||||
if (!cap_subs->pcm_substream ||
|
||||
!cap_subs->pcm_substream->runtime ||
|
||||
!cap_subs->pcm_substream->runtime->status ||
|
||||
cap_subs->pcm_substream->runtime->status->state < SNDRV_PCM_STATE_PREPARED) {
|
||||
atomic_set(&cap_subs->state, state_STOPPED);
|
||||
atomic_set(&cap_subs->state, STATE_STOPPED);
|
||||
if (NULL != cap_subs2)
|
||||
atomic_set(&cap_subs2->state, state_STOPPED);
|
||||
usX2Y_usbpcm_urbs_release(cap_subs);
|
||||
atomic_set(&cap_subs2->state, STATE_STOPPED);
|
||||
usx2y_usbpcm_urbs_release(cap_subs);
|
||||
if (NULL != cap_subs2)
|
||||
usX2Y_usbpcm_urbs_release(cap_subs2);
|
||||
usx2y_usbpcm_urbs_release(cap_subs2);
|
||||
}
|
||||
} else {
|
||||
struct snd_usX2Y_substream *playback_subs = subs->usX2Y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
if (atomic_read(&playback_subs->state) < state_PREPARED) {
|
||||
atomic_set(&subs->state, state_STOPPED);
|
||||
struct snd_usx2y_substream *playback_subs = subs->usx2y->subs[SNDRV_PCM_STREAM_PLAYBACK];
|
||||
if (atomic_read(&playback_subs->state) < STATE_PREPARED) {
|
||||
atomic_set(&subs->state, STATE_STOPPED);
|
||||
if (NULL != cap_subs2)
|
||||
atomic_set(&cap_subs2->state, state_STOPPED);
|
||||
usX2Y_usbpcm_urbs_release(subs);
|
||||
atomic_set(&cap_subs2->state, STATE_STOPPED);
|
||||
usx2y_usbpcm_urbs_release(subs);
|
||||
if (NULL != cap_subs2)
|
||||
usX2Y_usbpcm_urbs_release(cap_subs2);
|
||||
usx2y_usbpcm_urbs_release(cap_subs2);
|
||||
}
|
||||
}
|
||||
mutex_unlock(&subs->usX2Y->pcm_mutex);
|
||||
mutex_unlock(&subs->usx2y->pcm_mutex);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void usX2Y_usbpcm_subs_startup(struct snd_usX2Y_substream *subs)
|
||||
static void usx2y_usbpcm_subs_startup(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
struct usX2Ydev * usX2Y = subs->usX2Y;
|
||||
usX2Y->prepare_subs = subs;
|
||||
struct usx2ydev * usx2y = subs->usx2y;
|
||||
usx2y->prepare_subs = subs;
|
||||
subs->urb[0]->start_frame = -1;
|
||||
smp_wmb(); // Make sure above modifications are seen by i_usX2Y_subs_startup()
|
||||
usX2Y_urbs_set_complete(usX2Y, i_usX2Y_usbpcm_subs_startup);
|
||||
smp_wmb(); // Make sure above modifications are seen by i_usx2y_subs_startup()
|
||||
usx2y_urbs_set_complete(usx2y, i_usx2y_usbpcm_subs_startup);
|
||||
}
|
||||
|
||||
static int usX2Y_usbpcm_urbs_start(struct snd_usX2Y_substream *subs)
|
||||
static int usx2y_usbpcm_urbs_start(struct snd_usx2y_substream *subs)
|
||||
{
|
||||
int p, u, err,
|
||||
stream = subs->pcm_substream->stream;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
|
||||
if (SNDRV_PCM_STREAM_CAPTURE == stream) {
|
||||
usX2Y->hwdep_pcm_shm->captured_iso_head = -1;
|
||||
usX2Y->hwdep_pcm_shm->captured_iso_frames = 0;
|
||||
usx2y->hwdep_pcm_shm->captured_iso_head = -1;
|
||||
usx2y->hwdep_pcm_shm->captured_iso_frames = 0;
|
||||
}
|
||||
|
||||
for (p = 0; 3 >= (stream + p); p += 2) {
|
||||
struct snd_usX2Y_substream *subs = usX2Y->subs[stream + p];
|
||||
struct snd_usx2y_substream *subs = usx2y->subs[stream + p];
|
||||
if (subs != NULL) {
|
||||
if ((err = usX2Y_usbpcm_urbs_allocate(subs)) < 0)
|
||||
if ((err = usx2y_usbpcm_urbs_allocate(subs)) < 0)
|
||||
return err;
|
||||
subs->completed_urb = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
for (p = 0; p < 4; p++) {
|
||||
struct snd_usX2Y_substream *subs = usX2Y->subs[p];
|
||||
if (subs != NULL && atomic_read(&subs->state) >= state_PREPARED)
|
||||
struct snd_usx2y_substream *subs = usx2y->subs[p];
|
||||
if (subs != NULL && atomic_read(&subs->state) >= STATE_PREPARED)
|
||||
goto start;
|
||||
}
|
||||
|
||||
start:
|
||||
usX2Y_usbpcm_subs_startup(subs);
|
||||
usx2y_usbpcm_subs_startup(subs);
|
||||
for (u = 0; u < NRURBS; u++) {
|
||||
for (p = 0; 3 >= (stream + p); p += 2) {
|
||||
struct snd_usX2Y_substream *subs = usX2Y->subs[stream + p];
|
||||
struct snd_usx2y_substream *subs = usx2y->subs[stream + p];
|
||||
if (subs != NULL) {
|
||||
struct urb *urb = subs->urb[u];
|
||||
if (usb_pipein(urb->pipe)) {
|
||||
unsigned long pack;
|
||||
if (0 == u)
|
||||
atomic_set(&subs->state, state_STARTING3);
|
||||
urb->dev = usX2Y->dev;
|
||||
atomic_set(&subs->state, STATE_STARTING3);
|
||||
urb->dev = usx2y->dev;
|
||||
for (pack = 0; pack < nr_of_packs(); pack++) {
|
||||
urb->iso_frame_desc[pack].offset = subs->maxpacksize * (pack + u * nr_of_packs());
|
||||
urb->iso_frame_desc[pack].length = subs->maxpacksize;
|
||||
@ -438,25 +438,25 @@ static int usX2Y_usbpcm_urbs_start(struct snd_usX2Y_substream *subs)
|
||||
} else {
|
||||
snd_printdd("%i\n", urb->start_frame);
|
||||
if (u == 0)
|
||||
usX2Y->wait_iso_frame = urb->start_frame;
|
||||
usx2y->wait_iso_frame = urb->start_frame;
|
||||
}
|
||||
urb->transfer_flags = 0;
|
||||
} else {
|
||||
atomic_set(&subs->state, state_STARTING1);
|
||||
atomic_set(&subs->state, STATE_STARTING1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
err = 0;
|
||||
wait_event(usX2Y->prepare_wait_queue, NULL == usX2Y->prepare_subs);
|
||||
if (atomic_read(&subs->state) != state_PREPARED)
|
||||
wait_event(usx2y->prepare_wait_queue, NULL == usx2y->prepare_subs);
|
||||
if (atomic_read(&subs->state) != STATE_PREPARED)
|
||||
err = -EPIPE;
|
||||
|
||||
cleanup:
|
||||
if (err) {
|
||||
usX2Y_subs_startup_finish(usX2Y); // Call it now
|
||||
usX2Y_clients_stop(usX2Y); // something is completely wroong > stop evrything
|
||||
usx2y_subs_startup_finish(usx2y); // Call it now
|
||||
usx2y_clients_stop(usx2y); // something is completely wroong > stop evrything
|
||||
}
|
||||
return err;
|
||||
}
|
||||
@ -466,69 +466,69 @@ static int usX2Y_usbpcm_urbs_start(struct snd_usX2Y_substream *subs)
|
||||
*
|
||||
* set format and initialize urbs
|
||||
*/
|
||||
static int snd_usX2Y_usbpcm_prepare(struct snd_pcm_substream *substream)
|
||||
static int snd_usx2y_usbpcm_prepare(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
struct snd_usX2Y_substream *subs = runtime->private_data;
|
||||
struct usX2Ydev *usX2Y = subs->usX2Y;
|
||||
struct snd_usX2Y_substream *capsubs = subs->usX2Y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
struct snd_usx2y_substream *subs = runtime->private_data;
|
||||
struct usx2ydev *usx2y = subs->usx2y;
|
||||
struct snd_usx2y_substream *capsubs = subs->usx2y->subs[SNDRV_PCM_STREAM_CAPTURE];
|
||||
int err = 0;
|
||||
snd_printdd("snd_usX2Y_pcm_prepare(%p)\n", substream);
|
||||
snd_printdd("snd_usx2y_pcm_prepare(%p)\n", substream);
|
||||
|
||||
if (NULL == usX2Y->hwdep_pcm_shm) {
|
||||
usX2Y->hwdep_pcm_shm = alloc_pages_exact(sizeof(struct snd_usX2Y_hwdep_pcm_shm),
|
||||
if (NULL == usx2y->hwdep_pcm_shm) {
|
||||
usx2y->hwdep_pcm_shm = alloc_pages_exact(sizeof(struct snd_usx2y_hwdep_pcm_shm),
|
||||
GFP_KERNEL);
|
||||
if (!usX2Y->hwdep_pcm_shm)
|
||||
if (!usx2y->hwdep_pcm_shm)
|
||||
return -ENOMEM;
|
||||
memset(usX2Y->hwdep_pcm_shm, 0, sizeof(struct snd_usX2Y_hwdep_pcm_shm));
|
||||
memset(usx2y->hwdep_pcm_shm, 0, sizeof(struct snd_usx2y_hwdep_pcm_shm));
|
||||
}
|
||||
|
||||
mutex_lock(&usX2Y->pcm_mutex);
|
||||
usX2Y_subs_prepare(subs);
|
||||
mutex_lock(&usx2y->pcm_mutex);
|
||||
usx2y_subs_prepare(subs);
|
||||
// Start hardware streams
|
||||
// SyncStream first....
|
||||
if (atomic_read(&capsubs->state) < state_PREPARED) {
|
||||
if (usX2Y->format != runtime->format)
|
||||
if ((err = usX2Y_format_set(usX2Y, runtime->format)) < 0)
|
||||
if (atomic_read(&capsubs->state) < STATE_PREPARED) {
|
||||
if (usx2y->format != runtime->format)
|
||||
if ((err = usx2y_format_set(usx2y, runtime->format)) < 0)
|
||||
goto up_prepare_mutex;
|
||||
if (usX2Y->rate != runtime->rate)
|
||||
if ((err = usX2Y_rate_set(usX2Y, runtime->rate)) < 0)
|
||||
if (usx2y->rate != runtime->rate)
|
||||
if ((err = usx2y_rate_set(usx2y, runtime->rate)) < 0)
|
||||
goto up_prepare_mutex;
|
||||
snd_printdd("starting capture pipe for %s\n", subs == capsubs ?
|
||||
"self" : "playpipe");
|
||||
if (0 > (err = usX2Y_usbpcm_urbs_start(capsubs)))
|
||||
if (0 > (err = usx2y_usbpcm_urbs_start(capsubs)))
|
||||
goto up_prepare_mutex;
|
||||
}
|
||||
|
||||
if (subs != capsubs) {
|
||||
usX2Y->hwdep_pcm_shm->playback_iso_start = -1;
|
||||
if (atomic_read(&subs->state) < state_PREPARED) {
|
||||
while (usX2Y_iso_frames_per_buffer(runtime, usX2Y) >
|
||||
usX2Y->hwdep_pcm_shm->captured_iso_frames) {
|
||||
usx2y->hwdep_pcm_shm->playback_iso_start = -1;
|
||||
if (atomic_read(&subs->state) < STATE_PREPARED) {
|
||||
while (usx2y_iso_frames_per_buffer(runtime, usx2y) >
|
||||
usx2y->hwdep_pcm_shm->captured_iso_frames) {
|
||||
snd_printdd("Wait: iso_frames_per_buffer=%i,"
|
||||
"captured_iso_frames=%i\n",
|
||||
usX2Y_iso_frames_per_buffer(runtime, usX2Y),
|
||||
usX2Y->hwdep_pcm_shm->captured_iso_frames);
|
||||
usx2y_iso_frames_per_buffer(runtime, usx2y),
|
||||
usx2y->hwdep_pcm_shm->captured_iso_frames);
|
||||
if (msleep_interruptible(10)) {
|
||||
err = -ERESTARTSYS;
|
||||
goto up_prepare_mutex;
|
||||
}
|
||||
}
|
||||
if (0 > (err = usX2Y_usbpcm_urbs_start(subs)))
|
||||
if (0 > (err = usx2y_usbpcm_urbs_start(subs)))
|
||||
goto up_prepare_mutex;
|
||||
}
|
||||
snd_printdd("Ready: iso_frames_per_buffer=%i,captured_iso_frames=%i\n",
|
||||
usX2Y_iso_frames_per_buffer(runtime, usX2Y),
|
||||
usX2Y->hwdep_pcm_shm->captured_iso_frames);
|
||||
usx2y_iso_frames_per_buffer(runtime, usx2y),
|
||||
usx2y->hwdep_pcm_shm->captured_iso_frames);
|
||||
} else
|
||||
usX2Y->hwdep_pcm_shm->capture_iso_start = -1;
|
||||
usx2y->hwdep_pcm_shm->capture_iso_start = -1;
|
||||
|
||||
up_prepare_mutex:
|
||||
mutex_unlock(&usX2Y->pcm_mutex);
|
||||
mutex_unlock(&usx2y->pcm_mutex);
|
||||
return err;
|
||||
}
|
||||
|
||||
static const struct snd_pcm_hardware snd_usX2Y_4c =
|
||||
static const struct snd_pcm_hardware snd_usx2y_4c =
|
||||
{
|
||||
.info = (SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_INTERLEAVED |
|
||||
SNDRV_PCM_INFO_BLOCK_TRANSFER |
|
||||
@ -549,17 +549,17 @@ static const struct snd_pcm_hardware snd_usX2Y_4c =
|
||||
|
||||
|
||||
|
||||
static int snd_usX2Y_usbpcm_open(struct snd_pcm_substream *substream)
|
||||
static int snd_usx2y_usbpcm_open(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_usX2Y_substream *subs = ((struct snd_usX2Y_substream **)
|
||||
struct snd_usx2y_substream *subs = ((struct snd_usx2y_substream **)
|
||||
snd_pcm_substream_chip(substream))[substream->stream];
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
|
||||
if (!(subs->usX2Y->chip_status & USX2Y_STAT_CHIP_MMAP_PCM_URBS))
|
||||
if (!(subs->usx2y->chip_status & USX2Y_STAT_CHIP_MMAP_PCM_URBS))
|
||||
return -EBUSY;
|
||||
|
||||
runtime->hw = SNDRV_PCM_STREAM_PLAYBACK == substream->stream ? snd_usX2Y_2c :
|
||||
(subs->usX2Y->subs[3] ? snd_usX2Y_4c : snd_usX2Y_2c);
|
||||
runtime->hw = SNDRV_PCM_STREAM_PLAYBACK == substream->stream ? snd_usx2y_2c :
|
||||
(subs->usx2y->subs[3] ? snd_usx2y_4c : snd_usx2y_2c);
|
||||
runtime->private_data = subs;
|
||||
subs->pcm_substream = substream;
|
||||
snd_pcm_hw_constraint_minmax(runtime, SNDRV_PCM_HW_PARAM_PERIOD_TIME, 1000, 200000);
|
||||
@ -567,35 +567,35 @@ static int snd_usX2Y_usbpcm_open(struct snd_pcm_substream *substream)
|
||||
}
|
||||
|
||||
|
||||
static int snd_usX2Y_usbpcm_close(struct snd_pcm_substream *substream)
|
||||
static int snd_usx2y_usbpcm_close(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
struct snd_usX2Y_substream *subs = runtime->private_data;
|
||||
struct snd_usx2y_substream *subs = runtime->private_data;
|
||||
|
||||
subs->pcm_substream = NULL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static const struct snd_pcm_ops snd_usX2Y_usbpcm_ops =
|
||||
static const struct snd_pcm_ops snd_usx2y_usbpcm_ops =
|
||||
{
|
||||
.open = snd_usX2Y_usbpcm_open,
|
||||
.close = snd_usX2Y_usbpcm_close,
|
||||
.hw_params = snd_usX2Y_pcm_hw_params,
|
||||
.hw_free = snd_usX2Y_usbpcm_hw_free,
|
||||
.prepare = snd_usX2Y_usbpcm_prepare,
|
||||
.trigger = snd_usX2Y_pcm_trigger,
|
||||
.pointer = snd_usX2Y_pcm_pointer,
|
||||
.open = snd_usx2y_usbpcm_open,
|
||||
.close = snd_usx2y_usbpcm_close,
|
||||
.hw_params = snd_usx2y_pcm_hw_params,
|
||||
.hw_free = snd_usx2y_usbpcm_hw_free,
|
||||
.prepare = snd_usx2y_usbpcm_prepare,
|
||||
.trigger = snd_usx2y_pcm_trigger,
|
||||
.pointer = snd_usx2y_pcm_pointer,
|
||||
};
|
||||
|
||||
|
||||
static int usX2Y_pcms_busy_check(struct snd_card *card)
|
||||
static int usx2y_pcms_busy_check(struct snd_card *card)
|
||||
{
|
||||
struct usX2Ydev *dev = usX2Y(card);
|
||||
struct usx2ydev *dev = usx2y(card);
|
||||
int i;
|
||||
|
||||
for (i = 0; i < dev->pcm_devs * 2; i++) {
|
||||
struct snd_usX2Y_substream *subs = dev->subs[i];
|
||||
struct snd_usx2y_substream *subs = dev->subs[i];
|
||||
if (subs && subs->pcm_substream &&
|
||||
SUBSTREAM_BUSY(subs->pcm_substream))
|
||||
return -EBUSY;
|
||||
@ -603,102 +603,102 @@ static int usX2Y_pcms_busy_check(struct snd_card *card)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int snd_usX2Y_hwdep_pcm_open(struct snd_hwdep *hw, struct file *file)
|
||||
static int snd_usx2y_hwdep_pcm_open(struct snd_hwdep *hw, struct file *file)
|
||||
{
|
||||
struct snd_card *card = hw->card;
|
||||
int err;
|
||||
|
||||
mutex_lock(&usX2Y(card)->pcm_mutex);
|
||||
err = usX2Y_pcms_busy_check(card);
|
||||
mutex_lock(&usx2y(card)->pcm_mutex);
|
||||
err = usx2y_pcms_busy_check(card);
|
||||
if (!err)
|
||||
usX2Y(card)->chip_status |= USX2Y_STAT_CHIP_MMAP_PCM_URBS;
|
||||
mutex_unlock(&usX2Y(card)->pcm_mutex);
|
||||
usx2y(card)->chip_status |= USX2Y_STAT_CHIP_MMAP_PCM_URBS;
|
||||
mutex_unlock(&usx2y(card)->pcm_mutex);
|
||||
return err;
|
||||
}
|
||||
|
||||
|
||||
static int snd_usX2Y_hwdep_pcm_release(struct snd_hwdep *hw, struct file *file)
|
||||
static int snd_usx2y_hwdep_pcm_release(struct snd_hwdep *hw, struct file *file)
|
||||
{
|
||||
struct snd_card *card = hw->card;
|
||||
int err;
|
||||
|
||||
mutex_lock(&usX2Y(card)->pcm_mutex);
|
||||
err = usX2Y_pcms_busy_check(card);
|
||||
mutex_lock(&usx2y(card)->pcm_mutex);
|
||||
err = usx2y_pcms_busy_check(card);
|
||||
if (!err)
|
||||
usX2Y(hw->card)->chip_status &= ~USX2Y_STAT_CHIP_MMAP_PCM_URBS;
|
||||
mutex_unlock(&usX2Y(card)->pcm_mutex);
|
||||
usx2y(hw->card)->chip_status &= ~USX2Y_STAT_CHIP_MMAP_PCM_URBS;
|
||||
mutex_unlock(&usx2y(card)->pcm_mutex);
|
||||
return err;
|
||||
}
|
||||
|
||||
|
||||
static void snd_usX2Y_hwdep_pcm_vm_open(struct vm_area_struct *area)
|
||||
static void snd_usx2y_hwdep_pcm_vm_open(struct vm_area_struct *area)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
static void snd_usX2Y_hwdep_pcm_vm_close(struct vm_area_struct *area)
|
||||
static void snd_usx2y_hwdep_pcm_vm_close(struct vm_area_struct *area)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
static vm_fault_t snd_usX2Y_hwdep_pcm_vm_fault(struct vm_fault *vmf)
|
||||
static vm_fault_t snd_usx2y_hwdep_pcm_vm_fault(struct vm_fault *vmf)
|
||||
{
|
||||
unsigned long offset;
|
||||
void *vaddr;
|
||||
|
||||
offset = vmf->pgoff << PAGE_SHIFT;
|
||||
vaddr = (char *)((struct usX2Ydev *)vmf->vma->vm_private_data)->hwdep_pcm_shm + offset;
|
||||
vaddr = (char *)((struct usx2ydev *)vmf->vma->vm_private_data)->hwdep_pcm_shm + offset;
|
||||
vmf->page = virt_to_page(vaddr);
|
||||
get_page(vmf->page);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static const struct vm_operations_struct snd_usX2Y_hwdep_pcm_vm_ops = {
|
||||
.open = snd_usX2Y_hwdep_pcm_vm_open,
|
||||
.close = snd_usX2Y_hwdep_pcm_vm_close,
|
||||
.fault = snd_usX2Y_hwdep_pcm_vm_fault,
|
||||
static const struct vm_operations_struct snd_usx2y_hwdep_pcm_vm_ops = {
|
||||
.open = snd_usx2y_hwdep_pcm_vm_open,
|
||||
.close = snd_usx2y_hwdep_pcm_vm_close,
|
||||
.fault = snd_usx2y_hwdep_pcm_vm_fault,
|
||||
};
|
||||
|
||||
|
||||
static int snd_usX2Y_hwdep_pcm_mmap(struct snd_hwdep * hw, struct file *filp, struct vm_area_struct *area)
|
||||
static int snd_usx2y_hwdep_pcm_mmap(struct snd_hwdep * hw, struct file *filp, struct vm_area_struct *area)
|
||||
{
|
||||
unsigned long size = (unsigned long)(area->vm_end - area->vm_start);
|
||||
struct usX2Ydev *usX2Y = hw->private_data;
|
||||
struct usx2ydev *usx2y = hw->private_data;
|
||||
|
||||
if (!(usX2Y->chip_status & USX2Y_STAT_CHIP_INIT))
|
||||
if (!(usx2y->chip_status & USX2Y_STAT_CHIP_INIT))
|
||||
return -EBUSY;
|
||||
|
||||
/* if userspace tries to mmap beyond end of our buffer, fail */
|
||||
if (size > PAGE_ALIGN(sizeof(struct snd_usX2Y_hwdep_pcm_shm))) {
|
||||
snd_printd("%lu > %lu\n", size, (unsigned long)sizeof(struct snd_usX2Y_hwdep_pcm_shm));
|
||||
if (size > PAGE_ALIGN(sizeof(struct snd_usx2y_hwdep_pcm_shm))) {
|
||||
snd_printd("%lu > %lu\n", size, (unsigned long)sizeof(struct snd_usx2y_hwdep_pcm_shm));
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
if (!usX2Y->hwdep_pcm_shm) {
|
||||
if (!usx2y->hwdep_pcm_shm) {
|
||||
return -ENODEV;
|
||||
}
|
||||
area->vm_ops = &snd_usX2Y_hwdep_pcm_vm_ops;
|
||||
area->vm_ops = &snd_usx2y_hwdep_pcm_vm_ops;
|
||||
area->vm_flags |= VM_DONTEXPAND | VM_DONTDUMP;
|
||||
area->vm_private_data = hw->private_data;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static void snd_usX2Y_hwdep_pcm_private_free(struct snd_hwdep *hwdep)
|
||||
static void snd_usx2y_hwdep_pcm_private_free(struct snd_hwdep *hwdep)
|
||||
{
|
||||
struct usX2Ydev *usX2Y = hwdep->private_data;
|
||||
if (NULL != usX2Y->hwdep_pcm_shm)
|
||||
free_pages_exact(usX2Y->hwdep_pcm_shm, sizeof(struct snd_usX2Y_hwdep_pcm_shm));
|
||||
struct usx2ydev *usx2y = hwdep->private_data;
|
||||
if (NULL != usx2y->hwdep_pcm_shm)
|
||||
free_pages_exact(usx2y->hwdep_pcm_shm, sizeof(struct snd_usx2y_hwdep_pcm_shm));
|
||||
}
|
||||
|
||||
|
||||
int usX2Y_hwdep_pcm_new(struct snd_card *card)
|
||||
int usx2y_hwdep_pcm_new(struct snd_card *card)
|
||||
{
|
||||
int err;
|
||||
struct snd_hwdep *hw;
|
||||
struct snd_pcm *pcm;
|
||||
struct usb_device *dev = usX2Y(card)->dev;
|
||||
struct usb_device *dev = usx2y(card)->dev;
|
||||
if (1 != nr_of_packs())
|
||||
return 0;
|
||||
|
||||
@ -706,11 +706,11 @@ int usX2Y_hwdep_pcm_new(struct snd_card *card)
|
||||
return err;
|
||||
|
||||
hw->iface = SNDRV_HWDEP_IFACE_USX2Y_PCM;
|
||||
hw->private_data = usX2Y(card);
|
||||
hw->private_free = snd_usX2Y_hwdep_pcm_private_free;
|
||||
hw->ops.open = snd_usX2Y_hwdep_pcm_open;
|
||||
hw->ops.release = snd_usX2Y_hwdep_pcm_release;
|
||||
hw->ops.mmap = snd_usX2Y_hwdep_pcm_mmap;
|
||||
hw->private_data = usx2y(card);
|
||||
hw->private_free = snd_usx2y_hwdep_pcm_private_free;
|
||||
hw->ops.open = snd_usx2y_hwdep_pcm_open;
|
||||
hw->ops.release = snd_usx2y_hwdep_pcm_release;
|
||||
hw->ops.mmap = snd_usx2y_hwdep_pcm_mmap;
|
||||
hw->exclusive = 1;
|
||||
sprintf(hw->name, "/dev/bus/usb/%03d/%03d/hwdeppcm", dev->bus->busnum, dev->devnum);
|
||||
|
||||
@ -718,10 +718,10 @@ int usX2Y_hwdep_pcm_new(struct snd_card *card)
|
||||
if (err < 0) {
|
||||
return err;
|
||||
}
|
||||
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, &snd_usX2Y_usbpcm_ops);
|
||||
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE, &snd_usX2Y_usbpcm_ops);
|
||||
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, &snd_usx2y_usbpcm_ops);
|
||||
snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE, &snd_usx2y_usbpcm_ops);
|
||||
|
||||
pcm->private_data = usX2Y(card)->subs;
|
||||
pcm->private_data = usx2y(card)->subs;
|
||||
pcm->info_flags = 0;
|
||||
|
||||
sprintf(pcm->name, NAME_ALLCAPS" hwdep Audio");
|
||||
@ -739,7 +739,7 @@ int usX2Y_hwdep_pcm_new(struct snd_card *card)
|
||||
|
||||
#else
|
||||
|
||||
int usX2Y_hwdep_pcm_new(struct snd_card *card)
|
||||
int usx2y_hwdep_pcm_new(struct snd_card *card)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
@ -4,7 +4,7 @@
|
||||
#define MAXSTRIDE 3
|
||||
|
||||
#define SSS (((MAXPACK*MAXBUFFERMS*MAXSTRIDE + 4096) / 4096) * 4096)
|
||||
struct snd_usX2Y_hwdep_pcm_shm {
|
||||
struct snd_usx2y_hwdep_pcm_shm {
|
||||
char playback[SSS];
|
||||
char capture0x8[SSS];
|
||||
char capture0xA[SSS];
|
||||
@ -20,4 +20,4 @@ struct snd_usX2Y_hwdep_pcm_shm {
|
||||
int capture_iso_start;
|
||||
};
|
||||
|
||||
int usX2Y_hwdep_pcm_new(struct snd_card *card);
|
||||
int usx2y_hwdep_pcm_new(struct snd_card *card);
|
||||
|
Loading…
Reference in New Issue
Block a user