| .. | .. |
|---|
| 20 | 20 | #include <linux/mfd/syscon.h> |
|---|
| 21 | 21 | #include <linux/regmap.h> |
|---|
| 22 | 22 | #include <sound/pcm_params.h> |
|---|
| 23 | +#include <sound/pcm_iec958.h> |
|---|
| 23 | 24 | #include <sound/dmaengine_pcm.h> |
|---|
| 24 | 25 | |
|---|
| 25 | 26 | #include "rockchip_spdif.h" |
|---|
| .. | .. |
|---|
| 31 | 32 | RK_SPDIF_RK3366, |
|---|
| 32 | 33 | }; |
|---|
| 33 | 34 | |
|---|
| 34 | | -#define RK3288_GRF_SOC_CON2 0x24c |
|---|
| 35 | +/* |
|---|
| 36 | + * | 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 | |
|---|
| 37 | + * CS0: | Mode | d | c | b | a | |
|---|
| 38 | + * CS1: | Category Code | |
|---|
| 39 | + * CS2: | Channel Number | Source Number | |
|---|
| 40 | + * CS3: | Clock Accuracy | Sample Freq | |
|---|
| 41 | + * CS4: | Ori Sample Freq | Word Length | |
|---|
| 42 | + * CS5: | | CGMS-A | |
|---|
| 43 | + * CS6~CS23: Reserved |
|---|
| 44 | + * |
|---|
| 45 | + * a: use of channel status block |
|---|
| 46 | + * b: linear PCM identification: 0 for lpcm, 1 for nlpcm |
|---|
| 47 | + * c: copyright information |
|---|
| 48 | + * d: additional format information |
|---|
| 49 | + */ |
|---|
| 50 | +#define CS_BYTE 6 |
|---|
| 51 | +#define CS_FRAME(c) ((c) << 16 | (c)) |
|---|
| 52 | + |
|---|
| 53 | +#define RK3288_GRF_SOC_CON2 0x24c |
|---|
| 35 | 54 | |
|---|
| 36 | 55 | struct rk_spdif_dev { |
|---|
| 37 | 56 | struct device *dev; |
|---|
| .. | .. |
|---|
| 114 | 133 | struct rk_spdif_dev *spdif = snd_soc_dai_get_drvdata(dai); |
|---|
| 115 | 134 | unsigned int val = SPDIF_CFGR_HALFWORD_ENABLE; |
|---|
| 116 | 135 | int srate, mclk; |
|---|
| 117 | | - int ret; |
|---|
| 136 | + int ret, i; |
|---|
| 137 | + u8 cs[CS_BYTE]; |
|---|
| 138 | + u16 *fc = (u16 *)cs; |
|---|
| 139 | + |
|---|
| 140 | + ret = snd_pcm_create_iec958_consumer_hw_params(params, cs, sizeof(cs)); |
|---|
| 141 | + if (ret < 0) |
|---|
| 142 | + return ret; |
|---|
| 143 | + |
|---|
| 144 | + for (i = 0; i < CS_BYTE / 2; i++) |
|---|
| 145 | + regmap_write(spdif->regmap, SPDIF_CHNSRn(i), CS_FRAME(fc[i])); |
|---|
| 146 | + |
|---|
| 147 | + regmap_update_bits(spdif->regmap, SPDIF_CFGR, SPDIF_CFGR_CSE_MASK, |
|---|
| 148 | + SPDIF_CFGR_CSE_EN); |
|---|
| 118 | 149 | |
|---|
| 119 | 150 | srate = params_rate(params); |
|---|
| 120 | 151 | mclk = srate * 128; |
|---|
| .. | .. |
|---|
| 128 | 159 | break; |
|---|
| 129 | 160 | case SNDRV_PCM_FORMAT_S24_LE: |
|---|
| 130 | 161 | val |= SPDIF_CFGR_VDW_24; |
|---|
| 162 | + val |= SPDIF_CFGR_ADJ_RIGHT_J; |
|---|
| 163 | + break; |
|---|
| 164 | + case SNDRV_PCM_FORMAT_S32_LE: |
|---|
| 165 | + val |= SPDIF_CFGR_VDW_24; |
|---|
| 166 | + val |= SPDIF_CFGR_ADJ_LEFT_J; |
|---|
| 131 | 167 | break; |
|---|
| 132 | 168 | default: |
|---|
| 133 | 169 | return -EINVAL; |
|---|
| .. | .. |
|---|
| 141 | 177 | return ret; |
|---|
| 142 | 178 | } |
|---|
| 143 | 179 | |
|---|
| 180 | + regmap_update_bits(spdif->regmap, SPDIF_CFGR, SPDIF_CFGR_CLR_MASK, |
|---|
| 181 | + SPDIF_CFGR_CLR_EN); |
|---|
| 182 | + udelay(1); |
|---|
| 144 | 183 | ret = regmap_update_bits(spdif->regmap, SPDIF_CFGR, |
|---|
| 145 | 184 | SPDIF_CFGR_CLK_DIV_MASK | |
|---|
| 146 | 185 | SPDIF_CFGR_HALFWORD_ENABLE | |
|---|
| 147 | | - SDPIF_CFGR_VDW_MASK, val); |
|---|
| 186 | + SDPIF_CFGR_VDW_MASK | |
|---|
| 187 | + SPDIF_CFGR_ADJ_MASK, val); |
|---|
| 148 | 188 | |
|---|
| 149 | 189 | return ret; |
|---|
| 150 | 190 | } |
|---|
| .. | .. |
|---|
| 214 | 254 | .stream_name = "Playback", |
|---|
| 215 | 255 | .channels_min = 2, |
|---|
| 216 | 256 | .channels_max = 2, |
|---|
| 217 | | - .rates = (SNDRV_PCM_RATE_32000 | |
|---|
| 218 | | - SNDRV_PCM_RATE_44100 | |
|---|
| 219 | | - SNDRV_PCM_RATE_48000 | |
|---|
| 220 | | - SNDRV_PCM_RATE_96000 | |
|---|
| 221 | | - SNDRV_PCM_RATE_192000), |
|---|
| 257 | + .rates = SNDRV_PCM_RATE_8000_192000, |
|---|
| 222 | 258 | .formats = (SNDRV_PCM_FMTBIT_S16_LE | |
|---|
| 223 | 259 | SNDRV_PCM_FMTBIT_S20_3LE | |
|---|
| 224 | | - SNDRV_PCM_FMTBIT_S24_LE), |
|---|
| 260 | + SNDRV_PCM_FMTBIT_S24_LE | |
|---|
| 261 | + SNDRV_PCM_FMTBIT_S32_LE), |
|---|
| 225 | 262 | }, |
|---|
| 226 | 263 | .ops = &rk_spdif_dai_ops, |
|---|
| 227 | 264 | }; |
|---|
| .. | .. |
|---|
| 238 | 275 | case SPDIF_INTCR: |
|---|
| 239 | 276 | case SPDIF_XFER: |
|---|
| 240 | 277 | case SPDIF_SMPDR: |
|---|
| 278 | + case SPDIF_VLDFRn(0) ... SPDIF_VLDFRn(11): |
|---|
| 279 | + case SPDIF_USRDRn(0) ... SPDIF_USRDRn(11): |
|---|
| 280 | + case SPDIF_CHNSRn(0) ... SPDIF_CHNSRn(11): |
|---|
| 241 | 281 | return true; |
|---|
| 242 | 282 | default: |
|---|
| 243 | 283 | return false; |
|---|
| .. | .. |
|---|
| 253 | 293 | case SPDIF_INTSR: |
|---|
| 254 | 294 | case SPDIF_XFER: |
|---|
| 255 | 295 | case SPDIF_SMPDR: |
|---|
| 296 | + case SPDIF_VLDFRn(0) ... SPDIF_VLDFRn(11): |
|---|
| 297 | + case SPDIF_USRDRn(0) ... SPDIF_USRDRn(11): |
|---|
| 298 | + case SPDIF_CHNSRn(0) ... SPDIF_CHNSRn(11): |
|---|
| 256 | 299 | return true; |
|---|
| 257 | 300 | default: |
|---|
| 258 | 301 | return false; |
|---|
| .. | .. |
|---|
| 275 | 318 | .reg_bits = 32, |
|---|
| 276 | 319 | .reg_stride = 4, |
|---|
| 277 | 320 | .val_bits = 32, |
|---|
| 278 | | - .max_register = SPDIF_SMPDR, |
|---|
| 321 | + .max_register = SPDIF_VERSION, |
|---|
| 279 | 322 | .writeable_reg = rk_spdif_wr_reg, |
|---|
| 280 | 323 | .readable_reg = rk_spdif_rd_reg, |
|---|
| 281 | 324 | .volatile_reg = rk_spdif_volatile_reg, |
|---|