mirror of
https://github.com/hardkernel/linux.git
synced 2026-06-08 20:07:46 +09:00
audio: check toddr and fix clk of tdmout for loopback
PD#155103: audio: fix toddr checking and tdm clks for loopback 1) check toddr whether for loopback 2) fix clks of tdmout for loopback Change-Id: Ifd5ddc88114ebb8e7dcf5a0e991ead9b190c8621 Signed-off-by: Xing Wang <xing.wang@amlogic.com>
This commit is contained in:
@@ -32,6 +32,7 @@ struct snd_elem_info {
|
||||
};
|
||||
|
||||
static unsigned int loopback_enable;
|
||||
static unsigned int loopback_is_running;
|
||||
|
||||
static const char *const loopback_enable_texts[] = {
|
||||
"Disable",
|
||||
@@ -1085,7 +1086,7 @@ static void loopback_modules_disable(
|
||||
{
|
||||
/* tdminLB */
|
||||
tdmin_lb_fifo_enable(0);
|
||||
tdmin_lb_enable(0);
|
||||
tdmin_lb_enable(tdm_index, 0);
|
||||
|
||||
/* pdmin */
|
||||
pdm_enable(0);
|
||||
@@ -1100,12 +1101,14 @@ static void loopback_modules_disable(
|
||||
/* frddr */
|
||||
if (frddr_index >= 3)
|
||||
toddr_enable(0, frddr_index - 3);
|
||||
else
|
||||
else if (frddr_index >= 0)
|
||||
frddr_enable(0, frddr_index);
|
||||
|
||||
/* tdmout */
|
||||
tdm_fifo_enable(tdm_index, 0);
|
||||
tdm_enable(tdm_index, 0);
|
||||
if (frddr_index >= 0) {
|
||||
tdm_fifo_enable(tdm_index, 0);
|
||||
tdm_enable(tdm_index, 0);
|
||||
}
|
||||
}
|
||||
|
||||
static void loopback_modules_enable(
|
||||
@@ -1118,13 +1121,15 @@ static void loopback_modules_enable(
|
||||
*/
|
||||
|
||||
/* tdmout */
|
||||
tdm_fifo_enable(tdm_index, 1);
|
||||
tdm_enable(tdm_index, 1);
|
||||
if (frddr_index >= 0) {
|
||||
tdm_fifo_enable(tdm_index, 1);
|
||||
tdm_enable(tdm_index, 1);
|
||||
}
|
||||
|
||||
/* frddr */
|
||||
if (frddr_index >= 3)
|
||||
toddr_enable(1, frddr_index - 3);
|
||||
else
|
||||
else if (frddr_index >= 0)
|
||||
frddr_enable(1, frddr_index);
|
||||
|
||||
/* toddr */
|
||||
@@ -1139,7 +1144,7 @@ static void loopback_modules_enable(
|
||||
|
||||
/*tdminLB*/
|
||||
tdmin_lb_fifo_enable(1);
|
||||
tdmin_lb_enable(1);
|
||||
tdmin_lb_enable(tdm_index, 1);
|
||||
}
|
||||
|
||||
int loopback_trigger(
|
||||
@@ -1147,13 +1152,13 @@ int loopback_trigger(
|
||||
int cmd,
|
||||
struct loopback_cfg *lb_cfg)
|
||||
{
|
||||
pr_info("%s\n", __func__);
|
||||
|
||||
switch (cmd) {
|
||||
case SNDRV_PCM_TRIGGER_START:
|
||||
case SNDRV_PCM_TRIGGER_RESUME:
|
||||
case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
|
||||
if (substream->stream == SNDRV_PCM_STREAM_CAPTURE) {
|
||||
if (loopback_enable && loopback_is_running) {
|
||||
pr_info("loopback enable\n");
|
||||
|
||||
/*
|
||||
* toddr/frdd is selected in dai_prepare already.
|
||||
* check toddr index of datain
|
||||
@@ -1173,22 +1178,18 @@ int loopback_trigger(
|
||||
lb_cfg->toddr_index,
|
||||
lb_cfg->frddr_index);
|
||||
|
||||
if (loopback_enable
|
||||
&& (lb_cfg->toddr_index >= 0)
|
||||
&& (lb_cfg->frddr_index >= 0)) {
|
||||
pr_info("loopback modules in sequence!\n");
|
||||
/*if pdm overrun, re-set up the sequence*/
|
||||
if (lb_cfg->frddr_index >= 0)
|
||||
loopback_modules_disable(
|
||||
lb_cfg->datalb_src,
|
||||
lb_cfg->frddr_index,
|
||||
lb_cfg->toddr_index);
|
||||
pr_info("loopback modules in sequence!\n");
|
||||
/*if pdm overrun, re-set up the sequence*/
|
||||
if (lb_cfg->frddr_index >= 0)
|
||||
loopback_modules_disable(
|
||||
lb_cfg->datalb_src,
|
||||
lb_cfg->frddr_index,
|
||||
lb_cfg->toddr_index);
|
||||
|
||||
loopback_modules_enable(
|
||||
lb_cfg->datalb_src,
|
||||
lb_cfg->frddr_index,
|
||||
lb_cfg->toddr_index);
|
||||
}
|
||||
loopback_modules_enable(
|
||||
lb_cfg->datalb_src,
|
||||
lb_cfg->frddr_index,
|
||||
lb_cfg->toddr_index);
|
||||
}
|
||||
break;
|
||||
case SNDRV_PCM_TRIGGER_STOP:
|
||||
@@ -1198,7 +1199,7 @@ int loopback_trigger(
|
||||
if (loopback_enable) {
|
||||
pr_info("loopback disable\n");
|
||||
lb_enable(0);
|
||||
tdmin_lb_enable(0);
|
||||
tdmin_lb_enable(lb_cfg->datalb_src, 0);
|
||||
}
|
||||
}
|
||||
break;
|
||||
@@ -1209,7 +1210,19 @@ int loopback_trigger(
|
||||
return 0;
|
||||
}
|
||||
|
||||
void loopback_set_status(int is_running)
|
||||
{
|
||||
loopback_is_running = is_running;
|
||||
}
|
||||
|
||||
int loopback_is_enable(void)
|
||||
{
|
||||
return (loopback_enable == 1);
|
||||
}
|
||||
|
||||
int loopback_check_enable(int src)
|
||||
{
|
||||
return (src <= PDMIN)
|
||||
&& (loopback_datain == src)
|
||||
&& (loopback_enable == 1);
|
||||
}
|
||||
|
||||
@@ -118,16 +118,20 @@ struct loopback_cfg {
|
||||
enum datain_src datain_src;
|
||||
unsigned int datain_chnum;
|
||||
unsigned int datain_chmask;
|
||||
unsigned int toddr_index;
|
||||
int toddr_index;
|
||||
|
||||
enum tdmin_lb_src datalb_src;
|
||||
unsigned int datalb_chnum;
|
||||
unsigned int datalb_chmask;
|
||||
unsigned int frddr_index;
|
||||
int frddr_index;
|
||||
};
|
||||
|
||||
extern void loopback_set_status(int is_running);
|
||||
|
||||
extern int loopback_is_enable(void);
|
||||
|
||||
extern int loopback_check_enable(int src);
|
||||
|
||||
extern int snd_card_add_kcontrols(struct snd_soc_card *card);
|
||||
|
||||
extern int loopback_parse_of(struct device_node *node,
|
||||
|
||||
@@ -55,6 +55,7 @@ struct toddr {
|
||||
unsigned int lsb_bit;
|
||||
unsigned int reg_base;
|
||||
enum toddr_src src;
|
||||
int is_lb; /* check whether for loopback */
|
||||
int irq;
|
||||
bool in_use: 1;
|
||||
struct aml_audio_controller *actrl;
|
||||
@@ -135,6 +136,12 @@ static int unregister_toddr_l(struct device *dev, void *data)
|
||||
|
||||
to = &toddrs[i];
|
||||
|
||||
/* check for loopback */
|
||||
if (to->is_lb) {
|
||||
loopback_set_status(0);
|
||||
to->is_lb = 0;
|
||||
}
|
||||
|
||||
/* disable audio ddr arb */
|
||||
mask_bit = i;
|
||||
actrl = to->actrl;
|
||||
@@ -259,8 +266,11 @@ void aml_toddr_select_src(struct toddr *to, enum toddr_src src)
|
||||
to->src = src;
|
||||
|
||||
/* check whether loopback enable */
|
||||
if (loopback_is_enable())
|
||||
if (loopback_check_enable(src)) {
|
||||
loopback_set_status(1);
|
||||
to->is_lb = 1; /* in loopback */
|
||||
src = LOOPBACK;
|
||||
}
|
||||
|
||||
reg = calc_toddr_address(EE_AUDIO_TODDR_A_CTRL0, reg_base);
|
||||
aml_audiobus_update_bits(actrl, reg, 0x7, src & 0x7);
|
||||
|
||||
@@ -123,19 +123,22 @@ void lb_mode(int mode)
|
||||
);
|
||||
}
|
||||
|
||||
void tdmin_lb_clk_enalbe(int is_enable)
|
||||
static void tdmin_lb_clk_enalbe(int tdm_src, int is_enable)
|
||||
{
|
||||
audiobus_update_bits(
|
||||
EE_AUDIO_CLK_TDMIN_LB_CTRL,
|
||||
0x3 << 30 | 1 << 29 | 0xf << 24 | 0xf << 20,
|
||||
0x3 << 30 | 1 << 29 | 2 << 24 | 2 << 20
|
||||
);
|
||||
if (tdm_src <= 2)
|
||||
audiobus_update_bits(
|
||||
EE_AUDIO_CLK_TDMIN_LB_CTRL,
|
||||
0x3 << 30 | 1 << 29 | 0xf << 24 | 0xf << 20,
|
||||
0x3 << 30 | 1 << 29 | tdm_src << 24 | tdm_src << 20
|
||||
);
|
||||
else
|
||||
pr_warn_once("pad from tdmin_a, tdmin_b, tdmin_c needs clks\n");
|
||||
}
|
||||
|
||||
void tdmin_lb_enable(int is_enable)
|
||||
void tdmin_lb_enable(int tdm_index, int is_enable)
|
||||
{
|
||||
if (is_enable)
|
||||
tdmin_lb_clk_enalbe(is_enable);
|
||||
tdmin_lb_clk_enalbe(tdm_index, is_enable);
|
||||
|
||||
audiobus_update_bits(
|
||||
EE_AUDIO_TDMIN_LB_CTRL,
|
||||
|
||||
@@ -65,7 +65,7 @@ extern void lb_enable(bool is_enable);
|
||||
|
||||
extern void lb_mode(int mode);
|
||||
|
||||
extern void tdmin_lb_enable(int in_enable);
|
||||
extern void tdmin_lb_enable(int tdm_index, int in_enable);
|
||||
|
||||
extern void tdmin_lb_fifo_enable(int is_enable);
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user