mirror of
https://github.com/edk2-porting/linux-next.git
synced 2024-12-21 11:44:01 +08:00
sound fixes for 4.5-rc4
In this rc, we've got more volume than previous rc, unsurprisingly; the majority of updates in ASoC are about Intel drivers, and another major changes are the continued plumbing of ALSA timer bugs revealed by syzkaller fuzzer. Hopefully both settle down now. Other than that, HD-audio received a couple of code fixes as well as the usual quirks, and various small fixes are found for FireWire devices, ASoC codecs and drivers. -----BEGIN PGP SIGNATURE----- Version: GnuPG v2 iQIcBAABCAAGBQJWvaEAAAoJEGwxgFQ9KSmkIoAP/j3wwbGhEm5EmJaoUurgOrSv wrrFulUT6okCUfOoJMnn4nmW/8iYGS7ZsUTPOfcLYndnx0hAPVsQVIdSIIQJ8Adf pU+9KzdGCuZt9cblZthQePXQa6FKByfURQ3ycMWTy0PGUDE8IoR79C8p829cjrdt 0xFp64G2oEqCLHDPDpgkp6fGbA6YKKUYWFNuM+fJ99oDNnFkaHfaRCYy7dvL7QqY 0rpOyn6wnwjmmF2ng9YE0yqLf8s7fGHzwq8kHfklFoZyhaqA7iB8yeIZwDo536co m1Vl2KAhv+droGr6uXT+vASMTqkRBRf+8b0Y8+sCWpRLsBOJX4vAY7iQRC9MiHMM A7zIXPVHeRheb+GReujoJ+RSqB8xyuN0zcMUInQogVkI6C1APt8AkPxYXXWGBASO 04Dr+Z7frm6taQpXyOw65p5btmb5QhC9zmi79fmEk9ZMdFze74SFimpODm4u079u lM8wQPbRKx8cWfg/7y7M6cyZQYaYCNjy2dIl8ICyQkxB4d94aE+75hSvvHc2knJb IDg5orF39rK1MrQk3pjGKyoghDxMWLkVdSBi75zWsBED7jf/jtlhEy1Q7UAvaRok 1CdxeBhQf4PTcYEz9jTRZbmXNL55r/DMKaAwJOJhDLg3HHamq86+1Zi7YlNB8C0O mLIjktpkIHAZZ/Xwomfq =60er -----END PGP SIGNATURE----- Merge tag 'sound-4.5-rc4' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound Pull sound fixes from Takashi Iwai: "In this rc, we've got more volume than previous rc, unsurprisingly; the majority of updates in ASoC are about Intel drivers, and another major changes are the continued plumbing of ALSA timer bugs revealed by syzkaller fuzzer. Hopefully both settle down now. Other than that, HD-audio received a couple of code fixes as well as the usual quirks, and various small fixes are found for FireWire devices, ASoC codecs and drivers" * tag 'sound-4.5-rc4' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound: (50 commits) ASoC: arizona: fref must be limited in pseudo-fractional mode ASoC: sigmadsp: Fix missleading return value ALSA: timer: Fix race at concurrent reads ALSA: firewire-digi00x: Drop bogus const type qualifier on dot_scrt() ALSA: hda - Fix bad dereference of jack object ALSA: timer: Fix race between stop and interrupt ALSA: timer: Fix wrong instance passed to slave callbacks ASoC: Intel: Add module tags for common match module ASoC: Intel: Load the atom DPCM driver only ASoC: Intel: Create independent acpi match module ASoC: Intel: Revert "ASoC: Intel: fix ACPI probe regression with Atom DPCM driver" ALSA: dummy: Implement timer backend switching more safely ALSA: hda - Fix speaker output from VAIO AiO machines Revert "ALSA: hda - Fix noise on Gigabyte Z170X mobo" ALSA: firewire-tascam: remove needless member for control and status message ALSA: firewire-tascam: remove a flag for controller ALSA: firewire-tascam: add support for FW-1804 ALSA: firewire-tascam: fix NULL pointer dereference when model identification fails ALSA: hda - Fix static checker warning in patch_hdmi.c ASoC: Intel: Skylake: Remove autosuspend delay ...
This commit is contained in:
commit
0df34ad9b7
@ -30,6 +30,8 @@ The compatible list for this generic sound card currently:
|
||||
"fsl,imx-audio-sgtl5000"
|
||||
(compatible with Documentation/devicetree/bindings/sound/imx-audio-sgtl5000.txt)
|
||||
|
||||
"fsl,imx-audio-wm8960"
|
||||
|
||||
Required properties:
|
||||
|
||||
- compatible : Contains one of entries in the compatible list.
|
||||
|
@ -422,7 +422,7 @@ static void snd_timer_notify1(struct snd_timer_instance *ti, int event)
|
||||
spin_lock_irqsave(&timer->lock, flags);
|
||||
list_for_each_entry(ts, &ti->slave_active_head, active_list)
|
||||
if (ts->ccallback)
|
||||
ts->ccallback(ti, event + 100, &tstamp, resolution);
|
||||
ts->ccallback(ts, event + 100, &tstamp, resolution);
|
||||
spin_unlock_irqrestore(&timer->lock, flags);
|
||||
}
|
||||
|
||||
@ -518,9 +518,13 @@ static int _snd_timer_stop(struct snd_timer_instance *timeri, int event)
|
||||
spin_unlock_irqrestore(&slave_active_lock, flags);
|
||||
return -EBUSY;
|
||||
}
|
||||
if (timeri->timer)
|
||||
spin_lock(&timeri->timer->lock);
|
||||
timeri->flags &= ~SNDRV_TIMER_IFLG_RUNNING;
|
||||
list_del_init(&timeri->ack_list);
|
||||
list_del_init(&timeri->active_list);
|
||||
if (timeri->timer)
|
||||
spin_unlock(&timeri->timer->lock);
|
||||
spin_unlock_irqrestore(&slave_active_lock, flags);
|
||||
goto __end;
|
||||
}
|
||||
@ -1929,6 +1933,7 @@ static ssize_t snd_timer_user_read(struct file *file, char __user *buffer,
|
||||
{
|
||||
struct snd_timer_user *tu;
|
||||
long result = 0, unit;
|
||||
int qhead;
|
||||
int err = 0;
|
||||
|
||||
tu = file->private_data;
|
||||
@ -1940,7 +1945,7 @@ static ssize_t snd_timer_user_read(struct file *file, char __user *buffer,
|
||||
|
||||
if ((file->f_flags & O_NONBLOCK) != 0 || result > 0) {
|
||||
err = -EAGAIN;
|
||||
break;
|
||||
goto _error;
|
||||
}
|
||||
|
||||
set_current_state(TASK_INTERRUPTIBLE);
|
||||
@ -1955,42 +1960,37 @@ static ssize_t snd_timer_user_read(struct file *file, char __user *buffer,
|
||||
|
||||
if (tu->disconnected) {
|
||||
err = -ENODEV;
|
||||
break;
|
||||
goto _error;
|
||||
}
|
||||
if (signal_pending(current)) {
|
||||
err = -ERESTARTSYS;
|
||||
break;
|
||||
goto _error;
|
||||
}
|
||||
}
|
||||
|
||||
qhead = tu->qhead++;
|
||||
tu->qhead %= tu->queue_size;
|
||||
spin_unlock_irq(&tu->qlock);
|
||||
if (err < 0)
|
||||
goto _error;
|
||||
|
||||
if (tu->tread) {
|
||||
if (copy_to_user(buffer, &tu->tqueue[tu->qhead++],
|
||||
sizeof(struct snd_timer_tread))) {
|
||||
if (copy_to_user(buffer, &tu->tqueue[qhead],
|
||||
sizeof(struct snd_timer_tread)))
|
||||
err = -EFAULT;
|
||||
goto _error;
|
||||
}
|
||||
} else {
|
||||
if (copy_to_user(buffer, &tu->queue[tu->qhead++],
|
||||
sizeof(struct snd_timer_read))) {
|
||||
if (copy_to_user(buffer, &tu->queue[qhead],
|
||||
sizeof(struct snd_timer_read)))
|
||||
err = -EFAULT;
|
||||
goto _error;
|
||||
}
|
||||
}
|
||||
|
||||
tu->qhead %= tu->queue_size;
|
||||
|
||||
result += unit;
|
||||
buffer += unit;
|
||||
|
||||
spin_lock_irq(&tu->qlock);
|
||||
tu->qused--;
|
||||
if (err < 0)
|
||||
goto _error;
|
||||
result += unit;
|
||||
buffer += unit;
|
||||
}
|
||||
spin_unlock_irq(&tu->qlock);
|
||||
_error:
|
||||
spin_unlock_irq(&tu->qlock);
|
||||
return result > 0 ? result : err;
|
||||
}
|
||||
|
||||
|
@ -87,7 +87,7 @@ MODULE_PARM_DESC(pcm_substreams, "PCM substreams # (1-128) for dummy driver.");
|
||||
module_param(fake_buffer, bool, 0444);
|
||||
MODULE_PARM_DESC(fake_buffer, "Fake buffer allocations.");
|
||||
#ifdef CONFIG_HIGH_RES_TIMERS
|
||||
module_param(hrtimer, bool, 0444);
|
||||
module_param(hrtimer, bool, 0644);
|
||||
MODULE_PARM_DESC(hrtimer, "Use hrtimer as the timer source.");
|
||||
#endif
|
||||
|
||||
@ -109,6 +109,9 @@ struct dummy_timer_ops {
|
||||
snd_pcm_uframes_t (*pointer)(struct snd_pcm_substream *);
|
||||
};
|
||||
|
||||
#define get_dummy_ops(substream) \
|
||||
(*(const struct dummy_timer_ops **)(substream)->runtime->private_data)
|
||||
|
||||
struct dummy_model {
|
||||
const char *name;
|
||||
int (*playback_constraints)(struct snd_pcm_runtime *runtime);
|
||||
@ -137,7 +140,6 @@ struct snd_dummy {
|
||||
int iobox;
|
||||
struct snd_kcontrol *cd_volume_ctl;
|
||||
struct snd_kcontrol *cd_switch_ctl;
|
||||
const struct dummy_timer_ops *timer_ops;
|
||||
};
|
||||
|
||||
/*
|
||||
@ -231,6 +233,8 @@ static struct dummy_model *dummy_models[] = {
|
||||
*/
|
||||
|
||||
struct dummy_systimer_pcm {
|
||||
/* ops must be the first item */
|
||||
const struct dummy_timer_ops *timer_ops;
|
||||
spinlock_t lock;
|
||||
struct timer_list timer;
|
||||
unsigned long base_time;
|
||||
@ -366,6 +370,8 @@ static const struct dummy_timer_ops dummy_systimer_ops = {
|
||||
*/
|
||||
|
||||
struct dummy_hrtimer_pcm {
|
||||
/* ops must be the first item */
|
||||
const struct dummy_timer_ops *timer_ops;
|
||||
ktime_t base_time;
|
||||
ktime_t period_time;
|
||||
atomic_t running;
|
||||
@ -492,31 +498,25 @@ static const struct dummy_timer_ops dummy_hrtimer_ops = {
|
||||
|
||||
static int dummy_pcm_trigger(struct snd_pcm_substream *substream, int cmd)
|
||||
{
|
||||
struct snd_dummy *dummy = snd_pcm_substream_chip(substream);
|
||||
|
||||
switch (cmd) {
|
||||
case SNDRV_PCM_TRIGGER_START:
|
||||
case SNDRV_PCM_TRIGGER_RESUME:
|
||||
return dummy->timer_ops->start(substream);
|
||||
return get_dummy_ops(substream)->start(substream);
|
||||
case SNDRV_PCM_TRIGGER_STOP:
|
||||
case SNDRV_PCM_TRIGGER_SUSPEND:
|
||||
return dummy->timer_ops->stop(substream);
|
||||
return get_dummy_ops(substream)->stop(substream);
|
||||
}
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
static int dummy_pcm_prepare(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_dummy *dummy = snd_pcm_substream_chip(substream);
|
||||
|
||||
return dummy->timer_ops->prepare(substream);
|
||||
return get_dummy_ops(substream)->prepare(substream);
|
||||
}
|
||||
|
||||
static snd_pcm_uframes_t dummy_pcm_pointer(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_dummy *dummy = snd_pcm_substream_chip(substream);
|
||||
|
||||
return dummy->timer_ops->pointer(substream);
|
||||
return get_dummy_ops(substream)->pointer(substream);
|
||||
}
|
||||
|
||||
static struct snd_pcm_hardware dummy_pcm_hardware = {
|
||||
@ -562,17 +562,19 @@ static int dummy_pcm_open(struct snd_pcm_substream *substream)
|
||||
struct snd_dummy *dummy = snd_pcm_substream_chip(substream);
|
||||
struct dummy_model *model = dummy->model;
|
||||
struct snd_pcm_runtime *runtime = substream->runtime;
|
||||
const struct dummy_timer_ops *ops;
|
||||
int err;
|
||||
|
||||
dummy->timer_ops = &dummy_systimer_ops;
|
||||
ops = &dummy_systimer_ops;
|
||||
#ifdef CONFIG_HIGH_RES_TIMERS
|
||||
if (hrtimer)
|
||||
dummy->timer_ops = &dummy_hrtimer_ops;
|
||||
ops = &dummy_hrtimer_ops;
|
||||
#endif
|
||||
|
||||
err = dummy->timer_ops->create(substream);
|
||||
err = ops->create(substream);
|
||||
if (err < 0)
|
||||
return err;
|
||||
get_dummy_ops(substream) = ops;
|
||||
|
||||
runtime->hw = dummy->pcm_hw;
|
||||
if (substream->pcm->device & 1) {
|
||||
@ -594,7 +596,7 @@ static int dummy_pcm_open(struct snd_pcm_substream *substream)
|
||||
err = model->capture_constraints(substream->runtime);
|
||||
}
|
||||
if (err < 0) {
|
||||
dummy->timer_ops->free(substream);
|
||||
get_dummy_ops(substream)->free(substream);
|
||||
return err;
|
||||
}
|
||||
return 0;
|
||||
@ -602,8 +604,7 @@ static int dummy_pcm_open(struct snd_pcm_substream *substream)
|
||||
|
||||
static int dummy_pcm_close(struct snd_pcm_substream *substream)
|
||||
{
|
||||
struct snd_dummy *dummy = snd_pcm_substream_chip(substream);
|
||||
dummy->timer_ops->free(substream);
|
||||
get_dummy_ops(substream)->free(substream);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -63,7 +63,7 @@ struct amdtp_dot {
|
||||
#define BYTE_PER_SAMPLE (4)
|
||||
#define MAGIC_DOT_BYTE (2)
|
||||
#define MAGIC_BYTE_OFF(x) (((x) * BYTE_PER_SAMPLE) + MAGIC_DOT_BYTE)
|
||||
static const u8 dot_scrt(const u8 idx, const unsigned int off)
|
||||
static u8 dot_scrt(const u8 idx, const unsigned int off)
|
||||
{
|
||||
/*
|
||||
* the length of the added pattern only depends on the lower nibble
|
||||
|
@ -230,6 +230,7 @@ int snd_tscm_transaction_register(struct snd_tscm *tscm)
|
||||
return err;
|
||||
error:
|
||||
fw_core_remove_address_handler(&tscm->async_handler);
|
||||
tscm->async_handler.callback_data = NULL;
|
||||
return err;
|
||||
}
|
||||
|
||||
@ -276,6 +277,9 @@ void snd_tscm_transaction_unregister(struct snd_tscm *tscm)
|
||||
__be32 reg;
|
||||
unsigned int i;
|
||||
|
||||
if (tscm->async_handler.callback_data == NULL)
|
||||
return;
|
||||
|
||||
/* Turn off FireWire LED. */
|
||||
reg = cpu_to_be32(0x0000008e);
|
||||
snd_fw_transaction(tscm->unit, TCODE_WRITE_QUADLET_REQUEST,
|
||||
@ -297,6 +301,8 @@ void snd_tscm_transaction_unregister(struct snd_tscm *tscm)
|
||||
®, sizeof(reg), 0);
|
||||
|
||||
fw_core_remove_address_handler(&tscm->async_handler);
|
||||
tscm->async_handler.callback_data = NULL;
|
||||
|
||||
for (i = 0; i < TSCM_MIDI_OUT_PORT_MAX; i++)
|
||||
snd_fw_async_midi_port_destroy(&tscm->out_ports[i]);
|
||||
}
|
||||
|
@ -21,7 +21,6 @@ static struct snd_tscm_spec model_specs[] = {
|
||||
.pcm_playback_analog_channels = 8,
|
||||
.midi_capture_ports = 4,
|
||||
.midi_playback_ports = 4,
|
||||
.is_controller = true,
|
||||
},
|
||||
{
|
||||
.name = "FW-1082",
|
||||
@ -31,9 +30,16 @@ static struct snd_tscm_spec model_specs[] = {
|
||||
.pcm_playback_analog_channels = 2,
|
||||
.midi_capture_ports = 2,
|
||||
.midi_playback_ports = 2,
|
||||
.is_controller = true,
|
||||
},
|
||||
/* FW-1804 may be supported. */
|
||||
{
|
||||
.name = "FW-1804",
|
||||
.has_adat = true,
|
||||
.has_spdif = true,
|
||||
.pcm_capture_analog_channels = 8,
|
||||
.pcm_playback_analog_channels = 2,
|
||||
.midi_capture_ports = 2,
|
||||
.midi_playback_ports = 4,
|
||||
},
|
||||
};
|
||||
|
||||
static int identify_model(struct snd_tscm *tscm)
|
||||
|
@ -39,7 +39,6 @@ struct snd_tscm_spec {
|
||||
unsigned int pcm_playback_analog_channels;
|
||||
unsigned int midi_capture_ports;
|
||||
unsigned int midi_playback_ports;
|
||||
bool is_controller;
|
||||
};
|
||||
|
||||
#define TSCM_MIDI_IN_PORT_MAX 4
|
||||
@ -72,9 +71,6 @@ struct snd_tscm {
|
||||
struct snd_fw_async_midi_port out_ports[TSCM_MIDI_OUT_PORT_MAX];
|
||||
u8 running_status[TSCM_MIDI_OUT_PORT_MAX];
|
||||
bool on_sysex[TSCM_MIDI_OUT_PORT_MAX];
|
||||
|
||||
/* For control messages. */
|
||||
struct snd_firewire_tascam_status *status;
|
||||
};
|
||||
|
||||
#define TSCM_ADDR_BASE 0xffff00000000ull
|
||||
|
@ -4028,9 +4028,9 @@ static void pin_power_callback(struct hda_codec *codec,
|
||||
struct hda_jack_callback *jack,
|
||||
bool on)
|
||||
{
|
||||
if (jack && jack->tbl->nid)
|
||||
if (jack && jack->nid)
|
||||
sync_power_state_change(codec,
|
||||
set_pin_power_jack(codec, jack->tbl->nid, on));
|
||||
set_pin_power_jack(codec, jack->nid, on));
|
||||
}
|
||||
|
||||
/* callback only doing power up -- called at first */
|
||||
|
@ -259,7 +259,7 @@ snd_hda_jack_detect_enable_callback(struct hda_codec *codec, hda_nid_t nid,
|
||||
if (!callback)
|
||||
return ERR_PTR(-ENOMEM);
|
||||
callback->func = func;
|
||||
callback->tbl = jack;
|
||||
callback->nid = jack->nid;
|
||||
callback->next = jack->callback;
|
||||
jack->callback = callback;
|
||||
}
|
||||
|
@ -21,7 +21,7 @@ struct hda_jack_callback;
|
||||
typedef void (*hda_jack_callback_fn) (struct hda_codec *, struct hda_jack_callback *);
|
||||
|
||||
struct hda_jack_callback {
|
||||
struct hda_jack_tbl *tbl;
|
||||
hda_nid_t nid;
|
||||
hda_jack_callback_fn func;
|
||||
unsigned int private_data; /* arbitrary data */
|
||||
struct hda_jack_callback *next;
|
||||
|
@ -4427,13 +4427,16 @@ static void ca0132_process_dsp_response(struct hda_codec *codec,
|
||||
static void hp_callback(struct hda_codec *codec, struct hda_jack_callback *cb)
|
||||
{
|
||||
struct ca0132_spec *spec = codec->spec;
|
||||
struct hda_jack_tbl *tbl;
|
||||
|
||||
/* Delay enabling the HP amp, to let the mic-detection
|
||||
* state machine run.
|
||||
*/
|
||||
cancel_delayed_work_sync(&spec->unsol_hp_work);
|
||||
schedule_delayed_work(&spec->unsol_hp_work, msecs_to_jiffies(500));
|
||||
cb->tbl->block_report = 1;
|
||||
tbl = snd_hda_jack_tbl_get(codec, cb->nid);
|
||||
if (tbl)
|
||||
tbl->block_report = 1;
|
||||
}
|
||||
|
||||
static void amic_callback(struct hda_codec *codec, struct hda_jack_callback *cb)
|
||||
|
@ -448,7 +448,8 @@ static int hdmi_eld_ctl_get(struct snd_kcontrol *kcontrol,
|
||||
eld = &per_pin->sink_eld;
|
||||
|
||||
mutex_lock(&per_pin->lock);
|
||||
if (eld->eld_size > ARRAY_SIZE(ucontrol->value.bytes.data)) {
|
||||
if (eld->eld_size > ARRAY_SIZE(ucontrol->value.bytes.data) ||
|
||||
eld->eld_size > ELD_MAX_SIZE) {
|
||||
mutex_unlock(&per_pin->lock);
|
||||
snd_BUG();
|
||||
return -EINVAL;
|
||||
@ -1193,7 +1194,7 @@ static void check_presence_and_report(struct hda_codec *codec, hda_nid_t nid)
|
||||
static void jack_callback(struct hda_codec *codec,
|
||||
struct hda_jack_callback *jack)
|
||||
{
|
||||
check_presence_and_report(codec, jack->tbl->nid);
|
||||
check_presence_and_report(codec, jack->nid);
|
||||
}
|
||||
|
||||
static void hdmi_intrinsic_event(struct hda_codec *codec, unsigned int res)
|
||||
|
@ -282,7 +282,7 @@ static void alc_update_knob_master(struct hda_codec *codec,
|
||||
uctl = kzalloc(sizeof(*uctl), GFP_KERNEL);
|
||||
if (!uctl)
|
||||
return;
|
||||
val = snd_hda_codec_read(codec, jack->tbl->nid, 0,
|
||||
val = snd_hda_codec_read(codec, jack->nid, 0,
|
||||
AC_VERB_GET_VOLUME_KNOB_CONTROL, 0);
|
||||
val &= HDA_AMP_VOLMASK;
|
||||
uctl->value.integer.value[0] = val;
|
||||
@ -1787,7 +1787,6 @@ enum {
|
||||
ALC882_FIXUP_NO_PRIMARY_HP,
|
||||
ALC887_FIXUP_ASUS_BASS,
|
||||
ALC887_FIXUP_BASS_CHMAP,
|
||||
ALC882_FIXUP_DISABLE_AAMIX,
|
||||
};
|
||||
|
||||
static void alc889_fixup_coef(struct hda_codec *codec,
|
||||
@ -1949,8 +1948,6 @@ static void alc882_fixup_no_primary_hp(struct hda_codec *codec,
|
||||
|
||||
static void alc_fixup_bass_chmap(struct hda_codec *codec,
|
||||
const struct hda_fixup *fix, int action);
|
||||
static void alc_fixup_disable_aamix(struct hda_codec *codec,
|
||||
const struct hda_fixup *fix, int action);
|
||||
|
||||
static const struct hda_fixup alc882_fixups[] = {
|
||||
[ALC882_FIXUP_ABIT_AW9D_MAX] = {
|
||||
@ -2188,10 +2185,6 @@ static const struct hda_fixup alc882_fixups[] = {
|
||||
.type = HDA_FIXUP_FUNC,
|
||||
.v.func = alc_fixup_bass_chmap,
|
||||
},
|
||||
[ALC882_FIXUP_DISABLE_AAMIX] = {
|
||||
.type = HDA_FIXUP_FUNC,
|
||||
.v.func = alc_fixup_disable_aamix,
|
||||
},
|
||||
};
|
||||
|
||||
static const struct snd_pci_quirk alc882_fixup_tbl[] = {
|
||||
@ -2230,6 +2223,7 @@ static const struct snd_pci_quirk alc882_fixup_tbl[] = {
|
||||
SND_PCI_QUIRK(0x104d, 0x9047, "Sony Vaio TT", ALC889_FIXUP_VAIO_TT),
|
||||
SND_PCI_QUIRK(0x104d, 0x905a, "Sony Vaio Z", ALC882_FIXUP_NO_PRIMARY_HP),
|
||||
SND_PCI_QUIRK(0x104d, 0x9043, "Sony Vaio VGC-LN51JGB", ALC882_FIXUP_NO_PRIMARY_HP),
|
||||
SND_PCI_QUIRK(0x104d, 0x9044, "Sony VAIO AiO", ALC882_FIXUP_NO_PRIMARY_HP),
|
||||
|
||||
/* All Apple entries are in codec SSIDs */
|
||||
SND_PCI_QUIRK(0x106b, 0x00a0, "MacBookPro 3,1", ALC889_FIXUP_MBP_VREF),
|
||||
@ -2259,7 +2253,6 @@ static const struct snd_pci_quirk alc882_fixup_tbl[] = {
|
||||
SND_PCI_QUIRK(0x1462, 0x7350, "MSI-7350", ALC889_FIXUP_CD),
|
||||
SND_PCI_QUIRK_VENDOR(0x1462, "MSI", ALC882_FIXUP_GPIO3),
|
||||
SND_PCI_QUIRK(0x1458, 0xa002, "Gigabyte EP45-DS3/Z87X-UD3H", ALC889_FIXUP_FRONT_HP_NO_PRESENCE),
|
||||
SND_PCI_QUIRK(0x1458, 0xa182, "Gigabyte Z170X-UD3", ALC882_FIXUP_DISABLE_AAMIX),
|
||||
SND_PCI_QUIRK(0x147b, 0x107a, "Abit AW9D-MAX", ALC882_FIXUP_ABIT_AW9D_MAX),
|
||||
SND_PCI_QUIRK_VENDOR(0x1558, "Clevo laptop", ALC882_FIXUP_EAPD),
|
||||
SND_PCI_QUIRK(0x161f, 0x2054, "Medion laptop", ALC883_FIXUP_EAPD),
|
||||
|
@ -493,9 +493,9 @@ static void jack_update_power(struct hda_codec *codec,
|
||||
if (!spec->num_pwrs)
|
||||
return;
|
||||
|
||||
if (jack && jack->tbl->nid) {
|
||||
stac_toggle_power_map(codec, jack->tbl->nid,
|
||||
snd_hda_jack_detect(codec, jack->tbl->nid),
|
||||
if (jack && jack->nid) {
|
||||
stac_toggle_power_map(codec, jack->nid,
|
||||
snd_hda_jack_detect(codec, jack->nid),
|
||||
true);
|
||||
return;
|
||||
}
|
||||
|
@ -635,6 +635,7 @@ static int acp_dma_open(struct snd_pcm_substream *substream)
|
||||
SNDRV_PCM_HW_PARAM_PERIODS);
|
||||
if (ret < 0) {
|
||||
dev_err(prtd->platform->dev, "set integer constraint failed\n");
|
||||
kfree(adata);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -1929,6 +1929,25 @@ static struct {
|
||||
{ 1000000, 13500000, 0, 1 },
|
||||
};
|
||||
|
||||
static const unsigned int pseudo_fref_max[ARIZONA_FLL_MAX_FRATIO] = {
|
||||
13500000,
|
||||
6144000,
|
||||
6144000,
|
||||
3072000,
|
||||
3072000,
|
||||
2822400,
|
||||
2822400,
|
||||
1536000,
|
||||
1536000,
|
||||
1536000,
|
||||
1536000,
|
||||
1536000,
|
||||
1536000,
|
||||
1536000,
|
||||
1536000,
|
||||
768000,
|
||||
};
|
||||
|
||||
static struct {
|
||||
unsigned int min;
|
||||
unsigned int max;
|
||||
@ -2042,16 +2061,32 @@ static int arizona_calc_fratio(struct arizona_fll *fll,
|
||||
/* Adjust FRATIO/refdiv to avoid integer mode if possible */
|
||||
refdiv = cfg->refdiv;
|
||||
|
||||
arizona_fll_dbg(fll, "pseudo: initial ratio=%u fref=%u refdiv=%u\n",
|
||||
init_ratio, Fref, refdiv);
|
||||
|
||||
while (div <= ARIZONA_FLL_MAX_REFDIV) {
|
||||
for (ratio = init_ratio; ratio <= ARIZONA_FLL_MAX_FRATIO;
|
||||
ratio++) {
|
||||
if ((ARIZONA_FLL_VCO_CORNER / 2) /
|
||||
(fll->vco_mult * ratio) < Fref)
|
||||
(fll->vco_mult * ratio) < Fref) {
|
||||
arizona_fll_dbg(fll, "pseudo: hit VCO corner\n");
|
||||
break;
|
||||
}
|
||||
|
||||
if (Fref > pseudo_fref_max[ratio - 1]) {
|
||||
arizona_fll_dbg(fll,
|
||||
"pseudo: exceeded max fref(%u) for ratio=%u\n",
|
||||
pseudo_fref_max[ratio - 1],
|
||||
ratio);
|
||||
break;
|
||||
}
|
||||
|
||||
if (target % (ratio * Fref)) {
|
||||
cfg->refdiv = refdiv;
|
||||
cfg->fratio = ratio - 1;
|
||||
arizona_fll_dbg(fll,
|
||||
"pseudo: found fref=%u refdiv=%d(%d) ratio=%d\n",
|
||||
Fref, refdiv, div, ratio);
|
||||
return ratio;
|
||||
}
|
||||
}
|
||||
@ -2060,6 +2095,9 @@ static int arizona_calc_fratio(struct arizona_fll *fll,
|
||||
if (target % (ratio * Fref)) {
|
||||
cfg->refdiv = refdiv;
|
||||
cfg->fratio = ratio - 1;
|
||||
arizona_fll_dbg(fll,
|
||||
"pseudo: found fref=%u refdiv=%d(%d) ratio=%d\n",
|
||||
Fref, refdiv, div, ratio);
|
||||
return ratio;
|
||||
}
|
||||
}
|
||||
@ -2068,6 +2106,9 @@ static int arizona_calc_fratio(struct arizona_fll *fll,
|
||||
Fref /= 2;
|
||||
refdiv++;
|
||||
init_ratio = arizona_find_fratio(Fref, NULL);
|
||||
arizona_fll_dbg(fll,
|
||||
"pseudo: change fref=%u refdiv=%d(%d) ratio=%u\n",
|
||||
Fref, refdiv, div, init_ratio);
|
||||
}
|
||||
|
||||
arizona_fll_warn(fll, "Falling back to integer mode operation\n");
|
||||
|
@ -266,6 +266,8 @@ static int rt286_jack_detect(struct rt286_priv *rt286, bool *hp, bool *mic)
|
||||
} else {
|
||||
*mic = false;
|
||||
regmap_write(rt286->regmap, RT286_SET_MIC1, 0x20);
|
||||
regmap_update_bits(rt286->regmap,
|
||||
RT286_CBJ_CTRL1, 0x0400, 0x0000);
|
||||
}
|
||||
} else {
|
||||
regmap_read(rt286->regmap, RT286_GET_HP_SENSE, &buf);
|
||||
@ -470,24 +472,6 @@ static int rt286_set_dmic1_event(struct snd_soc_dapm_widget *w,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rt286_vref_event(struct snd_soc_dapm_widget *w,
|
||||
struct snd_kcontrol *kcontrol, int event)
|
||||
{
|
||||
struct snd_soc_codec *codec = snd_soc_dapm_to_codec(w->dapm);
|
||||
|
||||
switch (event) {
|
||||
case SND_SOC_DAPM_PRE_PMU:
|
||||
snd_soc_update_bits(codec,
|
||||
RT286_CBJ_CTRL1, 0x0400, 0x0000);
|
||||
mdelay(50);
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rt286_ldo2_event(struct snd_soc_dapm_widget *w,
|
||||
struct snd_kcontrol *kcontrol, int event)
|
||||
{
|
||||
@ -536,7 +520,7 @@ static const struct snd_soc_dapm_widget rt286_dapm_widgets[] = {
|
||||
SND_SOC_DAPM_SUPPLY_S("HV", 1, RT286_POWER_CTRL1,
|
||||
12, 1, NULL, 0),
|
||||
SND_SOC_DAPM_SUPPLY("VREF", RT286_POWER_CTRL1,
|
||||
0, 1, rt286_vref_event, SND_SOC_DAPM_PRE_PMU),
|
||||
0, 1, NULL, 0),
|
||||
SND_SOC_DAPM_SUPPLY_S("LDO1", 1, RT286_POWER_CTRL2,
|
||||
2, 0, NULL, 0),
|
||||
SND_SOC_DAPM_SUPPLY_S("LDO2", 2, RT286_POWER_CTRL1,
|
||||
@ -910,8 +894,6 @@ static int rt286_set_bias_level(struct snd_soc_codec *codec,
|
||||
|
||||
case SND_SOC_BIAS_ON:
|
||||
mdelay(10);
|
||||
snd_soc_update_bits(codec,
|
||||
RT286_CBJ_CTRL1, 0x0400, 0x0400);
|
||||
snd_soc_update_bits(codec,
|
||||
RT286_DC_GAIN, 0x200, 0x0);
|
||||
|
||||
@ -920,8 +902,6 @@ static int rt286_set_bias_level(struct snd_soc_codec *codec,
|
||||
case SND_SOC_BIAS_STANDBY:
|
||||
snd_soc_write(codec,
|
||||
RT286_SET_AUDIO_POWER, AC_PWRST_D3);
|
||||
snd_soc_update_bits(codec,
|
||||
RT286_CBJ_CTRL1, 0x0400, 0x0000);
|
||||
break;
|
||||
|
||||
default:
|
||||
|
@ -776,7 +776,7 @@ static const struct snd_kcontrol_new rt5645_snd_controls[] = {
|
||||
|
||||
/* IN1/IN2 Control */
|
||||
SOC_SINGLE_TLV("IN1 Boost", RT5645_IN1_CTRL1,
|
||||
RT5645_BST_SFT1, 8, 0, bst_tlv),
|
||||
RT5645_BST_SFT1, 12, 0, bst_tlv),
|
||||
SOC_SINGLE_TLV("IN2 Boost", RT5645_IN2_CTRL,
|
||||
RT5645_BST_SFT2, 8, 0, bst_tlv),
|
||||
|
||||
|
@ -3985,7 +3985,6 @@ static int rt5659_i2c_probe(struct i2c_client *i2c,
|
||||
if (rt5659 == NULL)
|
||||
return -ENOMEM;
|
||||
|
||||
rt5659->i2c = i2c;
|
||||
i2c_set_clientdata(i2c, rt5659);
|
||||
|
||||
if (pdata)
|
||||
@ -4157,24 +4156,17 @@ static int rt5659_i2c_probe(struct i2c_client *i2c,
|
||||
|
||||
INIT_DELAYED_WORK(&rt5659->jack_detect_work, rt5659_jack_detect_work);
|
||||
|
||||
if (rt5659->i2c->irq) {
|
||||
ret = request_threaded_irq(rt5659->i2c->irq, NULL, rt5659_irq,
|
||||
IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING
|
||||
if (i2c->irq) {
|
||||
ret = devm_request_threaded_irq(&i2c->dev, i2c->irq, NULL,
|
||||
rt5659_irq, IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING
|
||||
| IRQF_ONESHOT, "rt5659", rt5659);
|
||||
if (ret)
|
||||
dev_err(&i2c->dev, "Failed to reguest IRQ: %d\n", ret);
|
||||
|
||||
}
|
||||
|
||||
ret = snd_soc_register_codec(&i2c->dev, &soc_codec_dev_rt5659,
|
||||
return snd_soc_register_codec(&i2c->dev, &soc_codec_dev_rt5659,
|
||||
rt5659_dai, ARRAY_SIZE(rt5659_dai));
|
||||
|
||||
if (ret) {
|
||||
if (rt5659->i2c->irq)
|
||||
free_irq(rt5659->i2c->irq, rt5659);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int rt5659_i2c_remove(struct i2c_client *i2c)
|
||||
@ -4191,24 +4183,29 @@ void rt5659_i2c_shutdown(struct i2c_client *client)
|
||||
regmap_write(rt5659->regmap, RT5659_RESET, 0);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
static const struct of_device_id rt5659_of_match[] = {
|
||||
{ .compatible = "realtek,rt5658", },
|
||||
{ .compatible = "realtek,rt5659", },
|
||||
{},
|
||||
{ },
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, rt5659_of_match);
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_ACPI
|
||||
static struct acpi_device_id rt5659_acpi_match[] = {
|
||||
{ "10EC5658", 0},
|
||||
{ "10EC5659", 0},
|
||||
{ },
|
||||
{ "10EC5658", 0, },
|
||||
{ "10EC5659", 0, },
|
||||
{ },
|
||||
};
|
||||
MODULE_DEVICE_TABLE(acpi, rt5659_acpi_match);
|
||||
#endif
|
||||
|
||||
struct i2c_driver rt5659_i2c_driver = {
|
||||
.driver = {
|
||||
.name = "rt5659",
|
||||
.owner = THIS_MODULE,
|
||||
.of_match_table = rt5659_of_match,
|
||||
.of_match_table = of_match_ptr(rt5659_of_match),
|
||||
.acpi_match_table = ACPI_PTR(rt5659_acpi_match),
|
||||
},
|
||||
.probe = rt5659_i2c_probe,
|
||||
|
@ -1792,7 +1792,6 @@ struct rt5659_priv {
|
||||
struct snd_soc_codec *codec;
|
||||
struct rt5659_platform_data pdata;
|
||||
struct regmap *regmap;
|
||||
struct i2c_client *i2c;
|
||||
struct gpio_desc *gpiod_ldo1_en;
|
||||
struct gpio_desc *gpiod_reset;
|
||||
struct snd_soc_jack *hs_jack;
|
||||
|
@ -31,7 +31,10 @@ static int sigmadsp_write_i2c(void *control_data,
|
||||
|
||||
kfree(buf);
|
||||
|
||||
return ret;
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int sigmadsp_read_i2c(void *control_data,
|
||||
|
@ -2382,6 +2382,7 @@ error:
|
||||
|
||||
static int wm5110_remove(struct platform_device *pdev)
|
||||
{
|
||||
snd_soc_unregister_platform(&pdev->dev);
|
||||
snd_soc_unregister_codec(&pdev->dev);
|
||||
pm_runtime_disable(&pdev->dev);
|
||||
|
||||
|
@ -240,13 +240,13 @@ SOC_DOUBLE_R("Capture Volume ZC Switch", WM8960_LINVOL, WM8960_RINVOL,
|
||||
SOC_DOUBLE_R("Capture Switch", WM8960_LINVOL, WM8960_RINVOL,
|
||||
7, 1, 1),
|
||||
|
||||
SOC_SINGLE_TLV("Right Input Boost Mixer RINPUT3 Volume",
|
||||
WM8960_INBMIX1, 4, 7, 0, lineinboost_tlv),
|
||||
SOC_SINGLE_TLV("Right Input Boost Mixer RINPUT2 Volume",
|
||||
WM8960_INBMIX1, 1, 7, 0, lineinboost_tlv),
|
||||
SOC_SINGLE_TLV("Left Input Boost Mixer LINPUT3 Volume",
|
||||
WM8960_INBMIX2, 4, 7, 0, lineinboost_tlv),
|
||||
WM8960_INBMIX1, 4, 7, 0, lineinboost_tlv),
|
||||
SOC_SINGLE_TLV("Left Input Boost Mixer LINPUT2 Volume",
|
||||
WM8960_INBMIX1, 1, 7, 0, lineinboost_tlv),
|
||||
SOC_SINGLE_TLV("Right Input Boost Mixer RINPUT3 Volume",
|
||||
WM8960_INBMIX2, 4, 7, 0, lineinboost_tlv),
|
||||
SOC_SINGLE_TLV("Right Input Boost Mixer RINPUT2 Volume",
|
||||
WM8960_INBMIX2, 1, 7, 0, lineinboost_tlv),
|
||||
SOC_SINGLE_TLV("Right Input Boost Mixer RINPUT1 Volume",
|
||||
WM8960_RINPATH, 4, 3, 0, micboost_tlv),
|
||||
@ -643,29 +643,31 @@ static int wm8960_configure_clocking(struct snd_soc_codec *codec)
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
/* check if the sysclk frequency is available. */
|
||||
for (i = 0; i < ARRAY_SIZE(sysclk_divs); ++i) {
|
||||
if (sysclk_divs[i] == -1)
|
||||
continue;
|
||||
sysclk = freq_out / sysclk_divs[i];
|
||||
for (j = 0; j < ARRAY_SIZE(dac_divs); ++j) {
|
||||
if (sysclk == dac_divs[j] * lrclk) {
|
||||
if (wm8960->clk_id != WM8960_SYSCLK_PLL) {
|
||||
/* check if the sysclk frequency is available. */
|
||||
for (i = 0; i < ARRAY_SIZE(sysclk_divs); ++i) {
|
||||
if (sysclk_divs[i] == -1)
|
||||
continue;
|
||||
sysclk = freq_out / sysclk_divs[i];
|
||||
for (j = 0; j < ARRAY_SIZE(dac_divs); ++j) {
|
||||
if (sysclk != dac_divs[j] * lrclk)
|
||||
continue;
|
||||
for (k = 0; k < ARRAY_SIZE(bclk_divs); ++k)
|
||||
if (sysclk == bclk * bclk_divs[k] / 10)
|
||||
break;
|
||||
if (k != ARRAY_SIZE(bclk_divs))
|
||||
break;
|
||||
}
|
||||
if (j != ARRAY_SIZE(dac_divs))
|
||||
break;
|
||||
}
|
||||
if (j != ARRAY_SIZE(dac_divs))
|
||||
break;
|
||||
}
|
||||
|
||||
if (i != ARRAY_SIZE(sysclk_divs)) {
|
||||
goto configure_clock;
|
||||
} else if (wm8960->clk_id != WM8960_SYSCLK_AUTO) {
|
||||
dev_err(codec->dev, "failed to configure clock\n");
|
||||
return -EINVAL;
|
||||
if (i != ARRAY_SIZE(sysclk_divs)) {
|
||||
goto configure_clock;
|
||||
} else if (wm8960->clk_id != WM8960_SYSCLK_AUTO) {
|
||||
dev_err(codec->dev, "failed to configure clock\n");
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
/* get a available pll out frequency and set pll */
|
||||
for (i = 0; i < ARRAY_SIZE(sysclk_divs); ++i) {
|
||||
|
@ -645,6 +645,8 @@ static int dw_i2s_probe(struct platform_device *pdev)
|
||||
|
||||
dev->dev = &pdev->dev;
|
||||
|
||||
dev->i2s_reg_comp1 = I2S_COMP_PARAM_1;
|
||||
dev->i2s_reg_comp2 = I2S_COMP_PARAM_2;
|
||||
if (pdata) {
|
||||
dev->capability = pdata->cap;
|
||||
clk_id = NULL;
|
||||
@ -652,9 +654,6 @@ static int dw_i2s_probe(struct platform_device *pdev)
|
||||
if (dev->quirks & DW_I2S_QUIRK_COMP_REG_OFFSET) {
|
||||
dev->i2s_reg_comp1 = pdata->i2s_reg_comp1;
|
||||
dev->i2s_reg_comp2 = pdata->i2s_reg_comp2;
|
||||
} else {
|
||||
dev->i2s_reg_comp1 = I2S_COMP_PARAM_1;
|
||||
dev->i2s_reg_comp2 = I2S_COMP_PARAM_2;
|
||||
}
|
||||
ret = dw_configure_dai_by_pd(dev, dw_i2s_dai, res, pdata);
|
||||
} else {
|
||||
|
@ -112,20 +112,6 @@ struct fsl_ssi_rxtx_reg_val {
|
||||
struct fsl_ssi_reg_val tx;
|
||||
};
|
||||
|
||||
static const struct reg_default fsl_ssi_reg_defaults[] = {
|
||||
{CCSR_SSI_SCR, 0x00000000},
|
||||
{CCSR_SSI_SIER, 0x00003003},
|
||||
{CCSR_SSI_STCR, 0x00000200},
|
||||
{CCSR_SSI_SRCR, 0x00000200},
|
||||
{CCSR_SSI_STCCR, 0x00040000},
|
||||
{CCSR_SSI_SRCCR, 0x00040000},
|
||||
{CCSR_SSI_SACNT, 0x00000000},
|
||||
{CCSR_SSI_STMSK, 0x00000000},
|
||||
{CCSR_SSI_SRMSK, 0x00000000},
|
||||
{CCSR_SSI_SACCEN, 0x00000000},
|
||||
{CCSR_SSI_SACCDIS, 0x00000000},
|
||||
};
|
||||
|
||||
static bool fsl_ssi_readable_reg(struct device *dev, unsigned int reg)
|
||||
{
|
||||
switch (reg) {
|
||||
@ -190,8 +176,7 @@ static const struct regmap_config fsl_ssi_regconfig = {
|
||||
.val_bits = 32,
|
||||
.reg_stride = 4,
|
||||
.val_format_endian = REGMAP_ENDIAN_NATIVE,
|
||||
.reg_defaults = fsl_ssi_reg_defaults,
|
||||
.num_reg_defaults = ARRAY_SIZE(fsl_ssi_reg_defaults),
|
||||
.num_reg_defaults_raw = CCSR_SSI_SACCDIS / sizeof(uint32_t) + 1,
|
||||
.readable_reg = fsl_ssi_readable_reg,
|
||||
.volatile_reg = fsl_ssi_volatile_reg,
|
||||
.precious_reg = fsl_ssi_precious_reg,
|
||||
@ -201,6 +186,7 @@ static const struct regmap_config fsl_ssi_regconfig = {
|
||||
|
||||
struct fsl_ssi_soc_data {
|
||||
bool imx;
|
||||
bool imx21regs; /* imx21-class SSI - no SACC{ST,EN,DIS} regs */
|
||||
bool offline_config;
|
||||
u32 sisr_write_mask;
|
||||
};
|
||||
@ -303,6 +289,7 @@ static struct fsl_ssi_soc_data fsl_ssi_mpc8610 = {
|
||||
|
||||
static struct fsl_ssi_soc_data fsl_ssi_imx21 = {
|
||||
.imx = true,
|
||||
.imx21regs = true,
|
||||
.offline_config = true,
|
||||
.sisr_write_mask = 0,
|
||||
};
|
||||
@ -586,8 +573,12 @@ static void fsl_ssi_setup_ac97(struct fsl_ssi_private *ssi_private)
|
||||
*/
|
||||
regmap_write(regs, CCSR_SSI_SACNT,
|
||||
CCSR_SSI_SACNT_AC97EN | CCSR_SSI_SACNT_FV);
|
||||
regmap_write(regs, CCSR_SSI_SACCDIS, 0xff);
|
||||
regmap_write(regs, CCSR_SSI_SACCEN, 0x300);
|
||||
|
||||
/* no SACC{ST,EN,DIS} regs on imx21-class SSI */
|
||||
if (!ssi_private->soc->imx21regs) {
|
||||
regmap_write(regs, CCSR_SSI_SACCDIS, 0xff);
|
||||
regmap_write(regs, CCSR_SSI_SACCEN, 0x300);
|
||||
}
|
||||
|
||||
/*
|
||||
* Enable SSI, Transmit and Receive. AC97 has to communicate with the
|
||||
@ -1397,6 +1388,7 @@ static int fsl_ssi_probe(struct platform_device *pdev)
|
||||
struct resource *res;
|
||||
void __iomem *iomem;
|
||||
char name[64];
|
||||
struct regmap_config regconfig = fsl_ssi_regconfig;
|
||||
|
||||
of_id = of_match_device(fsl_ssi_ids, &pdev->dev);
|
||||
if (!of_id || !of_id->data)
|
||||
@ -1444,15 +1436,25 @@ static int fsl_ssi_probe(struct platform_device *pdev)
|
||||
return PTR_ERR(iomem);
|
||||
ssi_private->ssi_phys = res->start;
|
||||
|
||||
if (ssi_private->soc->imx21regs) {
|
||||
/*
|
||||
* According to datasheet imx21-class SSI
|
||||
* don't have SACC{ST,EN,DIS} regs.
|
||||
*/
|
||||
regconfig.max_register = CCSR_SSI_SRMSK;
|
||||
regconfig.num_reg_defaults_raw =
|
||||
CCSR_SSI_SRMSK / sizeof(uint32_t) + 1;
|
||||
}
|
||||
|
||||
ret = of_property_match_string(np, "clock-names", "ipg");
|
||||
if (ret < 0) {
|
||||
ssi_private->has_ipg_clk_name = false;
|
||||
ssi_private->regs = devm_regmap_init_mmio(&pdev->dev, iomem,
|
||||
&fsl_ssi_regconfig);
|
||||
®config);
|
||||
} else {
|
||||
ssi_private->has_ipg_clk_name = true;
|
||||
ssi_private->regs = devm_regmap_init_mmio_clk(&pdev->dev,
|
||||
"ipg", iomem, &fsl_ssi_regconfig);
|
||||
"ipg", iomem, ®config);
|
||||
}
|
||||
if (IS_ERR(ssi_private->regs)) {
|
||||
dev_err(&pdev->dev, "Failed to init register map\n");
|
||||
|
@ -72,8 +72,6 @@ static int imx_spdif_audio_probe(struct platform_device *pdev)
|
||||
goto end;
|
||||
}
|
||||
|
||||
platform_set_drvdata(pdev, data);
|
||||
|
||||
end:
|
||||
of_node_put(spdif_np);
|
||||
|
||||
|
@ -99,7 +99,7 @@ static int asoc_simple_card_hw_params(struct snd_pcm_substream *substream,
|
||||
if (ret && ret != -ENOTSUPP)
|
||||
goto err;
|
||||
}
|
||||
|
||||
return 0;
|
||||
err:
|
||||
return ret;
|
||||
}
|
||||
|
@ -30,11 +30,15 @@ config SND_SST_IPC_ACPI
|
||||
config SND_SOC_INTEL_SST
|
||||
tristate
|
||||
select SND_SOC_INTEL_SST_ACPI if ACPI
|
||||
select SND_SOC_INTEL_SST_MATCH if ACPI
|
||||
depends on (X86 || COMPILE_TEST)
|
||||
|
||||
config SND_SOC_INTEL_SST_ACPI
|
||||
tristate
|
||||
|
||||
config SND_SOC_INTEL_SST_MATCH
|
||||
tristate
|
||||
|
||||
config SND_SOC_INTEL_HASWELL
|
||||
tristate
|
||||
|
||||
@ -57,7 +61,7 @@ config SND_SOC_INTEL_HASWELL_MACH
|
||||
config SND_SOC_INTEL_BYT_RT5640_MACH
|
||||
tristate "ASoC Audio driver for Intel Baytrail with RT5640 codec"
|
||||
depends on X86_INTEL_LPSS && I2C
|
||||
depends on DW_DMAC_CORE=y && (SND_SOC_INTEL_BYTCR_RT5640_MACH = n)
|
||||
depends on DW_DMAC_CORE=y && (SND_SST_IPC_ACPI = n)
|
||||
select SND_SOC_INTEL_SST
|
||||
select SND_SOC_INTEL_BAYTRAIL
|
||||
select SND_SOC_RT5640
|
||||
@ -69,7 +73,7 @@ config SND_SOC_INTEL_BYT_RT5640_MACH
|
||||
config SND_SOC_INTEL_BYT_MAX98090_MACH
|
||||
tristate "ASoC Audio driver for Intel Baytrail with MAX98090 codec"
|
||||
depends on X86_INTEL_LPSS && I2C
|
||||
depends on DW_DMAC_CORE=y
|
||||
depends on DW_DMAC_CORE=y && (SND_SST_IPC_ACPI = n)
|
||||
select SND_SOC_INTEL_SST
|
||||
select SND_SOC_INTEL_BAYTRAIL
|
||||
select SND_SOC_MAX98090
|
||||
@ -97,6 +101,7 @@ config SND_SOC_INTEL_BYTCR_RT5640_MACH
|
||||
select SND_SOC_RT5640
|
||||
select SND_SST_MFLD_PLATFORM
|
||||
select SND_SST_IPC_ACPI
|
||||
select SND_SOC_INTEL_SST_MATCH if ACPI
|
||||
help
|
||||
This adds support for ASoC machine driver for Intel(R) Baytrail and Baytrail-CR
|
||||
platforms with RT5640 audio codec.
|
||||
@ -109,6 +114,7 @@ config SND_SOC_INTEL_BYTCR_RT5651_MACH
|
||||
select SND_SOC_RT5651
|
||||
select SND_SST_MFLD_PLATFORM
|
||||
select SND_SST_IPC_ACPI
|
||||
select SND_SOC_INTEL_SST_MATCH if ACPI
|
||||
help
|
||||
This adds support for ASoC machine driver for Intel(R) Baytrail and Baytrail-CR
|
||||
platforms with RT5651 audio codec.
|
||||
@ -121,6 +127,7 @@ config SND_SOC_INTEL_CHT_BSW_RT5672_MACH
|
||||
select SND_SOC_RT5670
|
||||
select SND_SST_MFLD_PLATFORM
|
||||
select SND_SST_IPC_ACPI
|
||||
select SND_SOC_INTEL_SST_MATCH if ACPI
|
||||
help
|
||||
This adds support for ASoC machine driver for Intel(R) Cherrytrail & Braswell
|
||||
platforms with RT5672 audio codec.
|
||||
@ -133,6 +140,7 @@ config SND_SOC_INTEL_CHT_BSW_RT5645_MACH
|
||||
select SND_SOC_RT5645
|
||||
select SND_SST_MFLD_PLATFORM
|
||||
select SND_SST_IPC_ACPI
|
||||
select SND_SOC_INTEL_SST_MATCH if ACPI
|
||||
help
|
||||
This adds support for ASoC machine driver for Intel(R) Cherrytrail & Braswell
|
||||
platforms with RT5645/5650 audio codec.
|
||||
@ -145,6 +153,7 @@ config SND_SOC_INTEL_CHT_BSW_MAX98090_TI_MACH
|
||||
select SND_SOC_TS3A227E
|
||||
select SND_SST_MFLD_PLATFORM
|
||||
select SND_SST_IPC_ACPI
|
||||
select SND_SOC_INTEL_SST_MATCH if ACPI
|
||||
help
|
||||
This adds support for ASoC machine driver for Intel(R) Cherrytrail & Braswell
|
||||
platforms with MAX98090 audio codec it also can support TI jack chip as aux device.
|
||||
|
@ -528,6 +528,7 @@ static struct snd_soc_dai_driver sst_platform_dai[] = {
|
||||
.ops = &sst_compr_dai_ops,
|
||||
.playback = {
|
||||
.stream_name = "Compress Playback",
|
||||
.channels_min = 1,
|
||||
},
|
||||
},
|
||||
/* BE CPU Dais */
|
||||
|
@ -212,7 +212,10 @@ static int skylake_dmic_fixup(struct snd_soc_pcm_runtime *rtd,
|
||||
{
|
||||
struct snd_interval *channels = hw_param_interval(params,
|
||||
SNDRV_PCM_HW_PARAM_CHANNELS);
|
||||
channels->min = channels->max = 4;
|
||||
if (params_channels(params) == 2)
|
||||
channels->min = channels->max = 2;
|
||||
else
|
||||
channels->min = channels->max = 4;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
@ -1,13 +1,10 @@
|
||||
snd-soc-sst-dsp-objs := sst-dsp.o
|
||||
ifneq ($(CONFIG_SND_SST_IPC_ACPI),)
|
||||
snd-soc-sst-acpi-objs := sst-match-acpi.o
|
||||
else
|
||||
snd-soc-sst-acpi-objs := sst-acpi.o sst-match-acpi.o
|
||||
endif
|
||||
|
||||
snd-soc-sst-acpi-objs := sst-acpi.o
|
||||
snd-soc-sst-match-objs := sst-match-acpi.o
|
||||
snd-soc-sst-ipc-objs := sst-ipc.o
|
||||
|
||||
snd-soc-sst-dsp-$(CONFIG_DW_DMAC_CORE) += sst-firmware.o
|
||||
|
||||
obj-$(CONFIG_SND_SOC_INTEL_SST) += snd-soc-sst-dsp.o snd-soc-sst-ipc.o
|
||||
obj-$(CONFIG_SND_SOC_INTEL_SST_ACPI) += snd-soc-sst-acpi.o
|
||||
obj-$(CONFIG_SND_SOC_INTEL_SST_MATCH) += snd-soc-sst-match.o
|
||||
|
@ -215,6 +215,7 @@ static struct sst_acpi_desc sst_acpi_broadwell_desc = {
|
||||
.dma_size = SST_LPT_DSP_DMA_SIZE,
|
||||
};
|
||||
|
||||
#if !IS_ENABLED(CONFIG_SND_SST_IPC_ACPI)
|
||||
static struct sst_acpi_mach baytrail_machines[] = {
|
||||
{ "10EC5640", "byt-rt5640", "intel/fw_sst_0f28.bin-48kHz_i2s_master", NULL, NULL, NULL },
|
||||
{ "193C9890", "byt-max98090", "intel/fw_sst_0f28.bin-48kHz_i2s_master", NULL, NULL, NULL },
|
||||
@ -231,11 +232,14 @@ static struct sst_acpi_desc sst_acpi_baytrail_desc = {
|
||||
.sst_id = SST_DEV_ID_BYT,
|
||||
.resindex_dma_base = -1,
|
||||
};
|
||||
#endif
|
||||
|
||||
static const struct acpi_device_id sst_acpi_match[] = {
|
||||
{ "INT33C8", (unsigned long)&sst_acpi_haswell_desc },
|
||||
{ "INT3438", (unsigned long)&sst_acpi_broadwell_desc },
|
||||
#if !IS_ENABLED(CONFIG_SND_SST_IPC_ACPI)
|
||||
{ "80860F28", (unsigned long)&sst_acpi_baytrail_desc },
|
||||
#endif
|
||||
{ }
|
||||
};
|
||||
MODULE_DEVICE_TABLE(acpi, sst_acpi_match);
|
||||
|
@ -41,3 +41,6 @@ struct sst_acpi_mach *sst_acpi_find_machine(struct sst_acpi_mach *machines)
|
||||
return NULL;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(sst_acpi_find_machine);
|
||||
|
||||
MODULE_LICENSE("GPL v2");
|
||||
MODULE_DESCRIPTION("Intel Common ACPI Match module");
|
||||
|
@ -688,14 +688,14 @@ int skl_unbind_modules(struct skl_sst *ctx,
|
||||
/* get src queue index */
|
||||
src_index = skl_get_queue_index(src_mcfg->m_out_pin, dst_id, out_max);
|
||||
if (src_index < 0)
|
||||
return -EINVAL;
|
||||
return 0;
|
||||
|
||||
msg.src_queue = src_index;
|
||||
|
||||
/* get dst queue index */
|
||||
dst_index = skl_get_queue_index(dst_mcfg->m_in_pin, src_id, in_max);
|
||||
if (dst_index < 0)
|
||||
return -EINVAL;
|
||||
return 0;
|
||||
|
||||
msg.dst_queue = dst_index;
|
||||
|
||||
@ -747,7 +747,7 @@ int skl_bind_modules(struct skl_sst *ctx,
|
||||
|
||||
skl_dump_bind_info(ctx, src_mcfg, dst_mcfg);
|
||||
|
||||
if (src_mcfg->m_state < SKL_MODULE_INIT_DONE &&
|
||||
if (src_mcfg->m_state < SKL_MODULE_INIT_DONE ||
|
||||
dst_mcfg->m_state < SKL_MODULE_INIT_DONE)
|
||||
return 0;
|
||||
|
||||
|
@ -863,6 +863,7 @@ static int skl_get_delay_from_lpib(struct hdac_ext_bus *ebus,
|
||||
else
|
||||
delay += hstream->bufsize;
|
||||
}
|
||||
delay = (hstream->bufsize == delay) ? 0 : delay;
|
||||
|
||||
if (delay >= hstream->period_bytes) {
|
||||
dev_info(bus->dev,
|
||||
|
@ -54,12 +54,9 @@ static int is_skl_dsp_widget_type(struct snd_soc_dapm_widget *w)
|
||||
|
||||
/*
|
||||
* Each pipelines needs memory to be allocated. Check if we have free memory
|
||||
* from available pool. Then only add this to pool
|
||||
* This is freed when pipe is deleted
|
||||
* Note: DSP does actual memory management we only keep track for complete
|
||||
* pool
|
||||
* from available pool.
|
||||
*/
|
||||
static bool skl_tplg_alloc_pipe_mem(struct skl *skl,
|
||||
static bool skl_is_pipe_mem_avail(struct skl *skl,
|
||||
struct skl_module_cfg *mconfig)
|
||||
{
|
||||
struct skl_sst *ctx = skl->skl_sst;
|
||||
@ -74,10 +71,20 @@ static bool skl_tplg_alloc_pipe_mem(struct skl *skl,
|
||||
"exceeds ppl memory available %d mem %d\n",
|
||||
skl->resource.max_mem, skl->resource.mem);
|
||||
return false;
|
||||
} else {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Add the mem to the mem pool. This is freed when pipe is deleted.
|
||||
* Note: DSP does actual memory management we only keep track for complete
|
||||
* pool
|
||||
*/
|
||||
static void skl_tplg_alloc_pipe_mem(struct skl *skl,
|
||||
struct skl_module_cfg *mconfig)
|
||||
{
|
||||
skl->resource.mem += mconfig->pipe->memory_pages;
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -85,10 +92,10 @@ static bool skl_tplg_alloc_pipe_mem(struct skl *skl,
|
||||
* quantified in MCPS (Million Clocks Per Second) required for module/pipe
|
||||
*
|
||||
* Each pipelines needs mcps to be allocated. Check if we have mcps for this
|
||||
* pipe. This adds the mcps to driver counter
|
||||
* This is removed on pipeline delete
|
||||
* pipe.
|
||||
*/
|
||||
static bool skl_tplg_alloc_pipe_mcps(struct skl *skl,
|
||||
|
||||
static bool skl_is_pipe_mcps_avail(struct skl *skl,
|
||||
struct skl_module_cfg *mconfig)
|
||||
{
|
||||
struct skl_sst *ctx = skl->skl_sst;
|
||||
@ -98,13 +105,18 @@ static bool skl_tplg_alloc_pipe_mcps(struct skl *skl,
|
||||
"%s: module_id %d instance %d\n", __func__,
|
||||
mconfig->id.module_id, mconfig->id.instance_id);
|
||||
dev_err(ctx->dev,
|
||||
"exceeds ppl memory available %d > mem %d\n",
|
||||
"exceeds ppl mcps available %d > mem %d\n",
|
||||
skl->resource.max_mcps, skl->resource.mcps);
|
||||
return false;
|
||||
} else {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
static void skl_tplg_alloc_pipe_mcps(struct skl *skl,
|
||||
struct skl_module_cfg *mconfig)
|
||||
{
|
||||
skl->resource.mcps += mconfig->mcps;
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -411,7 +423,7 @@ skl_tplg_init_pipe_modules(struct skl *skl, struct skl_pipe *pipe)
|
||||
mconfig = w->priv;
|
||||
|
||||
/* check resource available */
|
||||
if (!skl_tplg_alloc_pipe_mcps(skl, mconfig))
|
||||
if (!skl_is_pipe_mcps_avail(skl, mconfig))
|
||||
return -ENOMEM;
|
||||
|
||||
if (mconfig->is_loadable && ctx->dsp->fw_ops.load_mod) {
|
||||
@ -435,6 +447,7 @@ skl_tplg_init_pipe_modules(struct skl *skl, struct skl_pipe *pipe)
|
||||
ret = skl_tplg_set_module_params(w, ctx);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
skl_tplg_alloc_pipe_mcps(skl, mconfig);
|
||||
}
|
||||
|
||||
return 0;
|
||||
@ -477,10 +490,10 @@ static int skl_tplg_mixer_dapm_pre_pmu_event(struct snd_soc_dapm_widget *w,
|
||||
struct skl_sst *ctx = skl->skl_sst;
|
||||
|
||||
/* check resource available */
|
||||
if (!skl_tplg_alloc_pipe_mcps(skl, mconfig))
|
||||
if (!skl_is_pipe_mcps_avail(skl, mconfig))
|
||||
return -EBUSY;
|
||||
|
||||
if (!skl_tplg_alloc_pipe_mem(skl, mconfig))
|
||||
if (!skl_is_pipe_mem_avail(skl, mconfig))
|
||||
return -ENOMEM;
|
||||
|
||||
/*
|
||||
@ -526,11 +539,15 @@ static int skl_tplg_mixer_dapm_pre_pmu_event(struct snd_soc_dapm_widget *w,
|
||||
src_module = dst_module;
|
||||
}
|
||||
|
||||
skl_tplg_alloc_pipe_mem(skl, mconfig);
|
||||
skl_tplg_alloc_pipe_mcps(skl, mconfig);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int skl_tplg_bind_sinks(struct snd_soc_dapm_widget *w,
|
||||
struct skl *skl,
|
||||
struct snd_soc_dapm_widget *src_w,
|
||||
struct skl_module_cfg *src_mconfig)
|
||||
{
|
||||
struct snd_soc_dapm_path *p;
|
||||
@ -547,6 +564,10 @@ static int skl_tplg_bind_sinks(struct snd_soc_dapm_widget *w,
|
||||
dev_dbg(ctx->dev, "%s: sink widget=%s\n", __func__, p->sink->name);
|
||||
|
||||
next_sink = p->sink;
|
||||
|
||||
if (!is_skl_dsp_widget_type(p->sink))
|
||||
return skl_tplg_bind_sinks(p->sink, skl, src_w, src_mconfig);
|
||||
|
||||
/*
|
||||
* here we will check widgets in sink pipelines, so that
|
||||
* can be any widgets type and we are only interested if
|
||||
@ -576,7 +597,7 @@ static int skl_tplg_bind_sinks(struct snd_soc_dapm_widget *w,
|
||||
}
|
||||
|
||||
if (!sink)
|
||||
return skl_tplg_bind_sinks(next_sink, skl, src_mconfig);
|
||||
return skl_tplg_bind_sinks(next_sink, skl, src_w, src_mconfig);
|
||||
|
||||
return 0;
|
||||
}
|
||||
@ -605,7 +626,7 @@ static int skl_tplg_pga_dapm_pre_pmu_event(struct snd_soc_dapm_widget *w,
|
||||
* if sink is not started, start sink pipe first, then start
|
||||
* this pipe
|
||||
*/
|
||||
ret = skl_tplg_bind_sinks(w, skl, src_mconfig);
|
||||
ret = skl_tplg_bind_sinks(w, skl, w, src_mconfig);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
@ -773,10 +794,7 @@ static int skl_tplg_mixer_dapm_post_pmd_event(struct snd_soc_dapm_widget *w,
|
||||
continue;
|
||||
}
|
||||
|
||||
ret = skl_unbind_modules(ctx, src_module, dst_module);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
|
||||
skl_unbind_modules(ctx, src_module, dst_module);
|
||||
src_module = dst_module;
|
||||
}
|
||||
|
||||
@ -814,9 +832,6 @@ static int skl_tplg_pga_dapm_post_pmd_event(struct snd_soc_dapm_widget *w,
|
||||
* This is a connecter and if path is found that means
|
||||
* unbind between source and sink has not happened yet
|
||||
*/
|
||||
ret = skl_stop_pipe(ctx, sink_mconfig->pipe);
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
ret = skl_unbind_modules(ctx, src_mconfig,
|
||||
sink_mconfig);
|
||||
}
|
||||
@ -842,6 +857,12 @@ static int skl_tplg_vmixer_event(struct snd_soc_dapm_widget *w,
|
||||
case SND_SOC_DAPM_PRE_PMU:
|
||||
return skl_tplg_mixer_dapm_pre_pmu_event(w, skl);
|
||||
|
||||
case SND_SOC_DAPM_POST_PMU:
|
||||
return skl_tplg_mixer_dapm_post_pmu_event(w, skl);
|
||||
|
||||
case SND_SOC_DAPM_PRE_PMD:
|
||||
return skl_tplg_mixer_dapm_pre_pmd_event(w, skl);
|
||||
|
||||
case SND_SOC_DAPM_POST_PMD:
|
||||
return skl_tplg_mixer_dapm_post_pmd_event(w, skl);
|
||||
}
|
||||
@ -916,6 +937,13 @@ static int skl_tplg_tlv_control_get(struct snd_kcontrol *kcontrol,
|
||||
skl_get_module_params(skl->skl_sst, (u32 *)bc->params,
|
||||
bc->max, bc->param_id, mconfig);
|
||||
|
||||
/* decrement size for TLV header */
|
||||
size -= 2 * sizeof(u32);
|
||||
|
||||
/* check size as we don't want to send kernel data */
|
||||
if (size > bc->max)
|
||||
size = bc->max;
|
||||
|
||||
if (bc->params) {
|
||||
if (copy_to_user(data, &bc->param_id, sizeof(u32)))
|
||||
return -EFAULT;
|
||||
@ -1510,6 +1538,7 @@ int skl_tplg_init(struct snd_soc_platform *platform, struct hdac_ext_bus *ebus)
|
||||
&skl_tplg_ops, fw, 0);
|
||||
if (ret < 0) {
|
||||
dev_err(bus->dev, "tplg component load failed%d\n", ret);
|
||||
release_firmware(fw);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
|
@ -614,8 +614,6 @@ static int skl_probe(struct pci_dev *pci,
|
||||
goto out_unregister;
|
||||
|
||||
/*configure PM */
|
||||
pm_runtime_set_autosuspend_delay(bus->dev, SKL_SUSPEND_DELAY);
|
||||
pm_runtime_use_autosuspend(bus->dev);
|
||||
pm_runtime_put_noidle(bus->dev);
|
||||
pm_runtime_allow(bus->dev);
|
||||
|
||||
|
@ -9,7 +9,7 @@ config SND_SOC_MEDIATEK
|
||||
|
||||
config SND_SOC_MT8173_MAX98090
|
||||
tristate "ASoC Audio driver for MT8173 with MAX98090 codec"
|
||||
depends on SND_SOC_MEDIATEK
|
||||
depends on SND_SOC_MEDIATEK && I2C
|
||||
select SND_SOC_MAX98090
|
||||
help
|
||||
This adds ASoC driver for Mediatek MT8173 boards
|
||||
@ -19,7 +19,7 @@ config SND_SOC_MT8173_MAX98090
|
||||
|
||||
config SND_SOC_MT8173_RT5650_RT5676
|
||||
tristate "ASoC Audio driver for MT8173 with RT5650 RT5676 codecs"
|
||||
depends on SND_SOC_MEDIATEK
|
||||
depends on SND_SOC_MEDIATEK && I2C
|
||||
select SND_SOC_RT5645
|
||||
select SND_SOC_RT5677
|
||||
help
|
||||
|
@ -381,9 +381,19 @@ static int mxs_saif_startup(struct snd_pcm_substream *substream,
|
||||
__raw_writel(BM_SAIF_CTRL_CLKGATE,
|
||||
saif->base + SAIF_CTRL + MXS_CLR_ADDR);
|
||||
|
||||
clk_prepare(saif->clk);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void mxs_saif_shutdown(struct snd_pcm_substream *substream,
|
||||
struct snd_soc_dai *cpu_dai)
|
||||
{
|
||||
struct mxs_saif *saif = snd_soc_dai_get_drvdata(cpu_dai);
|
||||
|
||||
clk_unprepare(saif->clk);
|
||||
}
|
||||
|
||||
/*
|
||||
* Should only be called when port is inactive.
|
||||
* although can be called multiple times by upper layers.
|
||||
@ -424,8 +434,6 @@ static int mxs_saif_hw_params(struct snd_pcm_substream *substream,
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* prepare clk in hw_param, enable in trigger */
|
||||
clk_prepare(saif->clk);
|
||||
if (saif != master_saif) {
|
||||
/*
|
||||
* Set an initial clock rate for the saif internal logic to work
|
||||
@ -611,6 +619,7 @@ static int mxs_saif_trigger(struct snd_pcm_substream *substream, int cmd,
|
||||
|
||||
static const struct snd_soc_dai_ops mxs_saif_dai_ops = {
|
||||
.startup = mxs_saif_startup,
|
||||
.shutdown = mxs_saif_shutdown,
|
||||
.trigger = mxs_saif_trigger,
|
||||
.prepare = mxs_saif_prepare,
|
||||
.hw_params = mxs_saif_hw_params,
|
||||
|
@ -440,18 +440,18 @@ static irqreturn_t lpass_platform_lpaif_irq(int irq, void *data)
|
||||
}
|
||||
|
||||
static int lpass_platform_alloc_buffer(struct snd_pcm_substream *substream,
|
||||
struct snd_soc_pcm_runtime *soc_runtime)
|
||||
struct snd_soc_pcm_runtime *rt)
|
||||
{
|
||||
struct snd_dma_buffer *buf = &substream->dma_buffer;
|
||||
size_t size = lpass_platform_pcm_hardware.buffer_bytes_max;
|
||||
|
||||
buf->dev.type = SNDRV_DMA_TYPE_DEV;
|
||||
buf->dev.dev = soc_runtime->dev;
|
||||
buf->dev.dev = rt->platform->dev;
|
||||
buf->private_data = NULL;
|
||||
buf->area = dma_alloc_coherent(soc_runtime->dev, size, &buf->addr,
|
||||
buf->area = dma_alloc_coherent(rt->platform->dev, size, &buf->addr,
|
||||
GFP_KERNEL);
|
||||
if (!buf->area) {
|
||||
dev_err(soc_runtime->dev, "%s: Could not allocate DMA buffer\n",
|
||||
dev_err(rt->platform->dev, "%s: Could not allocate DMA buffer\n",
|
||||
__func__);
|
||||
return -ENOMEM;
|
||||
}
|
||||
@ -461,12 +461,12 @@ static int lpass_platform_alloc_buffer(struct snd_pcm_substream *substream,
|
||||
}
|
||||
|
||||
static void lpass_platform_free_buffer(struct snd_pcm_substream *substream,
|
||||
struct snd_soc_pcm_runtime *soc_runtime)
|
||||
struct snd_soc_pcm_runtime *rt)
|
||||
{
|
||||
struct snd_dma_buffer *buf = &substream->dma_buffer;
|
||||
|
||||
if (buf->area) {
|
||||
dma_free_coherent(soc_runtime->dev, buf->bytes, buf->area,
|
||||
dma_free_coherent(rt->dev, buf->bytes, buf->area,
|
||||
buf->addr);
|
||||
}
|
||||
buf->area = NULL;
|
||||
@ -499,9 +499,6 @@ static int lpass_platform_pcm_new(struct snd_soc_pcm_runtime *soc_runtime)
|
||||
|
||||
snd_soc_pcm_set_drvdata(soc_runtime, data);
|
||||
|
||||
soc_runtime->dev->coherent_dma_mask = DMA_BIT_MASK(32);
|
||||
soc_runtime->dev->dma_mask = &soc_runtime->dev->coherent_dma_mask;
|
||||
|
||||
ret = lpass_platform_alloc_buffer(substream, soc_runtime);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
@ -310,7 +310,7 @@ struct dapm_kcontrol_data {
|
||||
};
|
||||
|
||||
static int dapm_kcontrol_data_alloc(struct snd_soc_dapm_widget *widget,
|
||||
struct snd_kcontrol *kcontrol)
|
||||
struct snd_kcontrol *kcontrol, const char *ctrl_name)
|
||||
{
|
||||
struct dapm_kcontrol_data *data;
|
||||
struct soc_mixer_control *mc;
|
||||
@ -333,7 +333,7 @@ static int dapm_kcontrol_data_alloc(struct snd_soc_dapm_widget *widget,
|
||||
if (mc->autodisable) {
|
||||
struct snd_soc_dapm_widget template;
|
||||
|
||||
name = kasprintf(GFP_KERNEL, "%s %s", kcontrol->id.name,
|
||||
name = kasprintf(GFP_KERNEL, "%s %s", ctrl_name,
|
||||
"Autodisable");
|
||||
if (!name) {
|
||||
ret = -ENOMEM;
|
||||
@ -371,7 +371,7 @@ static int dapm_kcontrol_data_alloc(struct snd_soc_dapm_widget *widget,
|
||||
if (e->autodisable) {
|
||||
struct snd_soc_dapm_widget template;
|
||||
|
||||
name = kasprintf(GFP_KERNEL, "%s %s", kcontrol->id.name,
|
||||
name = kasprintf(GFP_KERNEL, "%s %s", ctrl_name,
|
||||
"Autodisable");
|
||||
if (!name) {
|
||||
ret = -ENOMEM;
|
||||
@ -871,7 +871,7 @@ static int dapm_create_or_share_kcontrol(struct snd_soc_dapm_widget *w,
|
||||
|
||||
kcontrol->private_free = dapm_kcontrol_free;
|
||||
|
||||
ret = dapm_kcontrol_data_alloc(w, kcontrol);
|
||||
ret = dapm_kcontrol_data_alloc(w, kcontrol, name);
|
||||
if (ret) {
|
||||
snd_ctl_free_one(kcontrol);
|
||||
goto exit_free;
|
||||
|
@ -1810,7 +1810,8 @@ int dpcm_be_dai_hw_free(struct snd_soc_pcm_runtime *fe, int stream)
|
||||
(be->dpcm[stream].state != SND_SOC_DPCM_STATE_PREPARE) &&
|
||||
(be->dpcm[stream].state != SND_SOC_DPCM_STATE_HW_FREE) &&
|
||||
(be->dpcm[stream].state != SND_SOC_DPCM_STATE_PAUSED) &&
|
||||
(be->dpcm[stream].state != SND_SOC_DPCM_STATE_STOP))
|
||||
(be->dpcm[stream].state != SND_SOC_DPCM_STATE_STOP) &&
|
||||
(be->dpcm[stream].state != SND_SOC_DPCM_STATE_SUSPEND))
|
||||
continue;
|
||||
|
||||
dev_dbg(be->dev, "ASoC: hw_free BE %s\n",
|
||||
|
Loading…
Reference in New Issue
Block a user