1856 lines · c
1// SPDX-License-Identifier: GPL-2.0-only2/*3 * intel_hdmi_audio.c - Intel HDMI audio driver4 *5 * Copyright (C) 2016 Intel Corp6 * Authors: Sailaja Bandarupalli <sailaja.bandarupalli@intel.com>7 * Ramesh Babu K V <ramesh.babu@intel.com>8 * Vaibhav Agarwal <vaibhav.agarwal@intel.com>9 * Jerome Anand <jerome.anand@intel.com>10 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~11 *12 * ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~13 * ALSA driver for Intel HDMI audio14 */15 16#include <linux/types.h>17#include <linux/platform_device.h>18#include <linux/io.h>19#include <linux/slab.h>20#include <linux/module.h>21#include <linux/interrupt.h>22#include <linux/pm_runtime.h>23#include <linux/dma-mapping.h>24#include <linux/delay.h>25#include <sound/core.h>26#include <sound/asoundef.h>27#include <sound/pcm.h>28#include <sound/pcm_params.h>29#include <sound/initval.h>30#include <sound/control.h>31#include <sound/jack.h>32#include <drm/drm_edid.h>33#include <drm/drm_eld.h>34#include <drm/intel/intel_lpe_audio.h>35#include "intel_hdmi_audio.h"36 37#define INTEL_HDMI_AUDIO_SUSPEND_DELAY_MS 500038 39#define for_each_pipe(card_ctx, pipe) \40 for ((pipe) = 0; (pipe) < (card_ctx)->num_pipes; (pipe)++)41#define for_each_port(card_ctx, port) \42 for ((port) = 0; (port) < (card_ctx)->num_ports; (port)++)43 44/*standard module options for ALSA. This module supports only one card*/45static int hdmi_card_index = SNDRV_DEFAULT_IDX1;46static char *hdmi_card_id = SNDRV_DEFAULT_STR1;47static bool single_port;48 49module_param_named(index, hdmi_card_index, int, 0444);50MODULE_PARM_DESC(index,51 "Index value for INTEL Intel HDMI Audio controller.");52module_param_named(id, hdmi_card_id, charp, 0444);53MODULE_PARM_DESC(id,54 "ID string for INTEL Intel HDMI Audio controller.");55module_param(single_port, bool, 0444);56MODULE_PARM_DESC(single_port,57 "Single-port mode (for compatibility)");58 59/*60 * ELD SA bits in the CEA Speaker Allocation data block61 */62static const int eld_speaker_allocation_bits[] = {63 [0] = FL | FR,64 [1] = LFE,65 [2] = FC,66 [3] = RL | RR,67 [4] = RC,68 [5] = FLC | FRC,69 [6] = RLC | RRC,70 /* the following are not defined in ELD yet */71 [7] = 0,72};73 74/*75 * This is an ordered list!76 *77 * The preceding ones have better chances to be selected by78 * hdmi_channel_allocation().79 */80static struct cea_channel_speaker_allocation channel_allocations[] = {81/* channel: 7 6 5 4 3 2 1 0 */82{ .ca_index = 0x00, .speakers = { 0, 0, 0, 0, 0, 0, FR, FL } },83 /* 2.1 */84{ .ca_index = 0x01, .speakers = { 0, 0, 0, 0, 0, LFE, FR, FL } },85 /* Dolby Surround */86{ .ca_index = 0x02, .speakers = { 0, 0, 0, 0, FC, 0, FR, FL } },87 /* surround40 */88{ .ca_index = 0x08, .speakers = { 0, 0, RR, RL, 0, 0, FR, FL } },89 /* surround41 */90{ .ca_index = 0x09, .speakers = { 0, 0, RR, RL, 0, LFE, FR, FL } },91 /* surround50 */92{ .ca_index = 0x0a, .speakers = { 0, 0, RR, RL, FC, 0, FR, FL } },93 /* surround51 */94{ .ca_index = 0x0b, .speakers = { 0, 0, RR, RL, FC, LFE, FR, FL } },95 /* 6.1 */96{ .ca_index = 0x0f, .speakers = { 0, RC, RR, RL, FC, LFE, FR, FL } },97 /* surround71 */98{ .ca_index = 0x13, .speakers = { RRC, RLC, RR, RL, FC, LFE, FR, FL } },99 100{ .ca_index = 0x03, .speakers = { 0, 0, 0, 0, FC, LFE, FR, FL } },101{ .ca_index = 0x04, .speakers = { 0, 0, 0, RC, 0, 0, FR, FL } },102{ .ca_index = 0x05, .speakers = { 0, 0, 0, RC, 0, LFE, FR, FL } },103{ .ca_index = 0x06, .speakers = { 0, 0, 0, RC, FC, 0, FR, FL } },104{ .ca_index = 0x07, .speakers = { 0, 0, 0, RC, FC, LFE, FR, FL } },105{ .ca_index = 0x0c, .speakers = { 0, RC, RR, RL, 0, 0, FR, FL } },106{ .ca_index = 0x0d, .speakers = { 0, RC, RR, RL, 0, LFE, FR, FL } },107{ .ca_index = 0x0e, .speakers = { 0, RC, RR, RL, FC, 0, FR, FL } },108{ .ca_index = 0x10, .speakers = { RRC, RLC, RR, RL, 0, 0, FR, FL } },109{ .ca_index = 0x11, .speakers = { RRC, RLC, RR, RL, 0, LFE, FR, FL } },110{ .ca_index = 0x12, .speakers = { RRC, RLC, RR, RL, FC, 0, FR, FL } },111{ .ca_index = 0x14, .speakers = { FRC, FLC, 0, 0, 0, 0, FR, FL } },112{ .ca_index = 0x15, .speakers = { FRC, FLC, 0, 0, 0, LFE, FR, FL } },113{ .ca_index = 0x16, .speakers = { FRC, FLC, 0, 0, FC, 0, FR, FL } },114{ .ca_index = 0x17, .speakers = { FRC, FLC, 0, 0, FC, LFE, FR, FL } },115{ .ca_index = 0x18, .speakers = { FRC, FLC, 0, RC, 0, 0, FR, FL } },116{ .ca_index = 0x19, .speakers = { FRC, FLC, 0, RC, 0, LFE, FR, FL } },117{ .ca_index = 0x1a, .speakers = { FRC, FLC, 0, RC, FC, 0, FR, FL } },118{ .ca_index = 0x1b, .speakers = { FRC, FLC, 0, RC, FC, LFE, FR, FL } },119{ .ca_index = 0x1c, .speakers = { FRC, FLC, RR, RL, 0, 0, FR, FL } },120{ .ca_index = 0x1d, .speakers = { FRC, FLC, RR, RL, 0, LFE, FR, FL } },121{ .ca_index = 0x1e, .speakers = { FRC, FLC, RR, RL, FC, 0, FR, FL } },122{ .ca_index = 0x1f, .speakers = { FRC, FLC, RR, RL, FC, LFE, FR, FL } },123};124 125static const struct channel_map_table map_tables[] = {126 { SNDRV_CHMAP_FL, 0x00, FL },127 { SNDRV_CHMAP_FR, 0x01, FR },128 { SNDRV_CHMAP_RL, 0x04, RL },129 { SNDRV_CHMAP_RR, 0x05, RR },130 { SNDRV_CHMAP_LFE, 0x02, LFE },131 { SNDRV_CHMAP_FC, 0x03, FC },132 { SNDRV_CHMAP_RLC, 0x06, RLC },133 { SNDRV_CHMAP_RRC, 0x07, RRC },134 {} /* terminator */135};136 137/* hardware capability structure */138static const struct snd_pcm_hardware had_pcm_hardware = {139 .info = (SNDRV_PCM_INFO_INTERLEAVED |140 SNDRV_PCM_INFO_MMAP |141 SNDRV_PCM_INFO_MMAP_VALID |142 SNDRV_PCM_INFO_NO_PERIOD_WAKEUP),143 .formats = (SNDRV_PCM_FMTBIT_S16_LE |144 SNDRV_PCM_FMTBIT_S24_LE |145 SNDRV_PCM_FMTBIT_S32_LE),146 .rates = SNDRV_PCM_RATE_32000 |147 SNDRV_PCM_RATE_44100 |148 SNDRV_PCM_RATE_48000 |149 SNDRV_PCM_RATE_88200 |150 SNDRV_PCM_RATE_96000 |151 SNDRV_PCM_RATE_176400 |152 SNDRV_PCM_RATE_192000,153 .rate_min = HAD_MIN_RATE,154 .rate_max = HAD_MAX_RATE,155 .channels_min = HAD_MIN_CHANNEL,156 .channels_max = HAD_MAX_CHANNEL,157 .buffer_bytes_max = HAD_MAX_BUFFER,158 .period_bytes_min = HAD_MIN_PERIOD_BYTES,159 .period_bytes_max = HAD_MAX_PERIOD_BYTES,160 .periods_min = HAD_MIN_PERIODS,161 .periods_max = HAD_MAX_PERIODS,162 .fifo_size = HAD_FIFO_SIZE,163};164 165/* Get the active PCM substream;166 * Call had_substream_put() for unreferecing.167 * Don't call this inside had_spinlock, as it takes by itself168 */169static struct snd_pcm_substream *170had_substream_get(struct snd_intelhad *intelhaddata)171{172 struct snd_pcm_substream *substream;173 unsigned long flags;174 175 spin_lock_irqsave(&intelhaddata->had_spinlock, flags);176 substream = intelhaddata->stream_info.substream;177 if (substream)178 intelhaddata->stream_info.substream_refcount++;179 spin_unlock_irqrestore(&intelhaddata->had_spinlock, flags);180 return substream;181}182 183/* Unref the active PCM substream;184 * Don't call this inside had_spinlock, as it takes by itself185 */186static void had_substream_put(struct snd_intelhad *intelhaddata)187{188 unsigned long flags;189 190 spin_lock_irqsave(&intelhaddata->had_spinlock, flags);191 intelhaddata->stream_info.substream_refcount--;192 spin_unlock_irqrestore(&intelhaddata->had_spinlock, flags);193}194 195static u32 had_config_offset(int pipe)196{197 switch (pipe) {198 default:199 case 0:200 return AUDIO_HDMI_CONFIG_A;201 case 1:202 return AUDIO_HDMI_CONFIG_B;203 case 2:204 return AUDIO_HDMI_CONFIG_C;205 }206}207 208/* Register access functions */209static u32 had_read_register_raw(struct snd_intelhad_card *card_ctx,210 int pipe, u32 reg)211{212 return ioread32(card_ctx->mmio_start + had_config_offset(pipe) + reg);213}214 215static void had_write_register_raw(struct snd_intelhad_card *card_ctx,216 int pipe, u32 reg, u32 val)217{218 iowrite32(val, card_ctx->mmio_start + had_config_offset(pipe) + reg);219}220 221static void had_read_register(struct snd_intelhad *ctx, u32 reg, u32 *val)222{223 if (!ctx->connected)224 *val = 0;225 else226 *val = had_read_register_raw(ctx->card_ctx, ctx->pipe, reg);227}228 229static void had_write_register(struct snd_intelhad *ctx, u32 reg, u32 val)230{231 if (ctx->connected)232 had_write_register_raw(ctx->card_ctx, ctx->pipe, reg, val);233}234 235/*236 * enable / disable audio configuration237 *238 * The normal read/modify should not directly be used on VLV2 for239 * updating AUD_CONFIG register.240 * This is because:241 * Bit6 of AUD_CONFIG register is writeonly due to a silicon bug on VLV2242 * HDMI IP. As a result a read-modify of AUD_CONFIG register will always243 * clear bit6. AUD_CONFIG[6:4] represents the "channels" field of the244 * register. This field should be 1xy binary for configuration with 6 or245 * more channels. Read-modify of AUD_CONFIG (Eg. for enabling audio)246 * causes the "channels" field to be updated as 0xy binary resulting in247 * bad audio. The fix is to always write the AUD_CONFIG[6:4] with248 * appropriate value when doing read-modify of AUD_CONFIG register.249 */250static void had_enable_audio(struct snd_intelhad *intelhaddata,251 bool enable)252{253 /* update the cached value */254 intelhaddata->aud_config.regx.aud_en = enable;255 had_write_register(intelhaddata, AUD_CONFIG,256 intelhaddata->aud_config.regval);257}258 259/* forcibly ACKs to both BUFFER_DONE and BUFFER_UNDERRUN interrupts */260static void had_ack_irqs(struct snd_intelhad *ctx)261{262 u32 status_reg;263 264 if (!ctx->connected)265 return;266 had_read_register(ctx, AUD_HDMI_STATUS, &status_reg);267 status_reg |= HDMI_AUDIO_BUFFER_DONE | HDMI_AUDIO_UNDERRUN;268 had_write_register(ctx, AUD_HDMI_STATUS, status_reg);269 had_read_register(ctx, AUD_HDMI_STATUS, &status_reg);270}271 272/* Reset buffer pointers */273static void had_reset_audio(struct snd_intelhad *intelhaddata)274{275 had_write_register(intelhaddata, AUD_HDMI_STATUS,276 AUD_HDMI_STATUSG_MASK_FUNCRST);277 had_write_register(intelhaddata, AUD_HDMI_STATUS, 0);278}279 280/*281 * initialize audio channel status registers282 * This function is called in the prepare callback283 */284static int had_prog_status_reg(struct snd_pcm_substream *substream,285 struct snd_intelhad *intelhaddata)286{287 union aud_ch_status_0 ch_stat0 = {.regval = 0};288 union aud_ch_status_1 ch_stat1 = {.regval = 0};289 290 ch_stat0.regx.lpcm_id = (intelhaddata->aes_bits &291 IEC958_AES0_NONAUDIO) >> 1;292 ch_stat0.regx.clk_acc = (intelhaddata->aes_bits &293 IEC958_AES3_CON_CLOCK) >> 4;294 295 switch (substream->runtime->rate) {296 case AUD_SAMPLE_RATE_32:297 ch_stat0.regx.samp_freq = CH_STATUS_MAP_32KHZ;298 break;299 300 case AUD_SAMPLE_RATE_44_1:301 ch_stat0.regx.samp_freq = CH_STATUS_MAP_44KHZ;302 break;303 case AUD_SAMPLE_RATE_48:304 ch_stat0.regx.samp_freq = CH_STATUS_MAP_48KHZ;305 break;306 case AUD_SAMPLE_RATE_88_2:307 ch_stat0.regx.samp_freq = CH_STATUS_MAP_88KHZ;308 break;309 case AUD_SAMPLE_RATE_96:310 ch_stat0.regx.samp_freq = CH_STATUS_MAP_96KHZ;311 break;312 case AUD_SAMPLE_RATE_176_4:313 ch_stat0.regx.samp_freq = CH_STATUS_MAP_176KHZ;314 break;315 case AUD_SAMPLE_RATE_192:316 ch_stat0.regx.samp_freq = CH_STATUS_MAP_192KHZ;317 break;318 319 default:320 /* control should never come here */321 return -EINVAL;322 }323 324 had_write_register(intelhaddata,325 AUD_CH_STATUS_0, ch_stat0.regval);326 327 switch (substream->runtime->format) {328 case SNDRV_PCM_FORMAT_S16_LE:329 ch_stat1.regx.max_wrd_len = MAX_SMPL_WIDTH_20;330 ch_stat1.regx.wrd_len = SMPL_WIDTH_16BITS;331 break;332 case SNDRV_PCM_FORMAT_S24_LE:333 case SNDRV_PCM_FORMAT_S32_LE:334 ch_stat1.regx.max_wrd_len = MAX_SMPL_WIDTH_24;335 ch_stat1.regx.wrd_len = SMPL_WIDTH_24BITS;336 break;337 default:338 return -EINVAL;339 }340 341 had_write_register(intelhaddata,342 AUD_CH_STATUS_1, ch_stat1.regval);343 return 0;344}345 346/*347 * function to initialize audio348 * registers and buffer configuration registers349 * This function is called in the prepare callback350 */351static int had_init_audio_ctrl(struct snd_pcm_substream *substream,352 struct snd_intelhad *intelhaddata)353{354 union aud_cfg cfg_val = {.regval = 0};355 union aud_buf_config buf_cfg = {.regval = 0};356 u8 channels;357 358 had_prog_status_reg(substream, intelhaddata);359 360 buf_cfg.regx.audio_fifo_watermark = FIFO_THRESHOLD;361 buf_cfg.regx.dma_fifo_watermark = DMA_FIFO_THRESHOLD;362 buf_cfg.regx.aud_delay = 0;363 had_write_register(intelhaddata, AUD_BUF_CONFIG, buf_cfg.regval);364 365 channels = substream->runtime->channels;366 cfg_val.regx.num_ch = channels - 2;367 if (channels <= 2)368 cfg_val.regx.layout = LAYOUT0;369 else370 cfg_val.regx.layout = LAYOUT1;371 372 if (substream->runtime->format == SNDRV_PCM_FORMAT_S16_LE)373 cfg_val.regx.packet_mode = 1;374 375 if (substream->runtime->format == SNDRV_PCM_FORMAT_S32_LE)376 cfg_val.regx.left_align = 1;377 378 cfg_val.regx.val_bit = 1;379 380 /* fix up the DP bits */381 if (intelhaddata->dp_output) {382 cfg_val.regx.dp_modei = 1;383 cfg_val.regx.set = 1;384 }385 386 had_write_register(intelhaddata, AUD_CONFIG, cfg_val.regval);387 intelhaddata->aud_config = cfg_val;388 return 0;389}390 391/*392 * Compute derived values in channel_allocations[].393 */394static void init_channel_allocations(void)395{396 int i, j;397 struct cea_channel_speaker_allocation *p;398 399 for (i = 0; i < ARRAY_SIZE(channel_allocations); i++) {400 p = channel_allocations + i;401 p->channels = 0;402 p->spk_mask = 0;403 for (j = 0; j < ARRAY_SIZE(p->speakers); j++)404 if (p->speakers[j]) {405 p->channels++;406 p->spk_mask |= p->speakers[j];407 }408 }409}410 411/*412 * The transformation takes two steps:413 *414 * eld->spk_alloc => (eld_speaker_allocation_bits[]) => spk_mask415 * spk_mask => (channel_allocations[]) => ai->CA416 *417 * TODO: it could select the wrong CA from multiple candidates.418 */419static int had_channel_allocation(struct snd_intelhad *intelhaddata,420 int channels)421{422 int i;423 int ca = 0;424 int spk_mask = 0;425 426 /*427 * CA defaults to 0 for basic stereo audio428 */429 if (channels <= 2)430 return 0;431 432 /*433 * expand ELD's speaker allocation mask434 *435 * ELD tells the speaker mask in a compact(paired) form,436 * expand ELD's notions to match the ones used by Audio InfoFrame.437 */438 439 for (i = 0; i < ARRAY_SIZE(eld_speaker_allocation_bits); i++) {440 if (intelhaddata->eld[DRM_ELD_SPEAKER] & (1 << i))441 spk_mask |= eld_speaker_allocation_bits[i];442 }443 444 /* search for the first working match in the CA table */445 for (i = 0; i < ARRAY_SIZE(channel_allocations); i++) {446 if (channels == channel_allocations[i].channels &&447 (spk_mask & channel_allocations[i].spk_mask) ==448 channel_allocations[i].spk_mask) {449 ca = channel_allocations[i].ca_index;450 break;451 }452 }453 454 dev_dbg(intelhaddata->dev, "select CA 0x%x for %d\n", ca, channels);455 456 return ca;457}458 459/* from speaker bit mask to ALSA API channel position */460static int spk_to_chmap(int spk)461{462 const struct channel_map_table *t = map_tables;463 464 for (; t->map; t++) {465 if (t->spk_mask == spk)466 return t->map;467 }468 return 0;469}470 471static void had_build_channel_allocation_map(struct snd_intelhad *intelhaddata)472{473 int i, c;474 int spk_mask = 0;475 struct snd_pcm_chmap_elem *chmap;476 u8 eld_high, eld_high_mask = 0xF0;477 u8 high_msb;478 479 kfree(intelhaddata->chmap->chmap);480 intelhaddata->chmap->chmap = NULL;481 482 chmap = kzalloc(sizeof(*chmap), GFP_KERNEL);483 if (!chmap)484 return;485 486 dev_dbg(intelhaddata->dev, "eld speaker = %x\n",487 intelhaddata->eld[DRM_ELD_SPEAKER]);488 489 /* WA: Fix the max channel supported to 8 */490 491 /*492 * Sink may support more than 8 channels, if eld_high has more than493 * one bit set. SOC supports max 8 channels.494 * Refer eld_speaker_allocation_bits, for sink speaker allocation495 */496 497 /* if 0x2F < eld < 0x4F fall back to 0x2f, else fall back to 0x4F */498 eld_high = intelhaddata->eld[DRM_ELD_SPEAKER] & eld_high_mask;499 if ((eld_high & (eld_high-1)) && (eld_high > 0x1F)) {500 /* eld_high & (eld_high-1): if more than 1 bit set */501 /* 0x1F: 7 channels */502 for (i = 1; i < 4; i++) {503 high_msb = eld_high & (0x80 >> i);504 if (high_msb) {505 intelhaddata->eld[DRM_ELD_SPEAKER] &=506 high_msb | 0xF;507 break;508 }509 }510 }511 512 for (i = 0; i < ARRAY_SIZE(eld_speaker_allocation_bits); i++) {513 if (intelhaddata->eld[DRM_ELD_SPEAKER] & (1 << i))514 spk_mask |= eld_speaker_allocation_bits[i];515 }516 517 for (i = 0; i < ARRAY_SIZE(channel_allocations); i++) {518 if (spk_mask == channel_allocations[i].spk_mask) {519 for (c = 0; c < channel_allocations[i].channels; c++) {520 chmap->map[c] = spk_to_chmap(521 channel_allocations[i].speakers[522 (MAX_SPEAKERS - 1) - c]);523 }524 chmap->channels = channel_allocations[i].channels;525 intelhaddata->chmap->chmap = chmap;526 break;527 }528 }529 if (i >= ARRAY_SIZE(channel_allocations))530 kfree(chmap);531}532 533/*534 * ALSA API channel-map control callbacks535 */536static int had_chmap_ctl_info(struct snd_kcontrol *kcontrol,537 struct snd_ctl_elem_info *uinfo)538{539 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER;540 uinfo->count = HAD_MAX_CHANNEL;541 uinfo->value.integer.min = 0;542 uinfo->value.integer.max = SNDRV_CHMAP_LAST;543 return 0;544}545 546static int had_chmap_ctl_get(struct snd_kcontrol *kcontrol,547 struct snd_ctl_elem_value *ucontrol)548{549 struct snd_pcm_chmap *info = snd_kcontrol_chip(kcontrol);550 struct snd_intelhad *intelhaddata = info->private_data;551 int i;552 const struct snd_pcm_chmap_elem *chmap;553 554 memset(ucontrol->value.integer.value, 0,555 sizeof(long) * HAD_MAX_CHANNEL);556 mutex_lock(&intelhaddata->mutex);557 if (!intelhaddata->chmap->chmap) {558 mutex_unlock(&intelhaddata->mutex);559 return 0;560 }561 562 chmap = intelhaddata->chmap->chmap;563 for (i = 0; i < chmap->channels; i++)564 ucontrol->value.integer.value[i] = chmap->map[i];565 mutex_unlock(&intelhaddata->mutex);566 567 return 0;568}569 570static int had_register_chmap_ctls(struct snd_intelhad *intelhaddata,571 struct snd_pcm *pcm)572{573 int err;574 575 err = snd_pcm_add_chmap_ctls(pcm, SNDRV_PCM_STREAM_PLAYBACK,576 NULL, 0, (unsigned long)intelhaddata,577 &intelhaddata->chmap);578 if (err < 0)579 return err;580 581 intelhaddata->chmap->private_data = intelhaddata;582 intelhaddata->chmap->kctl->info = had_chmap_ctl_info;583 intelhaddata->chmap->kctl->get = had_chmap_ctl_get;584 intelhaddata->chmap->chmap = NULL;585 return 0;586}587 588/*589 * Initialize Data Island Packets registers590 * This function is called in the prepare callback591 */592static void had_prog_dip(struct snd_pcm_substream *substream,593 struct snd_intelhad *intelhaddata)594{595 int i;596 union aud_ctrl_st ctrl_state = {.regval = 0};597 union aud_info_frame2 frame2 = {.regval = 0};598 union aud_info_frame3 frame3 = {.regval = 0};599 u8 checksum = 0;600 u32 info_frame;601 int channels;602 int ca;603 604 channels = substream->runtime->channels;605 606 had_write_register(intelhaddata, AUD_CNTL_ST, ctrl_state.regval);607 608 ca = had_channel_allocation(intelhaddata, channels);609 if (intelhaddata->dp_output) {610 info_frame = DP_INFO_FRAME_WORD1;611 frame2.regval = (substream->runtime->channels - 1) | (ca << 24);612 } else {613 info_frame = HDMI_INFO_FRAME_WORD1;614 frame2.regx.chnl_cnt = substream->runtime->channels - 1;615 frame3.regx.chnl_alloc = ca;616 617 /* Calculte the byte wide checksum for all valid DIP words */618 for (i = 0; i < BYTES_PER_WORD; i++)619 checksum += (info_frame >> (i * 8)) & 0xff;620 for (i = 0; i < BYTES_PER_WORD; i++)621 checksum += (frame2.regval >> (i * 8)) & 0xff;622 for (i = 0; i < BYTES_PER_WORD; i++)623 checksum += (frame3.regval >> (i * 8)) & 0xff;624 625 frame2.regx.chksum = -(checksum);626 }627 628 had_write_register(intelhaddata, AUD_HDMIW_INFOFR, info_frame);629 had_write_register(intelhaddata, AUD_HDMIW_INFOFR, frame2.regval);630 had_write_register(intelhaddata, AUD_HDMIW_INFOFR, frame3.regval);631 632 /* program remaining DIP words with zero */633 for (i = 0; i < HAD_MAX_DIP_WORDS-VALID_DIP_WORDS; i++)634 had_write_register(intelhaddata, AUD_HDMIW_INFOFR, 0x0);635 636 ctrl_state.regx.dip_freq = 1;637 ctrl_state.regx.dip_en_sta = 1;638 had_write_register(intelhaddata, AUD_CNTL_ST, ctrl_state.regval);639}640 641static int had_calculate_maud_value(u32 aud_samp_freq, u32 link_rate)642{643 u32 maud_val;644 645 /* Select maud according to DP 1.2 spec */646 if (link_rate == DP_2_7_GHZ) {647 switch (aud_samp_freq) {648 case AUD_SAMPLE_RATE_32:649 maud_val = AUD_SAMPLE_RATE_32_DP_2_7_MAUD_VAL;650 break;651 652 case AUD_SAMPLE_RATE_44_1:653 maud_val = AUD_SAMPLE_RATE_44_1_DP_2_7_MAUD_VAL;654 break;655 656 case AUD_SAMPLE_RATE_48:657 maud_val = AUD_SAMPLE_RATE_48_DP_2_7_MAUD_VAL;658 break;659 660 case AUD_SAMPLE_RATE_88_2:661 maud_val = AUD_SAMPLE_RATE_88_2_DP_2_7_MAUD_VAL;662 break;663 664 case AUD_SAMPLE_RATE_96:665 maud_val = AUD_SAMPLE_RATE_96_DP_2_7_MAUD_VAL;666 break;667 668 case AUD_SAMPLE_RATE_176_4:669 maud_val = AUD_SAMPLE_RATE_176_4_DP_2_7_MAUD_VAL;670 break;671 672 case HAD_MAX_RATE:673 maud_val = HAD_MAX_RATE_DP_2_7_MAUD_VAL;674 break;675 676 default:677 maud_val = -EINVAL;678 break;679 }680 } else if (link_rate == DP_1_62_GHZ) {681 switch (aud_samp_freq) {682 case AUD_SAMPLE_RATE_32:683 maud_val = AUD_SAMPLE_RATE_32_DP_1_62_MAUD_VAL;684 break;685 686 case AUD_SAMPLE_RATE_44_1:687 maud_val = AUD_SAMPLE_RATE_44_1_DP_1_62_MAUD_VAL;688 break;689 690 case AUD_SAMPLE_RATE_48:691 maud_val = AUD_SAMPLE_RATE_48_DP_1_62_MAUD_VAL;692 break;693 694 case AUD_SAMPLE_RATE_88_2:695 maud_val = AUD_SAMPLE_RATE_88_2_DP_1_62_MAUD_VAL;696 break;697 698 case AUD_SAMPLE_RATE_96:699 maud_val = AUD_SAMPLE_RATE_96_DP_1_62_MAUD_VAL;700 break;701 702 case AUD_SAMPLE_RATE_176_4:703 maud_val = AUD_SAMPLE_RATE_176_4_DP_1_62_MAUD_VAL;704 break;705 706 case HAD_MAX_RATE:707 maud_val = HAD_MAX_RATE_DP_1_62_MAUD_VAL;708 break;709 710 default:711 maud_val = -EINVAL;712 break;713 }714 } else715 maud_val = -EINVAL;716 717 return maud_val;718}719 720/*721 * Program HDMI audio CTS value722 *723 * @aud_samp_freq: sampling frequency of audio data724 * @tmds: sampling frequency of the display data725 * @link_rate: DP link rate726 * @n_param: N value, depends on aud_samp_freq727 * @intelhaddata: substream private data728 *729 * Program CTS register based on the audio and display sampling frequency730 */731static void had_prog_cts(u32 aud_samp_freq, u32 tmds, u32 link_rate,732 u32 n_param, struct snd_intelhad *intelhaddata)733{734 u32 cts_val;735 u64 dividend, divisor;736 737 if (intelhaddata->dp_output) {738 /* Substitute cts_val with Maud according to DP 1.2 spec*/739 cts_val = had_calculate_maud_value(aud_samp_freq, link_rate);740 } else {741 /* Calculate CTS according to HDMI 1.3a spec*/742 dividend = (u64)tmds * n_param*1000;743 divisor = 128 * aud_samp_freq;744 cts_val = div64_u64(dividend, divisor);745 }746 dev_dbg(intelhaddata->dev, "TMDS value=%d, N value=%d, CTS Value=%d\n",747 tmds, n_param, cts_val);748 had_write_register(intelhaddata, AUD_HDMI_CTS, (BIT(24) | cts_val));749}750 751static int had_calculate_n_value(u32 aud_samp_freq)752{753 int n_val;754 755 /* Select N according to HDMI 1.3a spec*/756 switch (aud_samp_freq) {757 case AUD_SAMPLE_RATE_32:758 n_val = 4096;759 break;760 761 case AUD_SAMPLE_RATE_44_1:762 n_val = 6272;763 break;764 765 case AUD_SAMPLE_RATE_48:766 n_val = 6144;767 break;768 769 case AUD_SAMPLE_RATE_88_2:770 n_val = 12544;771 break;772 773 case AUD_SAMPLE_RATE_96:774 n_val = 12288;775 break;776 777 case AUD_SAMPLE_RATE_176_4:778 n_val = 25088;779 break;780 781 case HAD_MAX_RATE:782 n_val = 24576;783 break;784 785 default:786 n_val = -EINVAL;787 break;788 }789 return n_val;790}791 792/*793 * Program HDMI audio N value794 *795 * @aud_samp_freq: sampling frequency of audio data796 * @n_param: N value, depends on aud_samp_freq797 * @intelhaddata: substream private data798 *799 * This function is called in the prepare callback.800 * It programs based on the audio and display sampling frequency801 */802static int had_prog_n(u32 aud_samp_freq, u32 *n_param,803 struct snd_intelhad *intelhaddata)804{805 int n_val;806 807 if (intelhaddata->dp_output) {808 /*809 * According to DP specs, Maud and Naud values hold810 * a relationship, which is stated as:811 * Maud/Naud = 512 * fs / f_LS_Clk812 * where, fs is the sampling frequency of the audio stream813 * and Naud is 32768 for Async clock.814 */815 816 n_val = DP_NAUD_VAL;817 } else818 n_val = had_calculate_n_value(aud_samp_freq);819 820 if (n_val < 0)821 return n_val;822 823 had_write_register(intelhaddata, AUD_N_ENABLE, (BIT(24) | n_val));824 *n_param = n_val;825 return 0;826}827 828/*829 * PCM ring buffer handling830 *831 * The hardware provides a ring buffer with the fixed 4 buffer descriptors832 * (BDs). The driver maps these 4 BDs onto the PCM ring buffer. The mapping833 * moves at each period elapsed. The below illustrates how it works:834 *835 * At time=0836 * PCM | 0 | 1 | 2 | 3 | 4 | 5 | .... |n-1|837 * BD | 0 | 1 | 2 | 3 |838 *839 * At time=1 (period elapsed)840 * PCM | 0 | 1 | 2 | 3 | 4 | 5 | .... |n-1|841 * BD | 1 | 2 | 3 | 0 |842 *843 * At time=2 (second period elapsed)844 * PCM | 0 | 1 | 2 | 3 | 4 | 5 | .... |n-1|845 * BD | 2 | 3 | 0 | 1 |846 *847 * The bd_head field points to the index of the BD to be read. It's also the848 * position to be filled at next. The pcm_head and the pcm_filled fields849 * point to the indices of the current position and of the next position to850 * be filled, respectively. For PCM buffer there are both _head and _filled851 * because they may be difference when nperiods > 4. For example, in the852 * example above at t=1, bd_head=1 and pcm_head=1 while pcm_filled=5:853 *854 * pcm_head (=1) --v v-- pcm_filled (=5)855 * PCM | 0 | 1 | 2 | 3 | 4 | 5 | .... |n-1|856 * BD | 1 | 2 | 3 | 0 |857 * bd_head (=1) --^ ^-- next to fill (= bd_head)858 *859 * For nperiods < 4, the remaining BDs out of 4 are marked as invalid, so that860 * the hardware skips those BDs in the loop.861 *862 * An exceptional setup is the case with nperiods=1. Since we have to update863 * BDs after finishing one BD processing, we'd need at least two BDs, where864 * both BDs point to the same content, the same address, the same size of the865 * whole PCM buffer.866 */867 868#define AUD_BUF_ADDR(x) (AUD_BUF_A_ADDR + (x) * HAD_REG_WIDTH)869#define AUD_BUF_LEN(x) (AUD_BUF_A_LENGTH + (x) * HAD_REG_WIDTH)870 871/* Set up a buffer descriptor at the "filled" position */872static void had_prog_bd(struct snd_pcm_substream *substream,873 struct snd_intelhad *intelhaddata)874{875 int idx = intelhaddata->bd_head;876 int ofs = intelhaddata->pcmbuf_filled * intelhaddata->period_bytes;877 u32 addr = substream->runtime->dma_addr + ofs;878 879 addr |= AUD_BUF_VALID;880 if (!substream->runtime->no_period_wakeup)881 addr |= AUD_BUF_INTR_EN;882 had_write_register(intelhaddata, AUD_BUF_ADDR(idx), addr);883 had_write_register(intelhaddata, AUD_BUF_LEN(idx),884 intelhaddata->period_bytes);885 886 /* advance the indices to the next */887 intelhaddata->bd_head++;888 intelhaddata->bd_head %= intelhaddata->num_bds;889 intelhaddata->pcmbuf_filled++;890 intelhaddata->pcmbuf_filled %= substream->runtime->periods;891}892 893/* invalidate a buffer descriptor with the given index */894static void had_invalidate_bd(struct snd_intelhad *intelhaddata,895 int idx)896{897 had_write_register(intelhaddata, AUD_BUF_ADDR(idx), 0);898 had_write_register(intelhaddata, AUD_BUF_LEN(idx), 0);899}900 901/* Initial programming of ring buffer */902static void had_init_ringbuf(struct snd_pcm_substream *substream,903 struct snd_intelhad *intelhaddata)904{905 struct snd_pcm_runtime *runtime = substream->runtime;906 int i, num_periods;907 908 num_periods = runtime->periods;909 intelhaddata->num_bds = min(num_periods, HAD_NUM_OF_RING_BUFS);910 /* set the minimum 2 BDs for num_periods=1 */911 intelhaddata->num_bds = max(intelhaddata->num_bds, 2U);912 intelhaddata->period_bytes =913 frames_to_bytes(runtime, runtime->period_size);914 WARN_ON(intelhaddata->period_bytes & 0x3f);915 916 intelhaddata->bd_head = 0;917 intelhaddata->pcmbuf_head = 0;918 intelhaddata->pcmbuf_filled = 0;919 920 for (i = 0; i < HAD_NUM_OF_RING_BUFS; i++) {921 if (i < intelhaddata->num_bds)922 had_prog_bd(substream, intelhaddata);923 else /* invalidate the rest */924 had_invalidate_bd(intelhaddata, i);925 }926 927 intelhaddata->bd_head = 0; /* reset at head again before starting */928}929 930/* process a bd, advance to the next */931static void had_advance_ringbuf(struct snd_pcm_substream *substream,932 struct snd_intelhad *intelhaddata)933{934 int num_periods = substream->runtime->periods;935 936 /* reprogram the next buffer */937 had_prog_bd(substream, intelhaddata);938 939 /* proceed to next */940 intelhaddata->pcmbuf_head++;941 intelhaddata->pcmbuf_head %= num_periods;942}943 944/* process the current BD(s);945 * returns the current PCM buffer byte position, or -EPIPE for underrun.946 */947static int had_process_ringbuf(struct snd_pcm_substream *substream,948 struct snd_intelhad *intelhaddata)949{950 int len, processed;951 unsigned long flags;952 953 processed = 0;954 spin_lock_irqsave(&intelhaddata->had_spinlock, flags);955 for (;;) {956 /* get the remaining bytes on the buffer */957 had_read_register(intelhaddata,958 AUD_BUF_LEN(intelhaddata->bd_head),959 &len);960 if (len < 0 || len > intelhaddata->period_bytes) {961 dev_dbg(intelhaddata->dev, "Invalid buf length %d\n",962 len);963 len = -EPIPE;964 goto out;965 }966 967 if (len > 0) /* OK, this is the current buffer */968 break;969 970 /* len=0 => already empty, check the next buffer */971 if (++processed >= intelhaddata->num_bds) {972 len = -EPIPE; /* all empty? - report underrun */973 goto out;974 }975 had_advance_ringbuf(substream, intelhaddata);976 }977 978 len = intelhaddata->period_bytes - len;979 len += intelhaddata->period_bytes * intelhaddata->pcmbuf_head;980 out:981 spin_unlock_irqrestore(&intelhaddata->had_spinlock, flags);982 return len;983}984 985/* called from irq handler */986static void had_process_buffer_done(struct snd_intelhad *intelhaddata)987{988 struct snd_pcm_substream *substream;989 990 substream = had_substream_get(intelhaddata);991 if (!substream)992 return; /* no stream? - bail out */993 994 if (!intelhaddata->connected) {995 snd_pcm_stop_xrun(substream);996 goto out; /* disconnected? - bail out */997 }998 999 /* process or stop the stream */1000 if (had_process_ringbuf(substream, intelhaddata) < 0)1001 snd_pcm_stop_xrun(substream);1002 else1003 snd_pcm_period_elapsed(substream);1004 1005 out:1006 had_substream_put(intelhaddata);1007}1008 1009/*1010 * The interrupt status 'sticky' bits might not be cleared by1011 * setting '1' to that bit once...1012 */1013static void wait_clear_underrun_bit(struct snd_intelhad *intelhaddata)1014{1015 int i;1016 u32 val;1017 1018 for (i = 0; i < 100; i++) {1019 /* clear bit30, 31 AUD_HDMI_STATUS */1020 had_read_register(intelhaddata, AUD_HDMI_STATUS, &val);1021 if (!(val & AUD_HDMI_STATUS_MASK_UNDERRUN))1022 return;1023 udelay(100);1024 cond_resched();1025 had_write_register(intelhaddata, AUD_HDMI_STATUS, val);1026 }1027 dev_err(intelhaddata->dev, "Unable to clear UNDERRUN bits\n");1028}1029 1030/* Perform some reset procedure after stopping the stream;1031 * this is called from prepare or hw_free callbacks once after trigger STOP1032 * or underrun has been processed in order to settle down the h/w state.1033 */1034static int had_pcm_sync_stop(struct snd_pcm_substream *substream)1035{1036 struct snd_intelhad *intelhaddata = snd_pcm_substream_chip(substream);1037 1038 if (!intelhaddata->connected)1039 return 0;1040 1041 /* Reset buffer pointers */1042 had_reset_audio(intelhaddata);1043 wait_clear_underrun_bit(intelhaddata);1044 return 0;1045}1046 1047/* called from irq handler */1048static void had_process_buffer_underrun(struct snd_intelhad *intelhaddata)1049{1050 struct snd_pcm_substream *substream;1051 1052 /* Report UNDERRUN error to above layers */1053 substream = had_substream_get(intelhaddata);1054 if (substream) {1055 snd_pcm_stop_xrun(substream);1056 had_substream_put(intelhaddata);1057 }1058}1059 1060/*1061 * ALSA PCM open callback1062 */1063static int had_pcm_open(struct snd_pcm_substream *substream)1064{1065 struct snd_intelhad *intelhaddata;1066 struct snd_pcm_runtime *runtime;1067 int retval;1068 1069 intelhaddata = snd_pcm_substream_chip(substream);1070 runtime = substream->runtime;1071 1072 retval = pm_runtime_resume_and_get(intelhaddata->dev);1073 if (retval < 0)1074 return retval;1075 1076 /* set the runtime hw parameter with local snd_pcm_hardware struct */1077 runtime->hw = had_pcm_hardware;1078 1079 retval = snd_pcm_hw_constraint_integer(runtime,1080 SNDRV_PCM_HW_PARAM_PERIODS);1081 if (retval < 0)1082 goto error;1083 1084 /* Make sure, that the period size is always aligned1085 * 64byte boundary1086 */1087 retval = snd_pcm_hw_constraint_step(substream->runtime, 0,1088 SNDRV_PCM_HW_PARAM_PERIOD_BYTES, 64);1089 if (retval < 0)1090 goto error;1091 1092 retval = snd_pcm_hw_constraint_msbits(runtime, 0, 32, 24);1093 if (retval < 0)1094 goto error;1095 1096 /* expose PCM substream */1097 spin_lock_irq(&intelhaddata->had_spinlock);1098 intelhaddata->stream_info.substream = substream;1099 intelhaddata->stream_info.substream_refcount++;1100 spin_unlock_irq(&intelhaddata->had_spinlock);1101 1102 return retval;1103 error:1104 pm_runtime_mark_last_busy(intelhaddata->dev);1105 pm_runtime_put_autosuspend(intelhaddata->dev);1106 return retval;1107}1108 1109/*1110 * ALSA PCM close callback1111 */1112static int had_pcm_close(struct snd_pcm_substream *substream)1113{1114 struct snd_intelhad *intelhaddata;1115 1116 intelhaddata = snd_pcm_substream_chip(substream);1117 1118 /* unreference and sync with the pending PCM accesses */1119 spin_lock_irq(&intelhaddata->had_spinlock);1120 intelhaddata->stream_info.substream = NULL;1121 intelhaddata->stream_info.substream_refcount--;1122 while (intelhaddata->stream_info.substream_refcount > 0) {1123 spin_unlock_irq(&intelhaddata->had_spinlock);1124 cpu_relax();1125 spin_lock_irq(&intelhaddata->had_spinlock);1126 }1127 spin_unlock_irq(&intelhaddata->had_spinlock);1128 1129 pm_runtime_mark_last_busy(intelhaddata->dev);1130 pm_runtime_put_autosuspend(intelhaddata->dev);1131 return 0;1132}1133 1134/*1135 * ALSA PCM hw_params callback1136 */1137static int had_pcm_hw_params(struct snd_pcm_substream *substream,1138 struct snd_pcm_hw_params *hw_params)1139{1140 struct snd_intelhad *intelhaddata;1141 int buf_size;1142 1143 intelhaddata = snd_pcm_substream_chip(substream);1144 buf_size = params_buffer_bytes(hw_params);1145 dev_dbg(intelhaddata->dev, "%s:allocated memory = %d\n",1146 __func__, buf_size);1147 return 0;1148}1149 1150/*1151 * ALSA PCM trigger callback1152 */1153static int had_pcm_trigger(struct snd_pcm_substream *substream, int cmd)1154{1155 int retval = 0;1156 struct snd_intelhad *intelhaddata;1157 1158 intelhaddata = snd_pcm_substream_chip(substream);1159 1160 spin_lock(&intelhaddata->had_spinlock);1161 switch (cmd) {1162 case SNDRV_PCM_TRIGGER_START:1163 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:1164 case SNDRV_PCM_TRIGGER_RESUME:1165 /* Enable Audio */1166 had_ack_irqs(intelhaddata); /* FIXME: do we need this? */1167 had_enable_audio(intelhaddata, true);1168 break;1169 1170 case SNDRV_PCM_TRIGGER_STOP:1171 case SNDRV_PCM_TRIGGER_PAUSE_PUSH:1172 /* Disable Audio */1173 had_enable_audio(intelhaddata, false);1174 break;1175 1176 default:1177 retval = -EINVAL;1178 }1179 spin_unlock(&intelhaddata->had_spinlock);1180 return retval;1181}1182 1183/*1184 * ALSA PCM prepare callback1185 */1186static int had_pcm_prepare(struct snd_pcm_substream *substream)1187{1188 int retval;1189 u32 disp_samp_freq, n_param;1190 u32 link_rate = 0;1191 struct snd_intelhad *intelhaddata;1192 struct snd_pcm_runtime *runtime;1193 1194 intelhaddata = snd_pcm_substream_chip(substream);1195 runtime = substream->runtime;1196 1197 dev_dbg(intelhaddata->dev, "period_size=%d\n",1198 (int)frames_to_bytes(runtime, runtime->period_size));1199 dev_dbg(intelhaddata->dev, "periods=%d\n", runtime->periods);1200 dev_dbg(intelhaddata->dev, "buffer_size=%d\n",1201 (int)snd_pcm_lib_buffer_bytes(substream));1202 dev_dbg(intelhaddata->dev, "rate=%d\n", runtime->rate);1203 dev_dbg(intelhaddata->dev, "channels=%d\n", runtime->channels);1204 1205 /* Get N value in KHz */1206 disp_samp_freq = intelhaddata->tmds_clock_speed;1207 1208 retval = had_prog_n(substream->runtime->rate, &n_param, intelhaddata);1209 if (retval) {1210 dev_err(intelhaddata->dev,1211 "programming N value failed %#x\n", retval);1212 goto prep_end;1213 }1214 1215 if (intelhaddata->dp_output)1216 link_rate = intelhaddata->link_rate;1217 1218 had_prog_cts(substream->runtime->rate, disp_samp_freq, link_rate,1219 n_param, intelhaddata);1220 1221 had_prog_dip(substream, intelhaddata);1222 1223 retval = had_init_audio_ctrl(substream, intelhaddata);1224 1225 /* Prog buffer address */1226 had_init_ringbuf(substream, intelhaddata);1227 1228 /*1229 * Program channel mapping in following order:1230 * FL, FR, C, LFE, RL, RR1231 */1232 1233 had_write_register(intelhaddata, AUD_BUF_CH_SWAP, SWAP_LFE_CENTER);1234 1235prep_end:1236 return retval;1237}1238 1239/*1240 * ALSA PCM pointer callback1241 */1242static snd_pcm_uframes_t had_pcm_pointer(struct snd_pcm_substream *substream)1243{1244 struct snd_intelhad *intelhaddata;1245 int len;1246 1247 intelhaddata = snd_pcm_substream_chip(substream);1248 1249 if (!intelhaddata->connected)1250 return SNDRV_PCM_POS_XRUN;1251 1252 len = had_process_ringbuf(substream, intelhaddata);1253 if (len < 0)1254 return SNDRV_PCM_POS_XRUN;1255 len = bytes_to_frames(substream->runtime, len);1256 /* wrapping may happen when periods=1 */1257 len %= substream->runtime->buffer_size;1258 return len;1259}1260 1261/*1262 * ALSA PCM ops1263 */1264static const struct snd_pcm_ops had_pcm_ops = {1265 .open = had_pcm_open,1266 .close = had_pcm_close,1267 .hw_params = had_pcm_hw_params,1268 .prepare = had_pcm_prepare,1269 .trigger = had_pcm_trigger,1270 .sync_stop = had_pcm_sync_stop,1271 .pointer = had_pcm_pointer,1272};1273 1274/* process mode change of the running stream; called in mutex */1275static int had_process_mode_change(struct snd_intelhad *intelhaddata)1276{1277 struct snd_pcm_substream *substream;1278 int retval = 0;1279 u32 disp_samp_freq, n_param;1280 u32 link_rate = 0;1281 1282 substream = had_substream_get(intelhaddata);1283 if (!substream)1284 return 0;1285 1286 /* Disable Audio */1287 had_enable_audio(intelhaddata, false);1288 1289 /* Update CTS value */1290 disp_samp_freq = intelhaddata->tmds_clock_speed;1291 1292 retval = had_prog_n(substream->runtime->rate, &n_param, intelhaddata);1293 if (retval) {1294 dev_err(intelhaddata->dev,1295 "programming N value failed %#x\n", retval);1296 goto out;1297 }1298 1299 if (intelhaddata->dp_output)1300 link_rate = intelhaddata->link_rate;1301 1302 had_prog_cts(substream->runtime->rate, disp_samp_freq, link_rate,1303 n_param, intelhaddata);1304 1305 /* Enable Audio */1306 had_enable_audio(intelhaddata, true);1307 1308out:1309 had_substream_put(intelhaddata);1310 return retval;1311}1312 1313/* process hot plug, called from wq with mutex locked */1314static void had_process_hot_plug(struct snd_intelhad *intelhaddata)1315{1316 struct snd_pcm_substream *substream;1317 1318 spin_lock_irq(&intelhaddata->had_spinlock);1319 if (intelhaddata->connected) {1320 dev_dbg(intelhaddata->dev, "Device already connected\n");1321 spin_unlock_irq(&intelhaddata->had_spinlock);1322 return;1323 }1324 1325 /* Disable Audio */1326 had_enable_audio(intelhaddata, false);1327 1328 intelhaddata->connected = true;1329 dev_dbg(intelhaddata->dev,1330 "%s @ %d:DEBUG PLUG/UNPLUG : HAD_DRV_CONNECTED\n",1331 __func__, __LINE__);1332 spin_unlock_irq(&intelhaddata->had_spinlock);1333 1334 had_build_channel_allocation_map(intelhaddata);1335 1336 /* Report to above ALSA layer */1337 substream = had_substream_get(intelhaddata);1338 if (substream) {1339 snd_pcm_stop_xrun(substream);1340 had_substream_put(intelhaddata);1341 }1342 1343 snd_jack_report(intelhaddata->jack, SND_JACK_AVOUT);1344}1345 1346/* process hot unplug, called from wq with mutex locked */1347static void had_process_hot_unplug(struct snd_intelhad *intelhaddata)1348{1349 struct snd_pcm_substream *substream;1350 1351 spin_lock_irq(&intelhaddata->had_spinlock);1352 if (!intelhaddata->connected) {1353 dev_dbg(intelhaddata->dev, "Device already disconnected\n");1354 spin_unlock_irq(&intelhaddata->had_spinlock);1355 return;1356 1357 }1358 1359 /* Disable Audio */1360 had_enable_audio(intelhaddata, false);1361 1362 intelhaddata->connected = false;1363 dev_dbg(intelhaddata->dev,1364 "%s @ %d:DEBUG PLUG/UNPLUG : HAD_DRV_DISCONNECTED\n",1365 __func__, __LINE__);1366 spin_unlock_irq(&intelhaddata->had_spinlock);1367 1368 kfree(intelhaddata->chmap->chmap);1369 intelhaddata->chmap->chmap = NULL;1370 1371 /* Report to above ALSA layer */1372 substream = had_substream_get(intelhaddata);1373 if (substream) {1374 snd_pcm_stop_xrun(substream);1375 had_substream_put(intelhaddata);1376 }1377 1378 snd_jack_report(intelhaddata->jack, 0);1379}1380 1381/*1382 * ALSA iec958 and ELD controls1383 */1384 1385static int had_iec958_info(struct snd_kcontrol *kcontrol,1386 struct snd_ctl_elem_info *uinfo)1387{1388 uinfo->type = SNDRV_CTL_ELEM_TYPE_IEC958;1389 uinfo->count = 1;1390 return 0;1391}1392 1393static int had_iec958_get(struct snd_kcontrol *kcontrol,1394 struct snd_ctl_elem_value *ucontrol)1395{1396 struct snd_intelhad *intelhaddata = snd_kcontrol_chip(kcontrol);1397 1398 mutex_lock(&intelhaddata->mutex);1399 ucontrol->value.iec958.status[0] = (intelhaddata->aes_bits >> 0) & 0xff;1400 ucontrol->value.iec958.status[1] = (intelhaddata->aes_bits >> 8) & 0xff;1401 ucontrol->value.iec958.status[2] =1402 (intelhaddata->aes_bits >> 16) & 0xff;1403 ucontrol->value.iec958.status[3] =1404 (intelhaddata->aes_bits >> 24) & 0xff;1405 mutex_unlock(&intelhaddata->mutex);1406 return 0;1407}1408 1409static int had_iec958_mask_get(struct snd_kcontrol *kcontrol,1410 struct snd_ctl_elem_value *ucontrol)1411{1412 ucontrol->value.iec958.status[0] = 0xff;1413 ucontrol->value.iec958.status[1] = 0xff;1414 ucontrol->value.iec958.status[2] = 0xff;1415 ucontrol->value.iec958.status[3] = 0xff;1416 return 0;1417}1418 1419static int had_iec958_put(struct snd_kcontrol *kcontrol,1420 struct snd_ctl_elem_value *ucontrol)1421{1422 unsigned int val;1423 struct snd_intelhad *intelhaddata = snd_kcontrol_chip(kcontrol);1424 int changed = 0;1425 1426 val = (ucontrol->value.iec958.status[0] << 0) |1427 (ucontrol->value.iec958.status[1] << 8) |1428 (ucontrol->value.iec958.status[2] << 16) |1429 (ucontrol->value.iec958.status[3] << 24);1430 mutex_lock(&intelhaddata->mutex);1431 if (intelhaddata->aes_bits != val) {1432 intelhaddata->aes_bits = val;1433 changed = 1;1434 }1435 mutex_unlock(&intelhaddata->mutex);1436 return changed;1437}1438 1439static int had_ctl_eld_info(struct snd_kcontrol *kcontrol,1440 struct snd_ctl_elem_info *uinfo)1441{1442 uinfo->type = SNDRV_CTL_ELEM_TYPE_BYTES;1443 uinfo->count = HDMI_MAX_ELD_BYTES;1444 return 0;1445}1446 1447static int had_ctl_eld_get(struct snd_kcontrol *kcontrol,1448 struct snd_ctl_elem_value *ucontrol)1449{1450 struct snd_intelhad *intelhaddata = snd_kcontrol_chip(kcontrol);1451 1452 mutex_lock(&intelhaddata->mutex);1453 memcpy(ucontrol->value.bytes.data, intelhaddata->eld,1454 HDMI_MAX_ELD_BYTES);1455 mutex_unlock(&intelhaddata->mutex);1456 return 0;1457}1458 1459static const struct snd_kcontrol_new had_controls[] = {1460 {1461 .access = SNDRV_CTL_ELEM_ACCESS_READ,1462 .iface = SNDRV_CTL_ELEM_IFACE_PCM,1463 .name = SNDRV_CTL_NAME_IEC958("", PLAYBACK, MASK),1464 .info = had_iec958_info, /* shared */1465 .get = had_iec958_mask_get,1466 },1467 {1468 .iface = SNDRV_CTL_ELEM_IFACE_PCM,1469 .name = SNDRV_CTL_NAME_IEC958("", PLAYBACK, DEFAULT),1470 .info = had_iec958_info,1471 .get = had_iec958_get,1472 .put = had_iec958_put,1473 },1474 {1475 .access = (SNDRV_CTL_ELEM_ACCESS_READ |1476 SNDRV_CTL_ELEM_ACCESS_VOLATILE),1477 .iface = SNDRV_CTL_ELEM_IFACE_PCM,1478 .name = "ELD",1479 .info = had_ctl_eld_info,1480 .get = had_ctl_eld_get,1481 },1482};1483 1484/*1485 * audio interrupt handler1486 */1487static irqreturn_t display_pipe_interrupt_handler(int irq, void *dev_id)1488{1489 struct snd_intelhad_card *card_ctx = dev_id;1490 u32 audio_stat[3] = {};1491 int pipe, port;1492 1493 for_each_pipe(card_ctx, pipe) {1494 /* use raw register access to ack IRQs even while disconnected */1495 audio_stat[pipe] = had_read_register_raw(card_ctx, pipe,1496 AUD_HDMI_STATUS) &1497 (HDMI_AUDIO_UNDERRUN | HDMI_AUDIO_BUFFER_DONE);1498 1499 if (audio_stat[pipe])1500 had_write_register_raw(card_ctx, pipe,1501 AUD_HDMI_STATUS, audio_stat[pipe]);1502 }1503 1504 for_each_port(card_ctx, port) {1505 struct snd_intelhad *ctx = &card_ctx->pcm_ctx[port];1506 int pipe = ctx->pipe;1507 1508 if (pipe < 0)1509 continue;1510 1511 if (audio_stat[pipe] & HDMI_AUDIO_BUFFER_DONE)1512 had_process_buffer_done(ctx);1513 if (audio_stat[pipe] & HDMI_AUDIO_UNDERRUN)1514 had_process_buffer_underrun(ctx);1515 }1516 1517 return IRQ_HANDLED;1518}1519 1520/*1521 * monitor plug/unplug notification from i915; just kick off the work1522 */1523static void notify_audio_lpe(struct platform_device *pdev, int port)1524{1525 struct snd_intelhad_card *card_ctx = platform_get_drvdata(pdev);1526 struct snd_intelhad *ctx;1527 1528 ctx = &card_ctx->pcm_ctx[single_port ? 0 : port];1529 if (single_port)1530 ctx->port = port;1531 1532 schedule_work(&ctx->hdmi_audio_wq);1533}1534 1535/* the work to handle monitor hot plug/unplug */1536static void had_audio_wq(struct work_struct *work)1537{1538 struct snd_intelhad *ctx =1539 container_of(work, struct snd_intelhad, hdmi_audio_wq);1540 struct intel_hdmi_lpe_audio_pdata *pdata = ctx->dev->platform_data;1541 struct intel_hdmi_lpe_audio_port_pdata *ppdata = &pdata->port[ctx->port];1542 int ret;1543 1544 ret = pm_runtime_resume_and_get(ctx->dev);1545 if (ret < 0)1546 return;1547 1548 mutex_lock(&ctx->mutex);1549 if (ppdata->pipe < 0) {1550 dev_dbg(ctx->dev, "%s: Event: HAD_NOTIFY_HOT_UNPLUG : port = %d\n",1551 __func__, ctx->port);1552 1553 memset(ctx->eld, 0, sizeof(ctx->eld)); /* clear the old ELD */1554 1555 ctx->dp_output = false;1556 ctx->tmds_clock_speed = 0;1557 ctx->link_rate = 0;1558 1559 /* Shut down the stream */1560 had_process_hot_unplug(ctx);1561 1562 ctx->pipe = -1;1563 } else {1564 dev_dbg(ctx->dev, "%s: HAD_NOTIFY_ELD : port = %d, tmds = %d\n",1565 __func__, ctx->port, ppdata->ls_clock);1566 1567 memcpy(ctx->eld, ppdata->eld, sizeof(ctx->eld));1568 1569 ctx->dp_output = ppdata->dp_output;1570 if (ctx->dp_output) {1571 ctx->tmds_clock_speed = 0;1572 ctx->link_rate = ppdata->ls_clock;1573 } else {1574 ctx->tmds_clock_speed = ppdata->ls_clock;1575 ctx->link_rate = 0;1576 }1577 1578 /*1579 * Shut down the stream before we change1580 * the pipe assignment for this pcm device1581 */1582 had_process_hot_plug(ctx);1583 1584 ctx->pipe = ppdata->pipe;1585 1586 /* Restart the stream if necessary */1587 had_process_mode_change(ctx);1588 }1589 1590 mutex_unlock(&ctx->mutex);1591 pm_runtime_mark_last_busy(ctx->dev);1592 pm_runtime_put_autosuspend(ctx->dev);1593}1594 1595/*1596 * Jack interface1597 */1598static int had_create_jack(struct snd_intelhad *ctx,1599 struct snd_pcm *pcm)1600{1601 char hdmi_str[32];1602 int err;1603 1604 snprintf(hdmi_str, sizeof(hdmi_str),1605 "HDMI/DP,pcm=%d", pcm->device);1606 1607 err = snd_jack_new(ctx->card_ctx->card, hdmi_str,1608 SND_JACK_AVOUT, &ctx->jack,1609 true, false);1610 if (err < 0)1611 return err;1612 ctx->jack->private_data = ctx;1613 return 0;1614}1615 1616/*1617 * PM callbacks1618 */1619 1620static int __maybe_unused hdmi_lpe_audio_suspend(struct device *dev)1621{1622 struct snd_intelhad_card *card_ctx = dev_get_drvdata(dev);1623 1624 snd_power_change_state(card_ctx->card, SNDRV_CTL_POWER_D3hot);1625 1626 return 0;1627}1628 1629static int __maybe_unused hdmi_lpe_audio_resume(struct device *dev)1630{1631 struct snd_intelhad_card *card_ctx = dev_get_drvdata(dev);1632 1633 pm_runtime_mark_last_busy(dev);1634 1635 snd_power_change_state(card_ctx->card, SNDRV_CTL_POWER_D0);1636 1637 return 0;1638}1639 1640/* release resources */1641static void hdmi_lpe_audio_free(struct snd_card *card)1642{1643 struct snd_intelhad_card *card_ctx = card->private_data;1644 struct intel_hdmi_lpe_audio_pdata *pdata = card_ctx->dev->platform_data;1645 int port;1646 1647 spin_lock_irq(&pdata->lpe_audio_slock);1648 pdata->notify_audio_lpe = NULL;1649 spin_unlock_irq(&pdata->lpe_audio_slock);1650 1651 for_each_port(card_ctx, port) {1652 struct snd_intelhad *ctx = &card_ctx->pcm_ctx[port];1653 1654 cancel_work_sync(&ctx->hdmi_audio_wq);1655 }1656}1657 1658/*1659 * hdmi_lpe_audio_probe - start bridge with i9151660 *1661 * This function is called when the i915 driver creates the1662 * hdmi-lpe-audio platform device.1663 */1664static int __hdmi_lpe_audio_probe(struct platform_device *pdev)1665{1666 struct snd_card *card;1667 struct snd_intelhad_card *card_ctx;1668 struct snd_intelhad *ctx;1669 struct snd_pcm *pcm;1670 struct intel_hdmi_lpe_audio_pdata *pdata;1671 int irq;1672 struct resource *res_mmio;1673 int port, ret;1674 1675 pdata = pdev->dev.platform_data;1676 if (!pdata) {1677 dev_err(&pdev->dev, "%s: quit: pdata not allocated by i915!!\n", __func__);1678 return -EINVAL;1679 }1680 1681 /* get resources */1682 irq = platform_get_irq(pdev, 0);1683 if (irq < 0)1684 return irq;1685 1686 res_mmio = platform_get_resource(pdev, IORESOURCE_MEM, 0);1687 if (!res_mmio) {1688 dev_err(&pdev->dev, "Could not get IO_MEM resources\n");1689 return -ENXIO;1690 }1691 1692 /* create a card instance with ALSA framework */1693 ret = snd_devm_card_new(&pdev->dev, hdmi_card_index, hdmi_card_id,1694 THIS_MODULE, sizeof(*card_ctx), &card);1695 if (ret)1696 return ret;1697 1698 card_ctx = card->private_data;1699 card_ctx->dev = &pdev->dev;1700 card_ctx->card = card;1701 strcpy(card->driver, INTEL_HAD);1702 strcpy(card->shortname, "Intel HDMI/DP LPE Audio");1703 strcpy(card->longname, "Intel HDMI/DP LPE Audio");1704 1705 card_ctx->irq = -1;1706 1707 card->private_free = hdmi_lpe_audio_free;1708 1709 platform_set_drvdata(pdev, card_ctx);1710 1711 card_ctx->num_pipes = pdata->num_pipes;1712 card_ctx->num_ports = single_port ? 1 : pdata->num_ports;1713 1714 for_each_port(card_ctx, port) {1715 ctx = &card_ctx->pcm_ctx[port];1716 ctx->card_ctx = card_ctx;1717 ctx->dev = card_ctx->dev;1718 ctx->port = single_port ? -1 : port;1719 ctx->pipe = -1;1720 1721 spin_lock_init(&ctx->had_spinlock);1722 mutex_init(&ctx->mutex);1723 INIT_WORK(&ctx->hdmi_audio_wq, had_audio_wq);1724 }1725 1726 dev_dbg(&pdev->dev, "%s: mmio_start = 0x%x, mmio_end = 0x%x\n",1727 __func__, (unsigned int)res_mmio->start,1728 (unsigned int)res_mmio->end);1729 1730 card_ctx->mmio_start =1731 devm_ioremap(&pdev->dev, res_mmio->start,1732 (size_t)(resource_size(res_mmio)));1733 if (!card_ctx->mmio_start) {1734 dev_err(&pdev->dev, "Could not get ioremap\n");1735 return -EACCES;1736 }1737 1738 /* setup interrupt handler */1739 ret = devm_request_irq(&pdev->dev, irq, display_pipe_interrupt_handler,1740 0, pdev->name, card_ctx);1741 if (ret < 0) {1742 dev_err(&pdev->dev, "request_irq failed\n");1743 return ret;1744 }1745 1746 card_ctx->irq = irq;1747 1748 /* only 32bit addressable */1749 ret = dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(32));1750 if (ret)1751 return ret;1752 1753 init_channel_allocations();1754 1755 card_ctx->num_pipes = pdata->num_pipes;1756 card_ctx->num_ports = single_port ? 1 : pdata->num_ports;1757 1758 for_each_port(card_ctx, port) {1759 int i;1760 1761 ctx = &card_ctx->pcm_ctx[port];1762 ret = snd_pcm_new(card, INTEL_HAD, port, MAX_PB_STREAMS,1763 MAX_CAP_STREAMS, &pcm);1764 if (ret)1765 return ret;1766 1767 /* setup private data which can be retrieved when required */1768 pcm->private_data = ctx;1769 pcm->info_flags = 0;1770 strscpy(pcm->name, card->shortname, strlen(card->shortname));1771 /* setup the ops for playback */1772 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, &had_pcm_ops);1773 1774 /* allocate dma pages;1775 * try to allocate 600k buffer as default which is large enough1776 */1777 snd_pcm_set_managed_buffer_all(pcm, SNDRV_DMA_TYPE_DEV_WC,1778 card->dev, HAD_DEFAULT_BUFFER,1779 HAD_MAX_BUFFER);1780 1781 /* create controls */1782 for (i = 0; i < ARRAY_SIZE(had_controls); i++) {1783 struct snd_kcontrol *kctl;1784 1785 kctl = snd_ctl_new1(&had_controls[i], ctx);1786 if (!kctl)1787 return -ENOMEM;1788 1789 kctl->id.device = pcm->device;1790 1791 ret = snd_ctl_add(card, kctl);1792 if (ret < 0)1793 return ret;1794 }1795 1796 /* Register channel map controls */1797 ret = had_register_chmap_ctls(ctx, pcm);1798 if (ret < 0)1799 return ret;1800 1801 ret = had_create_jack(ctx, pcm);1802 if (ret < 0)1803 return ret;1804 }1805 1806 ret = snd_card_register(card);1807 if (ret)1808 return ret;1809 1810 spin_lock_irq(&pdata->lpe_audio_slock);1811 pdata->notify_audio_lpe = notify_audio_lpe;1812 spin_unlock_irq(&pdata->lpe_audio_slock);1813 1814 pm_runtime_set_autosuspend_delay(&pdev->dev, INTEL_HDMI_AUDIO_SUSPEND_DELAY_MS);1815 pm_runtime_use_autosuspend(&pdev->dev);1816 pm_runtime_enable(&pdev->dev);1817 pm_runtime_mark_last_busy(&pdev->dev);1818 pm_runtime_idle(&pdev->dev);1819 1820 dev_dbg(&pdev->dev, "%s: handle pending notification\n", __func__);1821 for_each_port(card_ctx, port) {1822 struct snd_intelhad *ctx = &card_ctx->pcm_ctx[port];1823 1824 schedule_work(&ctx->hdmi_audio_wq);1825 }1826 1827 return 0;1828}1829 1830static int hdmi_lpe_audio_probe(struct platform_device *pdev)1831{1832 return snd_card_free_on_error(&pdev->dev, __hdmi_lpe_audio_probe(pdev));1833}1834 1835static const struct dev_pm_ops hdmi_lpe_audio_pm = {1836 SET_SYSTEM_SLEEP_PM_OPS(hdmi_lpe_audio_suspend, hdmi_lpe_audio_resume)1837};1838 1839static struct platform_driver hdmi_lpe_audio_driver = {1840 .driver = {1841 .name = "hdmi-lpe-audio",1842 .pm = &hdmi_lpe_audio_pm,1843 },1844 .probe = hdmi_lpe_audio_probe,1845};1846 1847module_platform_driver(hdmi_lpe_audio_driver);1848MODULE_ALIAS("platform:hdmi_lpe_audio");1849 1850MODULE_AUTHOR("Sailaja Bandarupalli <sailaja.bandarupalli@intel.com>");1851MODULE_AUTHOR("Ramesh Babu K V <ramesh.babu@intel.com>");1852MODULE_AUTHOR("Vaibhav Agarwal <vaibhav.agarwal@intel.com>");1853MODULE_AUTHOR("Jerome Anand <jerome.anand@intel.com>");1854MODULE_DESCRIPTION("Intel HDMI Audio driver");1855MODULE_LICENSE("GPL v2");1856