static int ak4647_set_clkdiv(struct snd_soc_dai *codec_dai, int div_id, int div) { int retval = 0; u8 value; if (AK4647_BCLK_CLKDIV == div_id) { ak4647_read_reg(AK4647_MODE1, &value); switch (div) { case AK4647_BCLK_DIV_32: CLEAR_BIT_IN_BYTE(value, 3); ak4647_write_reg(AK4647_MODE1, value); break; case AK4647_BCLK_DIV_64: SET_BIT_IN_BYTE(value, 3); ak4647_write_reg(AK4647_MODE1, value); break; default: retval = -1; pr_err("wrong div value for divid %d", div_id); break; } } else if (AK4647_MCLK_CLKDIV == div_id) { ak4647_read_reg(AK4647_MODE2, &value); switch (div) { case AK4647_MCLK_DIV_32: SET_BIT_IN_BYTE(value, 7); SET_BIT_IN_BYTE(value, 6); ak4647_write_reg(AK4647_MODE2, value); break; case AK4647_MCLK_DIV_64: SET_BIT_IN_BYTE(value, 7); CLEAR_BIT_IN_BYTE(value, 6); ak4647_write_reg(AK4647_MODE2, value); break; case AK4647_MCLK_DIV_128: CLEAR_BIT_IN_BYTE(value, 7); SET_BIT_IN_BYTE(value, 6); ak4647_write_reg(AK4647_MODE2, value); break; case AK4647_MCLK_DIV_256: CLEAR_BIT_IN_BYTE(value, 7); CLEAR_BIT_IN_BYTE(value, 6); ak4647_write_reg(AK4647_MODE2, value); break; default: retval = -1; pr_err("wrong div value for div id %d", div_id); break; } } else { retval = -1; pr_err("wrong div id"); } return retval; }
static int ak4647_set_dai_fmt(struct snd_soc_dai *codec_dai, unsigned int fmt) { u8 reg_mode1, reg_pm2; /* get current values */ ak4647_read_reg(AK4647_MODE1, ®_mode1); ak4647_read_reg(AK4647_PM2, ®_pm2); /* set master/slave audio interface */ switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { case SND_SOC_DAIFMT_CBM_CFM: SET_BIT_IN_BYTE(reg_pm2, 3); break; case SND_SOC_DAIFMT_CBS_CFS: CLEAR_BIT_IN_BYTE(reg_pm2, 3); break; default: return -EINVAL; } /* interface format */ switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { case SND_SOC_DAIFMT_I2S: SET_BIT_IN_BYTE(reg_mode1, 0); SET_BIT_IN_BYTE(reg_mode1, 1); break; case SND_SOC_DAIFMT_RIGHT_J: SET_BIT_IN_BYTE(reg_mode1, 0); CLEAR_BIT_IN_BYTE(reg_mode1, 1); break; case SND_SOC_DAIFMT_LEFT_J: CLEAR_BIT_IN_BYTE(reg_mode1, 0); SET_BIT_IN_BYTE(reg_mode1, 1); break; case SND_SOC_DAIFMT_DSP_A: case SND_SOC_DAIFMT_DSP_B: default: pr_err("dai format %d not supported", fmt); return -EINVAL; } ak4647_write_reg(AK4647_MODE1, reg_mode1); ak4647_write_reg(AK4647_PM2, reg_pm2); return 0; }
static int ak4647_pcm_prepare(struct snd_pcm_substream *substream, struct snd_soc_dai *dai) { u8 value; /* VCOM power on */ ak4647_write_reg(AK4647_PM1, 0x44); msleep(30); ak4647_read_reg(AK4647_PM2, &value); /* PLL enabled */ SET_BIT_IN_BYTE(value, 0); ak4647_write_reg(AK4647_PM2, value); /* wait for PLL locked */ msleep(40); /* don't mute */ SET_BIT_IN_BYTE(value, 6); ak4647_write_reg(AK4647_PM2, value); return 0; }
static int ak4647_digital_mute(struct snd_soc_dai *dai, int mute) { u8 value; ak4647_read_reg(AK4647_MODE3, &value); if (mute) SET_BIT_IN_BYTE(value, 5); else CLEAR_BIT_IN_BYTE(value, 5); ak4647_write_reg(AK4647_MODE3, value); return 0; }
int pmic_gpio_get_designation_bit_val(unsigned int bit, unsigned int *val) { unsigned int reg_read_val; u8 reg_mask = 0; if (bit > 7) return -1; SET_BIT_IN_BYTE(reg_mask, bit); CHECK_ERROR( mcu_pmic_read_reg(REG_MCU_DES_FLAG, ®_read_val, reg_mask)); if (0 == reg_read_val) *val = 0; else *val = 1; return 0; }
int pmic_gpio_get_bit_val(int reg, unsigned int bit, unsigned int *val) { int reg_name; unsigned int reg_read_val; u8 reg_mask = 0; if (bit > 7) return -1; switch (reg) { case MCU_GPIO_REG_RESET_1: reg_name = REG_MCU_RESET_1; break; case MCU_GPIO_REG_RESET_2: reg_name = REG_MCU_RESET_2; break; case MCU_GPIO_REG_POWER_CONTROL: reg_name = REG_MCU_POWER_CTL; break; case MCU_GPIO_REG_GPIO_CONTROL_1: reg_name = REG_MCU_GPIO_1; break; case MCU_GPIO_REG_GPIO_CONTROL_2: reg_name = REG_MCU_GPIO_2; break; default: return -1; } SET_BIT_IN_BYTE(reg_mask, bit); CHECK_ERROR(mcu_pmic_read_reg(reg_name, ®_read_val, reg_mask)); if (0 == reg_read_val) *val = 0; else *val = 1; return 0; }
int pmic_gpio_set_bit_val(int reg, unsigned int bit, unsigned int val) { int reg_name; u8 reg_mask = 0; if (bit > 7) return -1; switch (reg) { case MCU_GPIO_REG_RESET_1: reg_name = REG_MCU_RESET_1; break; case MCU_GPIO_REG_RESET_2: reg_name = REG_MCU_RESET_2; break; case MCU_GPIO_REG_POWER_CONTROL: reg_name = REG_MCU_POWER_CTL; break; case MCU_GPIO_REG_GPIO_CONTROL_1: reg_name = REG_MCU_GPIO_1; break; case MCU_GPIO_REG_GPIO_CONTROL_2: reg_name = REG_MCU_GPIO_2; break; default: return -1; } SET_BIT_IN_BYTE(reg_mask, bit); if (0 == val) CHECK_ERROR(mcu_pmic_write_reg(reg_name, 0, reg_mask)); else CHECK_ERROR(mcu_pmic_write_reg(reg_name, reg_mask, reg_mask)); return 0; }
int pmic_audio_fm_output_enable(bool enable) { u8 val; if (enable) { ak4647_set_dai_fmt(NULL, SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | SND_SOC_DAIFMT_CBM_CFM); ak4647_set_dai_sysclk(NULL, 0, 44100, 0); ak4647_set_clkdiv(NULL, 0, 0); /* VCOM power on */ ak4647_write_reg(AK4647_PM1, 0x44); msleep(30); ak4647_read_reg(AK4647_PM2, &val); /* PLL enabled */ SET_BIT_IN_BYTE(val, 0); ak4647_write_reg(AK4647_PM2, val); /* wait for PLL locked */ msleep(40); /* don't mute */ SET_BIT_IN_BYTE(val, 6); ak4647_write_reg(AK4647_PM2, val); /* loopback STDO to DAC */ ak4647_read_reg(AK4647_MODE3, &val); SET_BIT_IN_BYTE(val, 6); ak4647_write_reg(AK4647_MODE3, val); /* switch to R/L 1 */ ak4647_read_reg(AK4647_PM3, &val); CLEAR_BIT_IN_BYTE(val, 1); CLEAR_BIT_IN_BYTE(val, 2); ak4647_write_reg(AK4647_PM3, val); /* power up ADC */ ak4647_read_reg(AK4647_PM1, &val); SET_BIT_IN_BYTE(val, 0); ak4647_write_reg(AK4647_PM1, val); ak4647_read_reg(AK4647_PM3, &val); SET_BIT_IN_BYTE(val, 0); ak4647_write_reg(AK4647_PM3, val); /* power up DAC */ ak4647_read_reg(AK4647_PM1, &val); SET_BIT_IN_BYTE(val, 2); ak4647_write_reg(AK4647_PM1, val); msleep(30); /* headphone output switch on */ ak4647_read_reg(AK4647_MODE4, &val); SET_BIT_IN_BYTE(val, 0); ak4647_write_reg(AK4647_MODE4, val); /* power on headphone amp */ ak4647_read_reg(AK4647_PM2, &val); SET_BIT_IN_BYTE(val, 4); SET_BIT_IN_BYTE(val, 5); ak4647_write_reg(AK4647_PM2, val); ak4647_digital_mute(NULL, 0); } else { ak4647_digital_mute(NULL, 1); /* disbale loopback */ ak4647_read_reg(AK4647_MODE3, &val); CLEAR_BIT_IN_BYTE(val, 6); SET_BIT_IN_BYTE(val, 5); ak4647_write_reg(AK4647_MODE3, val); /* switch to R/L 2 */ ak4647_read_reg(AK4647_PM3, &val); SET_BIT_IN_BYTE(val, 1); SET_BIT_IN_BYTE(val, 2); ak4647_write_reg(AK4647_PM3, val); } return 0; }