• Home
  • Raw
  • Download

Lines Matching +full:ports +full:- +full:offset2

1 // SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause)
2 // Copyright(c) 2015-17 Intel Corporation.
200 return readl(cdns->registers + offset); in cdns_readl()
205 writel(value, cdns->registers + offset); in cdns_writel()
225 reg_read = readl(cdns->registers + offset); in cdns_set_wait()
229 timeout--; in cdns_set_wait()
233 return -ETIMEDOUT; in cdns_set_wait()
238 writel(value, cdns->registers + offset); in cdns_clear_bit()
253 dev_err(cdns->dev, "Cannot program MCP_CONFIG_UPDATE in ClockStopMode\n"); in cdns_config_update()
254 return -EINVAL; in cdns_config_update()
260 dev_err(cdns->dev, "Config update timedout\n"); in cdns_config_update()
275 return scnprintf(buf + pos, RD_BUF - pos, in cdns_sprintf()
281 struct sdw_cdns *cdns = s->private; in cdns_reg_show()
289 return -ENOMEM; in cdns_reg_show()
292 ret += scnprintf(buf + ret, RD_BUF - ret, "\nMCP Registers\n"); in cdns_reg_show()
297 ret += scnprintf(buf + ret, RD_BUF - ret, in cdns_reg_show()
303 ret += scnprintf(buf + ret, RD_BUF - ret, in cdns_reg_show()
310 ret += scnprintf(buf + ret, RD_BUF - ret, in cdns_reg_show()
313 num_ports = cdns->num_ports; in cdns_reg_show()
316 ret += scnprintf(buf + ret, RD_BUF - ret, in cdns_reg_show()
317 "\nDP-%d\n", i); in cdns_reg_show()
323 ret += scnprintf(buf + ret, RD_BUF - ret, in cdns_reg_show()
326 ret += scnprintf(buf + ret, RD_BUF - ret, in cdns_reg_show()
327 "\nDP-%d\n", i); in cdns_reg_show()
334 ret += scnprintf(buf + ret, RD_BUF - ret, in cdns_reg_show()
340 ret += scnprintf(buf + ret, RD_BUF - ret, in cdns_reg_show()
343 /* number of PDI and ports is interchangeable */ in cdns_reg_show()
360 return -EINVAL; in cdns_hw_reset()
367 dev_dbg(cdns->dev, "link hw_reset done: %d\n", ret); in cdns_hw_reset()
381 return -EINVAL; in cdns_parity_error_injection()
383 bus = &cdns->bus; in cdns_parity_error_injection()
387 * Slave devices will re-attach and be re-enumerated. in cdns_parity_error_injection()
389 ret = pm_runtime_get_sync(bus->dev); in cdns_parity_error_injection()
390 if (ret < 0 && ret != -EACCES) { in cdns_parity_error_injection()
391 dev_err_ratelimited(cdns->dev, in cdns_parity_error_injection()
394 pm_runtime_put_noidle(bus->dev); in cdns_parity_error_injection()
408 mutex_lock(&bus->bus_lock); in cdns_parity_error_injection()
421 ret = sdw_bread_no_pm_unlocked(&cdns->bus, 0xf, SDW_SCP_DEVID_0); in cdns_parity_error_injection()
422 dev_info(cdns->dev, "parity error injection, read: %d\n", ret); in cdns_parity_error_injection()
435 mutex_unlock(&bus->bus_lock); in cdns_parity_error_injection()
444 pm_runtime_mark_last_busy(bus->dev); in cdns_parity_error_injection()
445 pm_runtime_put_autosuspend(bus->dev); in cdns_parity_error_injection()
454 * sdw_cdns_debugfs_init() - Cadence debugfs init
460 debugfs_create_file("cdns-registers", 0400, root, cdns, &cdns_reg_fops); in sdw_cdns_debugfs_init()
462 debugfs_create_file("cdns-hw-reset", 0200, root, cdns, in sdw_cdns_debugfs_init()
465 debugfs_create_file("cdns-parity-error-injection", 0200, root, cdns, in sdw_cdns_debugfs_init()
484 if (!(cdns->response_buf[i] & CDNS_MCP_RESP_ACK)) { in cdns_fill_msg_resp()
486 dev_dbg_ratelimited(cdns->dev, "Msg Ack not received\n"); in cdns_fill_msg_resp()
488 if (cdns->response_buf[i] & CDNS_MCP_RESP_NACK) { in cdns_fill_msg_resp()
490 dev_err_ratelimited(cdns->dev, "Msg NACK received\n"); in cdns_fill_msg_resp()
495 dev_err_ratelimited(cdns->dev, "Msg NACKed for Slave %d\n", msg->dev_num); in cdns_fill_msg_resp()
500 dev_dbg_ratelimited(cdns->dev, "Msg ignored for Slave %d\n", msg->dev_num); in cdns_fill_msg_resp()
504 if (msg->flags == SDW_MSG_FLAG_READ) { in cdns_fill_msg_resp()
507 msg->buf[i + offset] = FIELD_GET(CDNS_MCP_RESP_RDATA, in cdns_fill_msg_resp()
508 cdns->response_buf[i]); in cdns_fill_msg_resp()
520 BUILD_BUG_ON(ARRAY_SIZE(cdns->response_buf) < CDNS_MCP_CMD_LEN + 2); in cdns_read_response()
524 if (num_resp > ARRAY_SIZE(cdns->response_buf)) { in cdns_read_response()
525 dev_warn(cdns->dev, "RX AVAIL %d too long\n", num_resp); in cdns_read_response()
526 num_resp = ARRAY_SIZE(cdns->response_buf); in cdns_read_response()
532 cdns->response_buf[i] = cdns_readl(cdns, cmd_base); in cdns_read_response()
546 if (cdns->msg_count != count) { in _cdns_xfer_msg()
548 cdns->msg_count = count; in _cdns_xfer_msg()
552 addr = msg->addr; in _cdns_xfer_msg()
555 data = FIELD_PREP(CDNS_MCP_CMD_DEV_ADDR, msg->dev_num); in _cdns_xfer_msg()
560 if (msg->flags == SDW_MSG_FLAG_WRITE) in _cdns_xfer_msg()
561 data |= msg->buf[i + offset]; in _cdns_xfer_msg()
563 data |= FIELD_PREP(CDNS_MCP_CMD_SSP_TAG, msg->ssp_sync); in _cdns_xfer_msg()
572 time = wait_for_completion_timeout(&cdns->tx_complete, in _cdns_xfer_msg()
575 dev_err(cdns->dev, "IO transfer timed out, cmd %d device %d addr %x len %d\n", in _cdns_xfer_msg()
576 cmd, msg->dev_num, msg->addr, msg->len); in _cdns_xfer_msg()
577 msg->len = 0; in _cdns_xfer_msg()
597 if (cdns->msg_count != CDNS_SCP_RX_FIFOLEVEL) { in cdns_program_scp_addr()
599 cdns->msg_count = CDNS_SCP_RX_FIFOLEVEL; in cdns_program_scp_addr()
602 data[0] = FIELD_PREP(CDNS_MCP_CMD_DEV_ADDR, msg->dev_num); in cdns_program_scp_addr()
609 data[0] |= msg->addr_page1; in cdns_program_scp_addr()
610 data[1] |= msg->addr_page2; in cdns_program_scp_addr()
617 time = wait_for_completion_timeout(&cdns->tx_complete, in cdns_program_scp_addr()
620 dev_err(cdns->dev, "SCP Msg trf timed out\n"); in cdns_program_scp_addr()
621 msg->len = 0; in cdns_program_scp_addr()
627 if (!(cdns->response_buf[i] & CDNS_MCP_RESP_ACK)) { in cdns_program_scp_addr()
629 dev_err(cdns->dev, "Program SCP Ack not received\n"); in cdns_program_scp_addr()
630 if (cdns->response_buf[i] & CDNS_MCP_RESP_NACK) { in cdns_program_scp_addr()
632 dev_err(cdns->dev, "Program SCP NACK received\n"); in cdns_program_scp_addr()
639 dev_err_ratelimited(cdns->dev, in cdns_program_scp_addr()
640 "SCP_addrpage NACKed for Slave %d\n", msg->dev_num); in cdns_program_scp_addr()
645 dev_dbg_ratelimited(cdns->dev, in cdns_program_scp_addr()
646 "SCP_addrpage ignored for Slave %d\n", msg->dev_num); in cdns_program_scp_addr()
657 if (msg->page) { in cdns_prep_msg()
660 msg->len = 0; in cdns_prep_msg()
665 switch (msg->flags) { in cdns_prep_msg()
675 dev_err(cdns->dev, "Invalid msg cmd: %d\n", msg->flags); in cdns_prep_msg()
676 return -EINVAL; in cdns_prep_msg()
692 for (i = 0; i < msg->len / CDNS_MCP_CMD_LEN; i++) { in cdns_xfer_msg()
699 if (!(msg->len % CDNS_MCP_CMD_LEN)) in cdns_xfer_msg()
703 msg->len % CDNS_MCP_CMD_LEN, false); in cdns_xfer_msg()
718 if (msg->len > 1) in cdns_xfer_msg_defer()
719 return -ENOTSUPP; in cdns_xfer_msg_defer()
725 cdns->defer = defer; in cdns_xfer_msg_defer()
726 cdns->defer->length = msg->len; in cdns_xfer_msg_defer()
728 return _cdns_xfer_msg(cdns, msg, cmd, 0, msg->len, true); in cdns_xfer_msg_defer()
796 dev_warn_ratelimited(cdns->dev, in cdns_update_slave_status()
820 dev_warn_ratelimited(cdns->dev, in cdns_update_slave_status()
828 return sdw_handle_slave_status(&cdns->bus, status); in cdns_update_slave_status()
834 * sdw_cdns_irq() - Cadence interrupt handler
845 if (!cdns->link_up) in sdw_cdns_irq()
860 if (cdns->defer) { in sdw_cdns_irq()
861 cdns_fill_msg_resp(cdns, cdns->defer->msg, in sdw_cdns_irq()
862 cdns->defer->length, 0); in sdw_cdns_irq()
863 complete(&cdns->defer->complete); in sdw_cdns_irq()
864 cdns->defer = NULL; in sdw_cdns_irq()
866 complete(&cdns->tx_complete); in sdw_cdns_irq()
872 dev_err_ratelimited(cdns->dev, "Parity error\n"); in sdw_cdns_irq()
877 dev_err_ratelimited(cdns->dev, "Bus clash for control word\n"); in sdw_cdns_irq()
885 dev_err_ratelimited(cdns->dev, "Bus clash for data word\n"); in sdw_cdns_irq()
888 if (cdns->bus.params.m_data_mode != SDW_PORT_DATA_MODE_NORMAL && in sdw_cdns_irq()
892 /* just log which ports report an error */ in sdw_cdns_irq()
894 dev_err_ratelimited(cdns->dev, "DP interrupt: PortIntStat %8x\n", in sdw_cdns_irq()
915 if (cdns->interrupt_enabled) in sdw_cdns_irq()
916 schedule_work(&cdns->work); in sdw_cdns_irq()
936 dev_dbg_ratelimited(cdns->dev, "Slave status change\n"); in cdns_update_slave_status_work()
957 * sdw_cdns_exit_reset() - Program reset parameters and start bus operations
984 * sdw_cdns_enable_slave_interrupt() - Enable SDW slave interrupts
1002 * sdw_cdns_enable_interrupt() - Enable SDW interrupts
1026 if (cdns->bus.params.m_data_mode != SDW_PORT_DATA_MODE_NORMAL) in sdw_cdns_enable_interrupt()
1051 cdns->interrupt_enabled = state; in sdw_cdns_enable_interrupt()
1054 * Complete any on-going status updates before updating masks, in sdw_cdns_enable_interrupt()
1063 cancel_work_sync(&cdns->work); in sdw_cdns_enable_interrupt()
1083 pdi = devm_kcalloc(cdns->dev, num, sizeof(*pdi), GFP_KERNEL); in cdns_allocate_pdi()
1085 return -ENOMEM; in cdns_allocate_pdi()
1096 * sdw_cdns_pdi_init() - PDI initialization routine
1108 cdns->pcm.num_bd = config.pcm_bd; in sdw_cdns_pdi_init()
1109 cdns->pcm.num_in = config.pcm_in; in sdw_cdns_pdi_init()
1110 cdns->pcm.num_out = config.pcm_out; in sdw_cdns_pdi_init()
1111 cdns->pdm.num_bd = config.pdm_bd; in sdw_cdns_pdi_init()
1112 cdns->pdm.num_in = config.pdm_in; in sdw_cdns_pdi_init()
1113 cdns->pdm.num_out = config.pdm_out; in sdw_cdns_pdi_init()
1116 stream = &cdns->pcm; in sdw_cdns_pdi_init()
1121 ret = cdns_allocate_pdi(cdns, &stream->bd, in sdw_cdns_pdi_init()
1122 stream->num_bd, offset); in sdw_cdns_pdi_init()
1126 offset += stream->num_bd; in sdw_cdns_pdi_init()
1128 ret = cdns_allocate_pdi(cdns, &stream->in, in sdw_cdns_pdi_init()
1129 stream->num_in, offset); in sdw_cdns_pdi_init()
1133 offset += stream->num_in; in sdw_cdns_pdi_init()
1135 ret = cdns_allocate_pdi(cdns, &stream->out, in sdw_cdns_pdi_init()
1136 stream->num_out, offset); in sdw_cdns_pdi_init()
1141 stream->num_pdi = stream->num_bd + stream->num_in + stream->num_out; in sdw_cdns_pdi_init()
1142 cdns->num_ports = stream->num_pdi; in sdw_cdns_pdi_init()
1145 stream = &cdns->pdm; in sdw_cdns_pdi_init()
1146 ret = cdns_allocate_pdi(cdns, &stream->bd, in sdw_cdns_pdi_init()
1147 stream->num_bd, offset); in sdw_cdns_pdi_init()
1151 offset += stream->num_bd; in sdw_cdns_pdi_init()
1153 ret = cdns_allocate_pdi(cdns, &stream->in, in sdw_cdns_pdi_init()
1154 stream->num_in, offset); in sdw_cdns_pdi_init()
1158 offset += stream->num_in; in sdw_cdns_pdi_init()
1160 ret = cdns_allocate_pdi(cdns, &stream->out, in sdw_cdns_pdi_init()
1161 stream->num_out, offset); in sdw_cdns_pdi_init()
1167 stream->num_pdi = stream->num_bd + stream->num_in + stream->num_out; in sdw_cdns_pdi_init()
1168 cdns->num_ports += stream->num_pdi; in sdw_cdns_pdi_init()
1191 struct sdw_bus *bus = &cdns->bus; in cdns_init_clock_ctrl()
1192 struct sdw_master_prop *prop = &bus->prop; in cdns_init_clock_ctrl()
1198 divider = (prop->mclk_freq / prop->max_clk_freq) - 1; in cdns_init_clock_ctrl()
1209 val = cdns_set_initial_frame_shape(prop->default_row, in cdns_init_clock_ctrl()
1210 prop->default_col); in cdns_init_clock_ctrl()
1214 ssp_interval = prop->default_frame_rate / SDW_CADENCE_GSYNC_HZ; in cdns_init_clock_ctrl()
1220 * sdw_cdns_init() - Cadence initialization
1230 cdns->msg_count = cdns_readl(cdns, CDNS_MCP_FIFOLEVEL); in sdw_cdns_init()
1256 if (cdns->bus.multi_link) in sdw_cdns_init()
1257 /* Set Multi-master mode to take gsync into account */ in sdw_cdns_init()
1273 struct sdw_master_prop *prop = &bus->prop; in cdns_bus_conf()
1278 if (!params->curr_dr_freq) { in cdns_bus_conf()
1279 dev_err(cdns->dev, "NULL curr_dr_freq\n"); in cdns_bus_conf()
1280 return -EINVAL; in cdns_bus_conf()
1283 divider = prop->mclk_freq * SDW_DOUBLE_RATE_FACTOR / in cdns_bus_conf()
1284 params->curr_dr_freq; in cdns_bus_conf()
1285 divider--; /* divider is 1/(N+1) */ in cdns_bus_conf()
1287 if (params->next_bank) in cdns_bus_conf()
1305 dpn_config_off = CDNS_DPN_B1_CONFIG(p_params->num); in cdns_port_params()
1307 dpn_config_off = CDNS_DPN_B0_CONFIG(p_params->num); in cdns_port_params()
1311 u32p_replace_bits(&dpn_config, (p_params->bps - 1), CDNS_DPN_CONFIG_WL); in cdns_port_params()
1312 u32p_replace_bits(&dpn_config, p_params->flow_mode, CDNS_DPN_CONFIG_PORT_FLOW); in cdns_port_params()
1313 u32p_replace_bits(&dpn_config, p_params->data_mode, CDNS_DPN_CONFIG_PORT_DAT); in cdns_port_params()
1328 int num = t_params->port_num; in cdns_transport_params()
1333 * both PCM and PDM ports. in cdns_transport_params()
1349 u32p_replace_bits(&dpn_config, t_params->blk_grp_ctrl, CDNS_DPN_CONFIG_BGC); in cdns_transport_params()
1350 u32p_replace_bits(&dpn_config, t_params->blk_pkg_mode, CDNS_DPN_CONFIG_BPM); in cdns_transport_params()
1353 u32p_replace_bits(&dpn_offsetctrl, t_params->offset1, CDNS_DPN_OFFSET_CTRL_1); in cdns_transport_params()
1354 u32p_replace_bits(&dpn_offsetctrl, t_params->offset2, CDNS_DPN_OFFSET_CTRL_2); in cdns_transport_params()
1357 u32p_replace_bits(&dpn_hctrl, t_params->hstart, CDNS_DPN_HCTRL_HSTART); in cdns_transport_params()
1358 u32p_replace_bits(&dpn_hctrl, t_params->hstop, CDNS_DPN_HCTRL_HSTOP); in cdns_transport_params()
1359 u32p_replace_bits(&dpn_hctrl, t_params->lane_ctrl, CDNS_DPN_HCTRL_LCTRL); in cdns_transport_params()
1362 cdns_writel(cdns, dpn_samplectrl_off, (t_params->sample_interval - 1)); in cdns_transport_params()
1374 dpn_chnen_off = CDNS_DPN_B1_CH_EN(enable_ch->port_num); in cdns_port_enable()
1376 dpn_chnen_off = CDNS_DPN_B0_CH_EN(enable_ch->port_num); in cdns_port_enable()
1378 ch_mask = enable_ch->ch_mask * enable_ch->enable; in cdns_port_enable()
1415 dev_dbg(cdns->dev, "Clock is already stopped\n"); in sdw_cdns_clock_stop()
1428 * master into a state in which it ignores wake-up trials in sdw_cdns_clock_stop()
1436 list_for_each_entry(slave, &cdns->bus.slaves, node) { in sdw_cdns_clock_stop()
1437 if (slave->status == SDW_SLAVE_ATTACHED || in sdw_cdns_clock_stop()
1438 slave->status == SDW_SLAVE_ALERT) { in sdw_cdns_clock_stop()
1461 dev_err(cdns->dev, "%s: config_update failed\n", __func__); in sdw_cdns_clock_stop()
1467 ret = sdw_bus_prep_clk_stop(&cdns->bus); in sdw_cdns_clock_stop()
1468 if (ret < 0 && ret != -ENODATA) { in sdw_cdns_clock_stop()
1469 dev_err(cdns->dev, "prepare clock stop failed %d\n", ret); in sdw_cdns_clock_stop()
1478 ret = sdw_bus_clk_stop(&cdns->bus); in sdw_cdns_clock_stop()
1479 if (ret < 0 && slave_present && ret != -ENODATA) { in sdw_cdns_clock_stop()
1480 dev_err(cdns->dev, "bus clock stop failed %d", ret); in sdw_cdns_clock_stop()
1488 dev_err(cdns->dev, "Clock stop failed %d\n", ret); in sdw_cdns_clock_stop()
1499 * may require a Severe Reset and re-enumeration after a wake.
1511 dev_err(cdns->dev, "Couldn't exit from clock stop\n"); in sdw_cdns_clock_restart()
1517 dev_err(cdns->dev, "clock stop exit failed %d\n", ret); in sdw_cdns_clock_restart()
1539 dev_err(cdns->dev, "%s: config_update failed\n", __func__); in sdw_cdns_clock_restart()
1543 ret = sdw_bus_exit_clk_stop(&cdns->bus); in sdw_cdns_clock_restart()
1545 dev_err(cdns->dev, "bus failed to exit clock stop %d\n", ret); in sdw_cdns_clock_restart()
1553 * sdw_cdns_probe() - Cadence probe routine
1558 init_completion(&cdns->tx_complete); in sdw_cdns_probe()
1559 cdns->bus.port_ops = &cdns_port_ops; in sdw_cdns_probe()
1561 INIT_WORK(&cdns->work, cdns_update_slave_status_work); in sdw_cdns_probe()
1575 dma = dai->playback_dma_data; in cdns_set_sdw_stream()
1577 dma = dai->capture_dma_data; in cdns_set_sdw_stream()
1580 dev_err(dai->dev, in cdns_set_sdw_stream()
1582 dai->name); in cdns_set_sdw_stream()
1583 return -EINVAL; in cdns_set_sdw_stream()
1589 return -ENOMEM; in cdns_set_sdw_stream()
1592 dma->stream_type = SDW_STREAM_PCM; in cdns_set_sdw_stream()
1594 dma->stream_type = SDW_STREAM_PDM; in cdns_set_sdw_stream()
1596 dma->bus = &cdns->bus; in cdns_set_sdw_stream()
1597 dma->link_id = cdns->instance; in cdns_set_sdw_stream()
1599 dma->stream = stream; in cdns_set_sdw_stream()
1602 dai->playback_dma_data = dma; in cdns_set_sdw_stream()
1604 dai->capture_dma_data = dma; in cdns_set_sdw_stream()
1608 kfree(dai->playback_dma_data); in cdns_set_sdw_stream()
1609 dai->playback_dma_data = NULL; in cdns_set_sdw_stream()
1611 kfree(dai->capture_dma_data); in cdns_set_sdw_stream()
1612 dai->capture_dma_data = NULL; in cdns_set_sdw_stream()
1620 * cdns_find_pdi() - Find a free PDI
1662 if (cdns->bus.params.m_data_mode != SDW_PORT_DATA_MODE_NORMAL) in sdw_cdns_config_stream()
1665 offset = CDNS_PORTCTRL + pdi->num * CDNS_PORT_OFFSET; in sdw_cdns_config_stream()
1670 val = pdi->num; in sdw_cdns_config_stream()
1672 val |= FIELD_PREP(CDNS_PDI_CONFIG_CHANNEL, (1 << ch) - 1); in sdw_cdns_config_stream()
1673 cdns_writel(cdns, CDNS_PDI_CONFIG(pdi->num), val); in sdw_cdns_config_stream()
1678 * sdw_cdns_alloc_pdi() - Allocate a PDI
1693 pdi = cdns_find_pdi(cdns, 0, stream->num_in, stream->in, in sdw_cdns_alloc_pdi()
1696 pdi = cdns_find_pdi(cdns, 0, stream->num_out, stream->out, in sdw_cdns_alloc_pdi()
1699 /* check if we found a PDI, else find in bi-directional */ in sdw_cdns_alloc_pdi()
1701 pdi = cdns_find_pdi(cdns, 2, stream->num_bd, stream->bd, in sdw_cdns_alloc_pdi()
1705 pdi->l_ch_num = 0; in sdw_cdns_alloc_pdi()
1706 pdi->h_ch_num = ch - 1; in sdw_cdns_alloc_pdi()
1707 pdi->dir = dir; in sdw_cdns_alloc_pdi()
1708 pdi->ch_count = ch; in sdw_cdns_alloc_pdi()