0001
0002
0003
0004
0005
0006
0007
0008
0009 #include <linux/module.h>
0010 #include <linux/regmap.h>
0011
0012 #include "cs35l45.h"
0013
0014 static const struct reg_sequence cs35l45_patch[] = {
0015 { 0x00000040, 0x00000055 },
0016 { 0x00000040, 0x000000AA },
0017 { 0x00000044, 0x00000055 },
0018 { 0x00000044, 0x000000AA },
0019 { 0x00006480, 0x0830500A },
0020 { 0x00007C60, 0x1000850B },
0021 { CS35L45_BOOST_OV_CFG, 0x007000D0 },
0022 { CS35L45_LDPM_CONFIG, 0x0001B636 },
0023 { 0x00002C08, 0x00000009 },
0024 { 0x00006850, 0x0A30FFC4 },
0025 { 0x00003820, 0x00040100 },
0026 { 0x00003824, 0x00000000 },
0027 { 0x00007CFC, 0x62870004 },
0028 { 0x00007C60, 0x1001850B },
0029 { 0x00000040, 0x00000000 },
0030 { 0x00000044, 0x00000000 },
0031 { CS35L45_BOOST_CCM_CFG, 0xF0000003 },
0032 { CS35L45_BOOST_DCM_CFG, 0x08710220 },
0033 { CS35L45_ERROR_RELEASE, 0x00200000 },
0034 };
0035
0036 int cs35l45_apply_patch(struct cs35l45_private *cs35l45)
0037 {
0038 return regmap_register_patch(cs35l45->regmap, cs35l45_patch,
0039 ARRAY_SIZE(cs35l45_patch));
0040 }
0041 EXPORT_SYMBOL_NS_GPL(cs35l45_apply_patch, SND_SOC_CS35L45_TABLES);
0042
0043 static const struct reg_default cs35l45_defaults[] = {
0044 { CS35L45_BLOCK_ENABLES, 0x00003323 },
0045 { CS35L45_BLOCK_ENABLES2, 0x00000010 },
0046 { CS35L45_REFCLK_INPUT, 0x00000510 },
0047 { CS35L45_GLOBAL_SAMPLE_RATE, 0x00000003 },
0048 { CS35L45_ASP_ENABLES1, 0x00000000 },
0049 { CS35L45_ASP_CONTROL1, 0x00000028 },
0050 { CS35L45_ASP_CONTROL2, 0x18180200 },
0051 { CS35L45_ASP_CONTROL3, 0x00000002 },
0052 { CS35L45_ASP_FRAME_CONTROL1, 0x03020100 },
0053 { CS35L45_ASP_FRAME_CONTROL2, 0x00000004 },
0054 { CS35L45_ASP_FRAME_CONTROL5, 0x00000100 },
0055 { CS35L45_ASP_DATA_CONTROL1, 0x00000018 },
0056 { CS35L45_ASP_DATA_CONTROL5, 0x00000018 },
0057 { CS35L45_DACPCM1_INPUT, 0x00000008 },
0058 { CS35L45_ASPTX1_INPUT, 0x00000018 },
0059 { CS35L45_ASPTX2_INPUT, 0x00000019 },
0060 { CS35L45_ASPTX3_INPUT, 0x00000020 },
0061 { CS35L45_ASPTX4_INPUT, 0x00000028 },
0062 { CS35L45_ASPTX5_INPUT, 0x00000048 },
0063 { CS35L45_AMP_PCM_CONTROL, 0x00100000 },
0064 };
0065
0066 static bool cs35l45_readable_reg(struct device *dev, unsigned int reg)
0067 {
0068 switch (reg) {
0069 case CS35L45_DEVID ... CS35L45_OTPID:
0070 case CS35L45_SFT_RESET:
0071 case CS35L45_GLOBAL_ENABLES:
0072 case CS35L45_BLOCK_ENABLES:
0073 case CS35L45_BLOCK_ENABLES2:
0074 case CS35L45_ERROR_RELEASE:
0075 case CS35L45_REFCLK_INPUT:
0076 case CS35L45_GLOBAL_SAMPLE_RATE:
0077 case CS35L45_ASP_ENABLES1:
0078 case CS35L45_ASP_CONTROL1:
0079 case CS35L45_ASP_CONTROL2:
0080 case CS35L45_ASP_CONTROL3:
0081 case CS35L45_ASP_FRAME_CONTROL1:
0082 case CS35L45_ASP_FRAME_CONTROL2:
0083 case CS35L45_ASP_FRAME_CONTROL5:
0084 case CS35L45_ASP_DATA_CONTROL1:
0085 case CS35L45_ASP_DATA_CONTROL5:
0086 case CS35L45_DACPCM1_INPUT:
0087 case CS35L45_ASPTX1_INPUT:
0088 case CS35L45_ASPTX2_INPUT:
0089 case CS35L45_ASPTX3_INPUT:
0090 case CS35L45_ASPTX4_INPUT:
0091 case CS35L45_ASPTX5_INPUT:
0092 case CS35L45_AMP_PCM_CONTROL:
0093 case CS35L45_AMP_PCM_HPF_TST:
0094 case CS35L45_IRQ1_EINT_4:
0095 return true;
0096 default:
0097 return false;
0098 }
0099 }
0100
0101 static bool cs35l45_volatile_reg(struct device *dev, unsigned int reg)
0102 {
0103 switch (reg) {
0104 case CS35L45_DEVID ... CS35L45_OTPID:
0105 case CS35L45_SFT_RESET:
0106 case CS35L45_GLOBAL_ENABLES:
0107 case CS35L45_ERROR_RELEASE:
0108 case CS35L45_AMP_PCM_HPF_TST:
0109 case CS35L45_IRQ1_EINT_4:
0110 return true;
0111 default:
0112 return false;
0113 }
0114 }
0115
0116 const struct regmap_config cs35l45_i2c_regmap = {
0117 .reg_bits = 32,
0118 .val_bits = 32,
0119 .reg_stride = 4,
0120 .reg_format_endian = REGMAP_ENDIAN_BIG,
0121 .val_format_endian = REGMAP_ENDIAN_BIG,
0122 .max_register = CS35L45_LASTREG,
0123 .reg_defaults = cs35l45_defaults,
0124 .num_reg_defaults = ARRAY_SIZE(cs35l45_defaults),
0125 .volatile_reg = cs35l45_volatile_reg,
0126 .readable_reg = cs35l45_readable_reg,
0127 .cache_type = REGCACHE_RBTREE,
0128 };
0129 EXPORT_SYMBOL_NS_GPL(cs35l45_i2c_regmap, SND_SOC_CS35L45_TABLES);
0130
0131 const struct regmap_config cs35l45_spi_regmap = {
0132 .reg_bits = 32,
0133 .val_bits = 32,
0134 .pad_bits = 16,
0135 .reg_stride = 4,
0136 .reg_format_endian = REGMAP_ENDIAN_BIG,
0137 .val_format_endian = REGMAP_ENDIAN_BIG,
0138 .max_register = CS35L45_LASTREG,
0139 .reg_defaults = cs35l45_defaults,
0140 .num_reg_defaults = ARRAY_SIZE(cs35l45_defaults),
0141 .volatile_reg = cs35l45_volatile_reg,
0142 .readable_reg = cs35l45_readable_reg,
0143 .cache_type = REGCACHE_RBTREE,
0144 };
0145 EXPORT_SYMBOL_NS_GPL(cs35l45_spi_regmap, SND_SOC_CS35L45_TABLES);
0146
0147 static const struct {
0148 u8 cfg_id;
0149 u32 freq;
0150 } cs35l45_pll_refclk_freq[] = {
0151 { 0x0C, 128000 },
0152 { 0x0F, 256000 },
0153 { 0x11, 384000 },
0154 { 0x12, 512000 },
0155 { 0x15, 768000 },
0156 { 0x17, 1024000 },
0157 { 0x19, 1411200 },
0158 { 0x1B, 1536000 },
0159 { 0x1C, 2116800 },
0160 { 0x1D, 2048000 },
0161 { 0x1E, 2304000 },
0162 { 0x1F, 2822400 },
0163 { 0x21, 3072000 },
0164 { 0x23, 4233600 },
0165 { 0x24, 4096000 },
0166 { 0x25, 4608000 },
0167 { 0x26, 5644800 },
0168 { 0x27, 6000000 },
0169 { 0x28, 6144000 },
0170 { 0x29, 6350400 },
0171 { 0x2A, 6912000 },
0172 { 0x2D, 7526400 },
0173 { 0x2E, 8467200 },
0174 { 0x2F, 8192000 },
0175 { 0x30, 9216000 },
0176 { 0x31, 11289600 },
0177 { 0x33, 12288000 },
0178 { 0x37, 16934400 },
0179 { 0x38, 18432000 },
0180 { 0x39, 22579200 },
0181 { 0x3B, 24576000 },
0182 };
0183
0184 unsigned int cs35l45_get_clk_freq_id(unsigned int freq)
0185 {
0186 int i;
0187
0188 if (freq == 0)
0189 return -EINVAL;
0190
0191 for (i = 0; i < ARRAY_SIZE(cs35l45_pll_refclk_freq); ++i) {
0192 if (cs35l45_pll_refclk_freq[i].freq == freq)
0193 return cs35l45_pll_refclk_freq[i].cfg_id;
0194 }
0195
0196 return -EINVAL;
0197 }
0198 EXPORT_SYMBOL_NS_GPL(cs35l45_get_clk_freq_id, SND_SOC_CS35L45_TABLES);
0199
0200 MODULE_DESCRIPTION("ASoC CS35L45 driver tables");
0201 MODULE_AUTHOR("James Schulman, Cirrus Logic Inc, <james.schulman@cirrus.com>");
0202 MODULE_LICENSE("Dual BSD/GPL");