123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248 |
- // SPDX-License-Identifier: GPL-2.0-only
- /*
- * skl-debug.c - Debugfs for skl driver
- *
- * Copyright (C) 2016-17 Intel Corp
- */
- #include <linux/pci.h>
- #include <linux/debugfs.h>
- #include <uapi/sound/skl-tplg-interface.h>
- #include "skl.h"
- #include "skl-sst-dsp.h"
- #include "skl-sst-ipc.h"
- #include "skl-topology.h"
- #include "../common/sst-dsp.h"
- #include "../common/sst-dsp-priv.h"
- #define MOD_BUF PAGE_SIZE
- #define FW_REG_BUF PAGE_SIZE
- #define FW_REG_SIZE 0x60
- struct skl_debug {
- struct skl_dev *skl;
- struct device *dev;
- struct dentry *fs;
- struct dentry *modules;
- u8 fw_read_buff[FW_REG_BUF];
- };
- static ssize_t skl_print_pins(struct skl_module_pin *m_pin, char *buf,
- int max_pin, ssize_t size, bool direction)
- {
- int i;
- ssize_t ret = 0;
- for (i = 0; i < max_pin; i++) {
- ret += scnprintf(buf + size, MOD_BUF - size,
- "%s %d\n\tModule %d\n\tInstance %d\n\t"
- "In-used %s\n\tType %s\n"
- "\tState %d\n\tIndex %d\n",
- direction ? "Input Pin:" : "Output Pin:",
- i, m_pin[i].id.module_id,
- m_pin[i].id.instance_id,
- m_pin[i].in_use ? "Used" : "Unused",
- m_pin[i].is_dynamic ? "Dynamic" : "Static",
- m_pin[i].pin_state, i);
- size += ret;
- }
- return ret;
- }
- static ssize_t skl_print_fmt(struct skl_module_fmt *fmt, char *buf,
- ssize_t size, bool direction)
- {
- return scnprintf(buf + size, MOD_BUF - size,
- "%s\n\tCh %d\n\tFreq %d\n\tBit depth %d\n\t"
- "Valid bit depth %d\n\tCh config %#x\n\tInterleaving %d\n\t"
- "Sample Type %d\n\tCh Map %#x\n",
- direction ? "Input Format:" : "Output Format:",
- fmt->channels, fmt->s_freq, fmt->bit_depth,
- fmt->valid_bit_depth, fmt->ch_cfg,
- fmt->interleaving_style, fmt->sample_type,
- fmt->ch_map);
- }
- static ssize_t module_read(struct file *file, char __user *user_buf,
- size_t count, loff_t *ppos)
- {
- struct skl_module_cfg *mconfig = file->private_data;
- struct skl_module *module = mconfig->module;
- struct skl_module_res *res = &module->resources[mconfig->res_idx];
- char *buf;
- ssize_t ret;
- buf = kzalloc(MOD_BUF, GFP_KERNEL);
- if (!buf)
- return -ENOMEM;
- ret = scnprintf(buf, MOD_BUF, "Module:\n\tUUID %pUL\n\tModule id %d\n"
- "\tInstance id %d\n\tPvt_id %d\n", mconfig->guid,
- mconfig->id.module_id, mconfig->id.instance_id,
- mconfig->id.pvt_id);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "Resources:\n\tCPC %#x\n\tIBS %#x\n\tOBS %#x\t\n",
- res->cpc, res->ibs, res->obs);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "Module data:\n\tCore %d\n\tIn queue %d\n\t"
- "Out queue %d\n\tType %s\n",
- mconfig->core_id, mconfig->max_in_queue,
- mconfig->max_out_queue,
- mconfig->is_loadable ? "loadable" : "inbuilt");
- ret += skl_print_fmt(mconfig->in_fmt, buf, ret, true);
- ret += skl_print_fmt(mconfig->out_fmt, buf, ret, false);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "Fixup:\n\tParams %#x\n\tConverter %#x\n",
- mconfig->params_fixup, mconfig->converter);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "Module Gateway:\n\tType %#x\n\tVbus %#x\n\tHW conn %#x\n\tSlot %#x\n",
- mconfig->dev_type, mconfig->vbus_id,
- mconfig->hw_conn_type, mconfig->time_slot);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "Pipeline:\n\tID %d\n\tPriority %d\n\tConn Type %d\n\t"
- "Pages %#x\n", mconfig->pipe->ppl_id,
- mconfig->pipe->pipe_priority, mconfig->pipe->conn_type,
- mconfig->pipe->memory_pages);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "\tParams:\n\t\tHost DMA %d\n\t\tLink DMA %d\n",
- mconfig->pipe->p_params->host_dma_id,
- mconfig->pipe->p_params->link_dma_id);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "\tPCM params:\n\t\tCh %d\n\t\tFreq %d\n\t\tFormat %d\n",
- mconfig->pipe->p_params->ch,
- mconfig->pipe->p_params->s_freq,
- mconfig->pipe->p_params->s_fmt);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "\tLink %#x\n\tStream %#x\n",
- mconfig->pipe->p_params->linktype,
- mconfig->pipe->p_params->stream);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "\tState %d\n\tPassthru %s\n",
- mconfig->pipe->state,
- mconfig->pipe->passthru ? "true" : "false");
- ret += skl_print_pins(mconfig->m_in_pin, buf,
- mconfig->max_in_queue, ret, true);
- ret += skl_print_pins(mconfig->m_out_pin, buf,
- mconfig->max_out_queue, ret, false);
- ret += scnprintf(buf + ret, MOD_BUF - ret,
- "Other:\n\tDomain %d\n\tHomogeneous Input %s\n\t"
- "Homogeneous Output %s\n\tIn Queue Mask %d\n\t"
- "Out Queue Mask %d\n\tDMA ID %d\n\tMem Pages %d\n\t"
- "Module Type %d\n\tModule State %d\n",
- mconfig->domain,
- mconfig->homogenous_inputs ? "true" : "false",
- mconfig->homogenous_outputs ? "true" : "false",
- mconfig->in_queue_mask, mconfig->out_queue_mask,
- mconfig->dma_id, mconfig->mem_pages, mconfig->m_state,
- mconfig->m_type);
- ret = simple_read_from_buffer(user_buf, count, ppos, buf, ret);
- kfree(buf);
- return ret;
- }
- static const struct file_operations mcfg_fops = {
- .open = simple_open,
- .read = module_read,
- .llseek = default_llseek,
- };
- void skl_debug_init_module(struct skl_debug *d,
- struct snd_soc_dapm_widget *w,
- struct skl_module_cfg *mconfig)
- {
- debugfs_create_file(w->name, 0444, d->modules, mconfig,
- &mcfg_fops);
- }
- static ssize_t fw_softreg_read(struct file *file, char __user *user_buf,
- size_t count, loff_t *ppos)
- {
- struct skl_debug *d = file->private_data;
- struct sst_dsp *sst = d->skl->dsp;
- size_t w0_stat_sz = sst->addr.w0_stat_sz;
- void __iomem *in_base = sst->mailbox.in_base;
- void __iomem *fw_reg_addr;
- unsigned int offset;
- char *tmp;
- ssize_t ret = 0;
- tmp = kzalloc(FW_REG_BUF, GFP_KERNEL);
- if (!tmp)
- return -ENOMEM;
- fw_reg_addr = in_base - w0_stat_sz;
- memset(d->fw_read_buff, 0, FW_REG_BUF);
- if (w0_stat_sz > 0)
- __ioread32_copy(d->fw_read_buff, fw_reg_addr, w0_stat_sz >> 2);
- for (offset = 0; offset < FW_REG_SIZE; offset += 16) {
- ret += scnprintf(tmp + ret, FW_REG_BUF - ret, "%#.4x: ", offset);
- hex_dump_to_buffer(d->fw_read_buff + offset, 16, 16, 4,
- tmp + ret, FW_REG_BUF - ret, 0);
- ret += strlen(tmp + ret);
- /* print newline for each offset */
- if (FW_REG_BUF - ret > 0)
- tmp[ret++] = '\n';
- }
- ret = simple_read_from_buffer(user_buf, count, ppos, tmp, ret);
- kfree(tmp);
- return ret;
- }
- static const struct file_operations soft_regs_ctrl_fops = {
- .open = simple_open,
- .read = fw_softreg_read,
- .llseek = default_llseek,
- };
- struct skl_debug *skl_debugfs_init(struct skl_dev *skl)
- {
- struct skl_debug *d;
- d = devm_kzalloc(&skl->pci->dev, sizeof(*d), GFP_KERNEL);
- if (!d)
- return NULL;
- /* create the debugfs dir with platform component's debugfs as parent */
- d->fs = debugfs_create_dir("dsp", skl->component->debugfs_root);
- d->skl = skl;
- d->dev = &skl->pci->dev;
- /* now create the module dir */
- d->modules = debugfs_create_dir("modules", d->fs);
- debugfs_create_file("fw_soft_regs_rd", 0444, d->fs, d,
- &soft_regs_ctrl_fops);
- return d;
- }
- void skl_debugfs_exit(struct skl_dev *skl)
- {
- struct skl_debug *d = skl->debugfs;
- debugfs_remove_recursive(d->fs);
- d = NULL;
- }
|