]> Gitweb @ Texas Instruments - Open Source Git Repositories - git.TI.com/gitweb - tas2557sw-android/tas2557-android-driver.git/blobdiff - tas2557-codec.c
Change Magic Number for kernel 4.19 support
[tas2557sw-android/tas2557-android-driver.git] / tas2557-codec.c
index 1f365d8212de768931f5979f72d5b6134647066e..cf9c4193ee8a123d1dd833bf09b54a6f3bc94fd4 100755 (executable)
@@ -3,17 +3,13 @@
 ** Copyright (c) 2016  Texas Instruments Inc.
 **
 ** This program is free software; you can redistribute it and/or modify it under
-** the terms of the GNU General Public License as published by the Free Software 
+** the terms of the GNU General Public License as published by the Free Software
 ** Foundation; version 2.
 **
 ** This program is distributed in the hope that it will be useful, but WITHOUT
 ** ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
 ** FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
 **
-** You should have received a copy of the GNU General Public License along with
-** this program; if not, write to the Free Software Foundation, Inc., 51 Franklin
-** Street, Fifth Floor, Boston, MA 02110-1301, USA.
-**
 ** File:
 **     tas2557-codec.c
 **
@@ -41,7 +37,7 @@
 #include <linux/slab.h>
 #include <linux/syscalls.h>
 #include <linux/fcntl.h>
-#include <asm/uaccess.h>
+#include <linux/uaccess.h>
 #include <sound/core.h>
 #include <sound/pcm.h>
 #include <sound/pcm_params.h>
 
 #define KCONTROL_CODEC
 
-static struct tas2557_register register_addr = { 0 };
-
-#define TAS2557_REG_IS_VALID(book, page, reg) \
-        ((book >= 0) && (book <= 255) &&\
-        (page >= 0) && (page <= 255) &&\
-        (reg >= 0) && (reg <= 127))
-
 static unsigned int tas2557_codec_read(struct snd_soc_codec *pCodec,
        unsigned int nRegister)
 {
@@ -69,15 +58,16 @@ static unsigned int tas2557_codec_read(struct snd_soc_codec *pCodec,
        unsigned int Value = 0;
 
        mutex_lock(&pTAS2557->codec_lock);
+
        ret = pTAS2557->read(pTAS2557, nRegister, &Value);
-       mutex_unlock(&pTAS2557->codec_lock);
-       
-       if (ret < 0) {
-               dev_err(pTAS2557->dev, "%s, %d, ERROR happen=%d\n", __FUNCTION__,
+       if (ret < 0)
+               dev_err(pTAS2557->dev, "%s, %d, ERROR happen=%d\n", __func__,
                        __LINE__, ret);
-               return 0;
-       } else
-               return Value;
+       else
+               ret = Value;
+
+       mutex_unlock(&pTAS2557->codec_lock);
+       return ret;
 }
 
 static int tas2557_codec_write(struct snd_soc_codec *pCodec, unsigned int nRegister,
@@ -85,10 +75,40 @@ static int tas2557_codec_write(struct snd_soc_codec *pCodec, unsigned int nRegis
 {
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(pCodec);
        int ret = 0;
+
        mutex_lock(&pTAS2557->codec_lock);
+
        ret = pTAS2557->write(pTAS2557, nRegister, nValue);
+
+       mutex_unlock(&pTAS2557->codec_lock);
+       return ret;
+}
+
+static int tas2557_codec_suspend(struct snd_soc_codec *pCodec)
+{
+       struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(pCodec);
+       int ret = 0;
+
+       mutex_lock(&pTAS2557->codec_lock);
+
+       dev_dbg(pTAS2557->dev, "%s\n", __func__);
+       pTAS2557->runtime_suspend(pTAS2557);
+
+       mutex_unlock(&pTAS2557->codec_lock);
+       return ret;
+}
+
+static int tas2557_codec_resume(struct snd_soc_codec *pCodec)
+{
+       struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(pCodec);
+       int ret = 0;
+
+       mutex_lock(&pTAS2557->codec_lock);
+
+       dev_dbg(pTAS2557->dev, "%s\n", __func__);
+       pTAS2557->runtime_resume(pTAS2557);
+
        mutex_unlock(&pTAS2557->codec_lock);
-       
        return ret;
 }
 
@@ -121,9 +141,8 @@ static int tas2557_startup(struct snd_pcm_substream *substream,
 {
        struct snd_soc_codec *codec = dai->codec;
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-       
-       dev_dbg(pTAS2557->dev, "%s\n", __func__);
 
+       dev_dbg(pTAS2557->dev, "%s\n", __func__);
        return 0;
 }
 
@@ -140,12 +159,13 @@ static int tas2557_mute(struct snd_soc_dai *dai, int mute)
 {
        struct snd_soc_codec *codec = dai->codec;
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-       
-       dev_dbg(pTAS2557->dev, "%s\n", __func__);
+
        mutex_lock(&pTAS2557->codec_lock);
+
+       dev_dbg(pTAS2557->dev, "%s\n", __func__);
        tas2557_enable(pTAS2557, !mute);
+
        mutex_unlock(&pTAS2557->codec_lock);
-       
        return 0;
 }
 
@@ -166,12 +186,14 @@ static int tas2557_hw_params(struct snd_pcm_substream *pSubstream,
        struct snd_soc_codec *pCodec = pDAI->codec;
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(pCodec);
 
-       dev_dbg(pCodec->dev, "%s\n", __func__);
-       
        mutex_lock(&pTAS2557->codec_lock);
+
+       dev_dbg(pTAS2557->dev, "%s\n", __func__);
+/* do bit rate setting during platform data */
+/* tas2557_set_bit_rate(pTAS2557, channel_both, snd_pcm_format_width(params_format(pParams))); */
        tas2557_set_sampling_rate(pTAS2557, params_rate(pParams));
-       mutex_unlock(&pTAS2557->codec_lock);
 
+       mutex_unlock(&pTAS2557->codec_lock);
        return 0;
 }
 
@@ -179,9 +201,8 @@ static int tas2557_set_dai_fmt(struct snd_soc_dai *pDAI, unsigned int nFormat)
 {
        struct snd_soc_codec *codec = pDAI->codec;
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-       
+
        dev_dbg(pTAS2557->dev, "%s\n", __func__);
-       
        return 0;
 }
 
@@ -190,9 +211,8 @@ static int tas2557_prepare(struct snd_pcm_substream *pSubstream,
 {
        struct snd_soc_codec *codec = pDAI->codec;
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-       
+
        dev_dbg(pTAS2557->dev, "%s\n", __func__);
-       
        return 0;
 }
 
@@ -200,9 +220,8 @@ static int tas2557_set_bias_level(struct snd_soc_codec *pCodec,
        enum snd_soc_bias_level eLevel)
 {
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(pCodec);
-       
-       dev_dbg(pTAS2557->dev, "%s: %d\n", __func__, eLevel);
 
+       dev_dbg(pTAS2557->dev, "%s: %d\n", __func__, eLevel);
        return 0;
 }
 
@@ -210,8 +229,7 @@ static int tas2557_codec_probe(struct snd_soc_codec *pCodec)
 {
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(pCodec);
 
-       dev_info(pTAS2557->dev, "%s\n", __func__);
-
+       dev_dbg(pTAS2557->dev, "%s\n", __func__);
        return 0;
 }
 
@@ -220,8 +238,8 @@ static int tas2557_codec_remove(struct snd_soc_codec *pCodec)
        return 0;
 }
 
-static int tas2557_get_reg_addr(struct snd_kcontrol *pKcontrol,
-       struct snd_ctl_elem_value *pUcontrol)
+static int tas2557_power_ctrl_get(struct snd_kcontrol *pKcontrol,
+       struct snd_ctl_elem_value *pValue)
 {
 #ifdef KCONTROL_CODEC
        struct snd_soc_codec *codec = snd_soc_kcontrol_codec(pKcontrol);
@@ -230,18 +248,18 @@ static int tas2557_get_reg_addr(struct snd_kcontrol *pKcontrol,
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
 
-       pUcontrol->value.integer.value[0] = register_addr.book;
-       pUcontrol->value.integer.value[1] = register_addr.page;
-       pUcontrol->value.integer.value[2] = register_addr.reg;
+       mutex_lock(&pTAS2557->codec_lock);
 
-       dev_dbg(pTAS2557->dev, "%s: Get address [%d, %d, %d]\n", __func__,
-               register_addr.book, register_addr.page, register_addr.reg);
+       pValue->value.integer.value[0] = pTAS2557->mbPowerUp;
+       dev_dbg(pTAS2557->dev, "tas2557_power_ctrl_get = %d\n",
+               pTAS2557->mbPowerUp);
 
+       mutex_unlock(&pTAS2557->codec_lock);
        return 0;
 }
 
-static int tas2557_put_reg_addr(struct snd_kcontrol *pKcontrol,
-       struct snd_ctl_elem_value *pUcontrol)
+static int tas2557_power_ctrl_put(struct snd_kcontrol *pKcontrol,
+       struct snd_ctl_elem_value *pValue)
 {
 #ifdef KCONTROL_CODEC
        struct snd_soc_codec *codec = snd_soc_kcontrol_codec(pKcontrol);
@@ -250,52 +268,19 @@ static int tas2557_put_reg_addr(struct snd_kcontrol *pKcontrol,
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
 
-       register_addr.book = pUcontrol->value.integer.value[0];
-       register_addr.page = pUcontrol->value.integer.value[1];
-       register_addr.reg = pUcontrol->value.integer.value[2];
+       int nPowerOn = pValue->value.integer.value[0];
 
-       dev_dbg(pTAS2557->dev, "%s: Set address [%d, %d, %d]\n", __func__,
-               register_addr.book, register_addr.page, register_addr.reg);
+       mutex_lock(&pTAS2557->codec_lock);
 
-       return 0;
-}
+       dev_dbg(pTAS2557->dev, "tas2557_power_ctrl_put = %d\n", nPowerOn);
+       tas2557_enable(pTAS2557, (nPowerOn != 0));
 
-static int tas2557_get_reg_value(struct snd_kcontrol *pKcontrol,
-       struct snd_ctl_elem_value *pUcontrol)
-{
-#ifdef KCONTROL_CODEC
-       struct snd_soc_codec *codec = snd_soc_kcontrol_codec(pKcontrol);
-#else
-       struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
-#endif
-       struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-       unsigned int reg;
-       unsigned int nValue;
-
-       mutex_lock(&pTAS2557->codec_lock);      
-       
-       if (TAS2557_REG_IS_VALID(register_addr.book,
-                       register_addr.page, register_addr.reg)) {
-               reg = TAS2557_REG((unsigned int) register_addr.book,
-                       (unsigned int) register_addr.page,
-                       (unsigned int) register_addr.reg);
-               pTAS2557->read(pTAS2557, reg, &nValue);
-               pUcontrol->value.integer.value[0] = nValue;
-       } else {
-               dev_err(pTAS2557->dev, "%s: Invalid register address!\n", __func__);
-               pUcontrol->value.integer.value[0] = 0xFFFF;
-       }
-
-       dev_dbg(pTAS2557->dev, "%s: Read [%d, %d, %d] = %ld\n", __func__,
-               register_addr.book, register_addr.page, register_addr.reg,
-               pUcontrol->value.integer.value[0]);
-               
        mutex_unlock(&pTAS2557->codec_lock);
        return 0;
 }
 
-static int tas2557_put_reg_value(struct snd_kcontrol *pKcontrol,
-       struct snd_ctl_elem_value *pUcontrol)
+static int tas2557_fs_get(struct snd_kcontrol *pKcontrol,
+       struct snd_ctl_elem_value *pValue)
 {
 #ifdef KCONTROL_CODEC
        struct snd_soc_codec *codec = snd_soc_kcontrol_codec(pKcontrol);
@@ -303,49 +288,20 @@ static int tas2557_put_reg_value(struct snd_kcontrol *pKcontrol,
        struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-       unsigned int reg;
+       int nFS = 48000;
 
        mutex_lock(&pTAS2557->codec_lock);
-       
-       if (TAS2557_REG_IS_VALID(register_addr.book,
-                       register_addr.page, register_addr.reg)) {
-               reg = TAS2557_REG((unsigned int) register_addr.book,
-                       (unsigned int) register_addr.page,
-                       (unsigned int) register_addr.reg);
-               pTAS2557->write(pTAS2557, reg, pUcontrol->value.integer.value[0]);
-       } else {
-               dev_err(pTAS2557->dev, "%s: Invalid register address!\n", __func__);
-       }
-
-       dev_dbg(pTAS2557->dev, "%s: Write [%d, %d, %d] = %ld\n", __func__,
-               register_addr.book, register_addr.page, register_addr.reg,
-               pUcontrol->value.integer.value[0]);
-
-       mutex_unlock(&pTAS2557->codec_lock);                    
-       return 0;
-}
 
-static int tas2557_power_ctrl_get(struct snd_kcontrol *pKcontrol,
-       struct snd_ctl_elem_value *pValue)
-{
-#ifdef KCONTROL_CODEC
-       struct snd_soc_codec *codec = snd_soc_kcontrol_codec(pKcontrol);
-#else
-       struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
-#endif
-       struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
+       if (pTAS2557->mpFirmware->mnConfigurations)
+               nFS = pTAS2557->mpFirmware->mpConfigurations[pTAS2557->mnCurrentConfiguration].mnSamplingRate;
+       pValue->value.integer.value[0] = nFS;
+       dev_dbg(pTAS2557->dev, "tas2557_fs_get = %d\n", nFS);
 
-       mutex_lock(&pTAS2557->codec_lock);      
-       
-       pValue->value.integer.value[0] = pTAS2557->mnPowerCtrl;
-       dev_dbg(pTAS2557->dev, "tas2557_power_ctrl_get = %d\n",
-               pTAS2557->mnPowerCtrl);
-               
-       mutex_unlock(&pTAS2557->codec_lock);                    
+       mutex_unlock(&pTAS2557->codec_lock);
        return 0;
 }
 
-static int tas2557_power_ctrl_put(struct snd_kcontrol *pKcontrol,
+static int tas2557_fs_put(struct snd_kcontrol *pKcontrol,
        struct snd_ctl_elem_value *pValue)
 {
 #ifdef KCONTROL_CODEC
@@ -354,23 +310,19 @@ static int tas2557_power_ctrl_put(struct snd_kcontrol *pKcontrol,
        struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
+       int ret = 0;
+       int nFS = pValue->value.integer.value[0];
 
-       mutex_lock(&pTAS2557->codec_lock);      
-       pTAS2557->mnPowerCtrl = pValue->value.integer.value[0];
+       mutex_lock(&pTAS2557->codec_lock);
 
-       dev_dbg(pTAS2557->dev, "tas2557_power_ctrl_put = %d\n",
-               pTAS2557->mnPowerCtrl);
+       dev_info(pTAS2557->dev, "tas2557_fs_put = %d\n", nFS);
+       ret = tas2557_set_sampling_rate(pTAS2557, nFS);
 
-       if (pTAS2557->mnPowerCtrl == 1)
-               tas2557_enable(pTAS2557, true);
-       if (pTAS2557->mnPowerCtrl == 0)
-               tas2557_enable(pTAS2557, false);
-               
        mutex_unlock(&pTAS2557->codec_lock);
-       return 0;
+       return ret;
 }
 
-static int tas2557_fs_get(struct snd_kcontrol *pKcontrol,
+static int tas2557_Cali_get(struct snd_kcontrol *pKcontrol,
        struct snd_ctl_elem_value *pValue)
 {
 #ifdef KCONTROL_CODEC
@@ -379,41 +331,18 @@ static int tas2557_fs_get(struct snd_kcontrol *pKcontrol,
        struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-
-       int nFS = 48000;
+       bool ret = 0;
+       int prm_r0 = 0;
 
        mutex_lock(&pTAS2557->codec_lock);
-       
-       if (pTAS2557->mpFirmware->mnConfigurations)
-               nFS = pTAS2557->mpFirmware->mpConfigurations[pTAS2557->mnCurrentConfiguration].mnSamplingRate;
-       
-       pValue->value.integer.value[0] = nFS;
-       
-       mutex_unlock(&pTAS2557->codec_lock);    
-       
-       dev_info(pTAS2557->dev, "tas2557_fs_get = %d\n", nFS);
-       return 0;
-}
 
-static int tas2557_fs_put(struct snd_kcontrol *pKcontrol,
-       struct snd_ctl_elem_value *pValue)
-{
-#ifdef KCONTROL_CODEC
-       struct snd_soc_codec *codec = snd_soc_kcontrol_codec(pKcontrol);
-#else
-       struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
-#endif
-       struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-       int ret = 0;
-       int nFS = pValue->value.integer.value[0];
-       
-       dev_info(pTAS2557->dev, "tas2557_fs_put = %d\n", nFS);
-       
-       mutex_lock(&pTAS2557->codec_lock);      
-       ret = tas2557_set_sampling_rate(pTAS2557, nFS);
-       
-       mutex_unlock(&pTAS2557->codec_lock);    
-       return ret;
+       ret = tas2557_get_Cali_prm_r0(pTAS2557, &prm_r0);
+       if (ret)
+               pValue->value.integer.value[0] = prm_r0;
+
+
+       mutex_unlock(&pTAS2557->codec_lock);
+       return 0;
 }
 
 static int tas2557_program_get(struct snd_kcontrol *pKcontrol,
@@ -425,11 +354,14 @@ static int tas2557_program_get(struct snd_kcontrol *pKcontrol,
        struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
-       mutex_lock(&pTAS2557->codec_lock);      
+
+       mutex_lock(&pTAS2557->codec_lock);
+
        pValue->value.integer.value[0] = pTAS2557->mnCurrentProgram;
        dev_dbg(pTAS2557->dev, "tas2557_program_get = %d\n",
                pTAS2557->mnCurrentProgram);
-       mutex_unlock(&pTAS2557->codec_lock);                    
+
+       mutex_unlock(&pTAS2557->codec_lock);
        return 0;
 }
 
@@ -443,10 +375,15 @@ static int tas2557_program_put(struct snd_kcontrol *pKcontrol,
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
        unsigned int nProgram = pValue->value.integer.value[0];
-       int ret = 0;
-       mutex_lock(&pTAS2557->codec_lock);      
-       ret = tas2557_set_program(pTAS2557, nProgram);
-       mutex_unlock(&pTAS2557->codec_lock);    
+       int ret = 0, nConfiguration = -1;
+
+       mutex_lock(&pTAS2557->codec_lock);
+
+       if (nProgram == pTAS2557->mnCurrentProgram)
+               nConfiguration = pTAS2557->mnCurrentConfiguration;
+       ret = tas2557_set_program(pTAS2557, nProgram, nConfiguration);
+
+       mutex_unlock(&pTAS2557->codec_lock);
        return ret;
 }
 
@@ -460,11 +397,13 @@ static int tas2557_configuration_get(struct snd_kcontrol *pKcontrol,
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
 
-       mutex_lock(&pTAS2557->codec_lock);      
+       mutex_lock(&pTAS2557->codec_lock);
+
        pValue->value.integer.value[0] = pTAS2557->mnCurrentConfiguration;
        dev_dbg(pTAS2557->dev, "tas2557_configuration_get = %d\n",
                pTAS2557->mnCurrentConfiguration);
-       mutex_unlock(&pTAS2557->codec_lock);                    
+
+       mutex_unlock(&pTAS2557->codec_lock);
        return 0;
 }
 
@@ -480,9 +419,12 @@ static int tas2557_configuration_put(struct snd_kcontrol *pKcontrol,
        unsigned int nConfiguration = pValue->value.integer.value[0];
        int ret = 0;
 
-       mutex_lock(&pTAS2557->codec_lock);      
+       mutex_lock(&pTAS2557->codec_lock);
+
+       dev_info(pTAS2557->dev, "%s = %d\n", __func__, nConfiguration);
        ret = tas2557_set_config(pTAS2557, nConfiguration);
-       mutex_unlock(&pTAS2557->codec_lock);    
+
+       mutex_unlock(&pTAS2557->codec_lock);
        return ret;
 }
 
@@ -496,12 +438,14 @@ static int tas2557_calibration_get(struct snd_kcontrol *pKcontrol,
 #endif
        struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
 
-       mutex_lock(&pTAS2557->codec_lock);      
+       mutex_lock(&pTAS2557->codec_lock);
+
        pValue->value.integer.value[0] = pTAS2557->mnCurrentCalibration;
        dev_info(pTAS2557->dev,
                "tas2557_calibration_get = %d\n",
                pTAS2557->mnCurrentCalibration);
-       mutex_unlock(&pTAS2557->codec_lock);                    
+
+       mutex_unlock(&pTAS2557->codec_lock);
        return 0;
 }
 
@@ -517,25 +461,67 @@ static int tas2557_calibration_put(struct snd_kcontrol *pKcontrol,
        unsigned int nCalibration = pValue->value.integer.value[0];
        int ret = 0;
 
-       mutex_lock(&pTAS2557->codec_lock);              
+       mutex_lock(&pTAS2557->codec_lock);
+
        ret = tas2557_set_calibration(pTAS2557, nCalibration);
-       mutex_unlock(&pTAS2557->codec_lock);    
-       
+
+       mutex_unlock(&pTAS2557->codec_lock);
        return ret;
 }
 
-/*
- * DAC digital volumes. From 0 to 15 dB in 1 dB steps
- */
-static DECLARE_TLV_DB_SCALE(dac_tlv, 0, 100, 0);
+static const char * const classd_edge_text[] = {
+       "0 (50ns)",
+       "1 (40ns)",
+       "2 (29ns)",
+       "3 (25ns)",
+       "4 (14ns)",
+       "5 (13ns)",
+       "6 (12ns)",
+       "7 (11ns)",
+};
+
+static const struct soc_enum classd_edge_enum[] = {
+       SOC_ENUM_SINGLE_EXT(ARRAY_SIZE(classd_edge_text), classd_edge_text),
+};
+
+static int tas2557_edge_get(struct snd_kcontrol *pKcontrol,
+                       struct snd_ctl_elem_value *pValue)
+{
+#ifdef KCONTROL_CODEC
+       struct snd_soc_codec *codec = snd_soc_kcontrol_codec(pKcontrol);
+#else
+       struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
+#endif
+       struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
+       mutex_lock(&pTAS2557->codec_lock);
+
+       pValue->value.integer.value[0] = pTAS2557->mnEdge;
+
+       mutex_unlock(&pTAS2557->codec_lock);
+       return 0;
+}
+static int tas2557_edge_put(struct snd_kcontrol *pKcontrol,
+                       struct snd_ctl_elem_value *pValue)
+{
+#ifdef KCONTROL_CODEC
+       struct snd_soc_codec *codec = snd_soc_kcontrol_codec(pKcontrol);
+#else
+       struct snd_soc_codec *codec = snd_kcontrol_chip(pKcontrol);
+#endif
+       struct tas2557_priv *pTAS2557 = snd_soc_codec_get_drvdata(codec);
+       unsigned int edge = pValue->value.integer.value[0];
+
+       mutex_lock(&pTAS2557->codec_lock);
+
+       dev_dbg(pTAS2557->dev, "%s, edge %d\n", __func__, edge);
+       pTAS2557->mnEdge = pValue->value.integer.value[0];
+       tas2557_update_edge(pTAS2557);
+
+       mutex_unlock(&pTAS2557->codec_lock);
+       return 0;
+}
 
 static const struct snd_kcontrol_new tas2557_snd_controls[] = {
-       SOC_SINGLE_TLV("DAC Playback Volume", TAS2557_SPK_CTRL_REG, 3, 0x0f, 0,
-               dac_tlv),
-       SOC_SINGLE_MULTI_EXT("Reg Addr", 0, 0, INT_MAX, 0, 3, tas2557_get_reg_addr,
-               tas2557_put_reg_addr),
-       SOC_SINGLE_EXT("Reg Value", SND_SOC_NOPM, 0, 0xFFFF, 0,
-               tas2557_get_reg_value, tas2557_put_reg_value),
        SOC_SINGLE_EXT("PowerCtrl", SND_SOC_NOPM, 0, 0x0001, 0,
                tas2557_power_ctrl_get, tas2557_power_ctrl_put),
        SOC_SINGLE_EXT("Program", SND_SOC_NOPM, 0, 0x00FF, 0, tas2557_program_get,
@@ -544,8 +530,12 @@ static const struct snd_kcontrol_new tas2557_snd_controls[] = {
                tas2557_configuration_get, tas2557_configuration_put),
        SOC_SINGLE_EXT("FS", SND_SOC_NOPM, 8000, 48000, 0,
                tas2557_fs_get, tas2557_fs_put),
+       SOC_SINGLE_EXT("Get Cali_Re", SND_SOC_NOPM, 0, 0x7f000000, 0,
+               tas2557_Cali_get, NULL),
        SOC_SINGLE_EXT("Calibration", SND_SOC_NOPM, 0, 0x00FF, 0,
                tas2557_calibration_get, tas2557_calibration_put),
+       SOC_ENUM_EXT("TAS2557 ClassD Edge", classd_edge_enum[0],
+               tas2557_edge_get, tas2557_edge_put),
 };
 
 static struct snd_soc_codec_driver soc_codec_driver_tas2557 = {
@@ -553,15 +543,18 @@ static struct snd_soc_codec_driver soc_codec_driver_tas2557 = {
        .remove = tas2557_codec_remove,
        .read = tas2557_codec_read,
        .write = tas2557_codec_write,
+       .suspend = tas2557_codec_suspend,
+       .resume = tas2557_codec_resume,
        .set_bias_level = tas2557_set_bias_level,
        .idle_bias_off = true,
-       //.ignore_pmdown_time = true,
-       .controls = tas2557_snd_controls,
-       .num_controls = ARRAY_SIZE(tas2557_snd_controls),
-       .dapm_widgets = tas2557_dapm_widgets,
-       .num_dapm_widgets = ARRAY_SIZE(tas2557_dapm_widgets),
-       .dapm_routes = tas2557_audio_map,
-       .num_dapm_routes = ARRAY_SIZE(tas2557_audio_map),
+       .component_driver = {
+               .controls = tas2557_snd_controls,
+               .num_controls = ARRAY_SIZE(tas2557_snd_controls),
+               .dapm_widgets = tas2557_dapm_widgets,
+               .num_dapm_widgets = ARRAY_SIZE(tas2557_dapm_widgets),
+               .dapm_routes = tas2557_audio_map,
+               .num_dapm_routes = ARRAY_SIZE(tas2557_audio_map),
+       },
 };
 
 static struct snd_soc_dai_ops tas2557_dai_ops = {
@@ -575,7 +568,7 @@ static struct snd_soc_dai_ops tas2557_dai_ops = {
 };
 
 #define TAS2557_FORMATS (SNDRV_PCM_FMTBIT_S16_LE | SNDRV_PCM_FMTBIT_S20_3LE |\
-             SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S32_LE)
+       SNDRV_PCM_FMTBIT_S24_LE | SNDRV_PCM_FMTBIT_S32_LE)
 static struct snd_soc_dai_driver tas2557_dai_driver[] = {
        {
                .name = "tas2557 ASI1",
@@ -622,23 +615,20 @@ int tas2557_register_codec(struct tas2557_priv *pTAS2557)
 {
        int nResult = 0;
 
-       dev_info(pTAS2557->dev, "%s, enter\n", __FUNCTION__);
-         
-       nResult = snd_soc_register_codec(pTAS2557->dev, 
+       dev_info(pTAS2557->dev, "%s, enter\n", __func__);
+       nResult = snd_soc_register_codec(pTAS2557->dev,
                &soc_codec_driver_tas2557,
                tas2557_dai_driver, ARRAY_SIZE(tas2557_dai_driver));
-               
        return nResult;
 }
 
 int tas2557_deregister_codec(struct tas2557_priv *pTAS2557)
 {
        snd_soc_unregister_codec(pTAS2557->dev);
-               
        return 0;
 }
 
 MODULE_AUTHOR("Texas Instruments Inc.");
 MODULE_DESCRIPTION("TAS2557 ALSA SOC Smart Amplifier driver");
-MODULE_LICENSE("GPLv2");
+MODULE_LICENSE("GPL v2");
 #endif