Lines Matching +full:trace +full:- +full:buffer +full:- +full:extension
1 // SPDX-License-Identifier: GPL-2.0-only
9 #include "sof-priv.h"
10 #include "ipc4-priv.h"
15 * ------------------------
16 * | Page0 - descriptors |
17 * ------------------------
18 * | Page1 - slot0 |
19 * ------------------------
20 * | Page2 - slot1 |
21 * ------------------------
23 * ------------------------
24 * | Page14 - slot13 |
25 * ------------------------
26 * | Page15 - slot14 |
27 * ------------------------
37 * Log buffer slots have the following layout:
40 * u8 buffer[];
42 * The two pointers are offsets within the buffer.
118 struct sof_mtrace_core_data *core_data = inode->i_private; in sof_ipc4_mtrace_dfs_open()
121 mutex_lock(&core_data->buffer_lock); in sof_ipc4_mtrace_dfs_open()
123 if (core_data->log_buffer) { in sof_ipc4_mtrace_dfs_open()
124 ret = -EBUSY; in sof_ipc4_mtrace_dfs_open()
128 ret = debugfs_file_get(file->f_path.dentry); in sof_ipc4_mtrace_dfs_open()
132 core_data->log_buffer = kmalloc(SOF_IPC4_DEBUG_SLOT_SIZE, GFP_KERNEL); in sof_ipc4_mtrace_dfs_open()
133 if (!core_data->log_buffer) { in sof_ipc4_mtrace_dfs_open()
134 debugfs_file_put(file->f_path.dentry); in sof_ipc4_mtrace_dfs_open()
135 ret = -ENOMEM; in sof_ipc4_mtrace_dfs_open()
141 kfree(core_data->log_buffer); in sof_ipc4_mtrace_dfs_open()
142 debugfs_file_put(file->f_path.dentry); in sof_ipc4_mtrace_dfs_open()
146 mutex_unlock(&core_data->buffer_lock); in sof_ipc4_mtrace_dfs_open()
156 if (core_data->host_read_ptr != core_data->dsp_write_ptr) in sof_wait_mtrace_avail()
159 /* wait for available trace data from FW */ in sof_wait_mtrace_avail()
162 add_wait_queue(&core_data->trace_sleep, &wait); in sof_wait_mtrace_avail()
168 remove_wait_queue(&core_data->trace_sleep, &wait); in sof_wait_mtrace_avail()
170 if (core_data->host_read_ptr != core_data->dsp_write_ptr) in sof_wait_mtrace_avail()
176 static ssize_t sof_ipc4_mtrace_dfs_read(struct file *file, char __user *buffer, in sof_ipc4_mtrace_dfs_read() argument
179 struct sof_mtrace_core_data *core_data = file->private_data; in sof_ipc4_mtrace_dfs_read()
181 struct snd_sof_dev *sdev = core_data->sdev; in sof_ipc4_mtrace_dfs_read()
182 struct sof_mtrace_priv *priv = sdev->fw_trace_data; in sof_ipc4_mtrace_dfs_read()
183 void *log_buffer = core_data->log_buffer; in sof_ipc4_mtrace_dfs_read()
190 return -EINVAL; in sof_ipc4_mtrace_dfs_read()
198 if (copy_to_user(buffer, &avail, sizeof(avail))) in sof_ipc4_mtrace_dfs_read()
199 return -EFAULT; in sof_ipc4_mtrace_dfs_read()
204 if (core_data->slot_offset == SOF_IPC4_INVALID_SLOT_OFFSET) in sof_ipc4_mtrace_dfs_read()
207 /* The log data buffer starts after the two pointer in the slot */ in sof_ipc4_mtrace_dfs_read()
208 log_buffer_offset = core_data->slot_offset + (sizeof(u32) * 2); in sof_ipc4_mtrace_dfs_read()
210 log_buffer_size = SOF_IPC4_DEBUG_SLOT_SIZE - (sizeof(u32) * 2); in sof_ipc4_mtrace_dfs_read()
212 read_ptr = core_data->host_read_ptr; in sof_ipc4_mtrace_dfs_read()
213 write_ptr = core_data->dsp_write_ptr; in sof_ipc4_mtrace_dfs_read()
216 avail = write_ptr - read_ptr; in sof_ipc4_mtrace_dfs_read()
218 avail = log_buffer_size - read_ptr + write_ptr; in sof_ipc4_mtrace_dfs_read()
227 if (avail > count - sizeof(avail)) in sof_ipc4_mtrace_dfs_read()
228 avail = count - sizeof(avail); in sof_ipc4_mtrace_dfs_read()
231 dev_dbg(sdev->dev, in sof_ipc4_mtrace_dfs_read()
233 core_data->id, read_ptr, write_ptr, avail); in sof_ipc4_mtrace_dfs_read()
241 avail - write_ptr); in sof_ipc4_mtrace_dfs_read()
245 (u8 *)(log_buffer) + avail - write_ptr, in sof_ipc4_mtrace_dfs_read()
250 ret = copy_to_user(buffer, &avail, sizeof(avail)); in sof_ipc4_mtrace_dfs_read()
252 return -EFAULT; in sof_ipc4_mtrace_dfs_read()
255 ret = copy_to_user(buffer + sizeof(avail), log_buffer, avail); in sof_ipc4_mtrace_dfs_read()
257 return -EFAULT; in sof_ipc4_mtrace_dfs_read()
262 read_ptr -= log_buffer_size; in sof_ipc4_mtrace_dfs_read()
263 sof_mailbox_write(sdev, core_data->slot_offset, &read_ptr, sizeof(read_ptr)); in sof_ipc4_mtrace_dfs_read()
266 if (priv->mtrace_state != SOF_MTRACE_DISABLED) in sof_ipc4_mtrace_dfs_read()
267 core_data->host_read_ptr = read_ptr; in sof_ipc4_mtrace_dfs_read()
270 * Ask for a new buffer from user space for the next chunk, not in sof_ipc4_mtrace_dfs_read()
280 struct sof_mtrace_core_data *core_data = inode->i_private; in sof_ipc4_mtrace_dfs_release()
282 debugfs_file_put(file->f_path.dentry); in sof_ipc4_mtrace_dfs_release()
284 mutex_lock(&core_data->buffer_lock); in sof_ipc4_mtrace_dfs_release()
285 kfree(core_data->log_buffer); in sof_ipc4_mtrace_dfs_release()
286 core_data->log_buffer = NULL; in sof_ipc4_mtrace_dfs_release()
287 mutex_unlock(&core_data->buffer_lock); in sof_ipc4_mtrace_dfs_release()
304 struct sof_mtrace_priv *priv = file->private_data; in sof_ipc4_priority_mask_dfs_read()
316 return -ENOMEM; in sof_ipc4_priority_mask_dfs_read()
320 remaining = 241 - offset; in sof_ipc4_priority_mask_dfs_read()
322 priv->state_info.logs_priorities_mask[i]); in sof_ipc4_priority_mask_dfs_read()
335 struct sof_mtrace_priv *priv = file->private_data; in sof_ipc4_priority_mask_dfs_write()
354 ret = -EINVAL; in sof_ipc4_priority_mask_dfs_write()
360 ret = -EINVAL; in sof_ipc4_priority_mask_dfs_write()
364 priv->state_info.logs_priorities_mask[id] = mask; in sof_ipc4_priority_mask_dfs_write()
383 struct sof_mtrace_priv *priv = sdev->fw_trace_data; in mtrace_debugfs_create()
388 dfs_root = debugfs_create_dir("mtrace", sdev->debugfs_root); in mtrace_debugfs_create()
394 &priv->state_info.aging_timer_period); in mtrace_debugfs_create()
396 &priv->state_info.fifo_full_timer_period); in mtrace_debugfs_create()
401 for (i = 0; i < sdev->num_cores; i++) { in mtrace_debugfs_create()
403 debugfs_create_file(dfs_name, 0444, dfs_root, &priv->cores[i], in mtrace_debugfs_create()
412 struct sof_mtrace_priv *priv = sdev->fw_trace_data; in ipc4_mtrace_enable()
413 const struct sof_ipc_ops *iops = sdev->ipc->ops; in ipc4_mtrace_enable()
418 if (priv->mtrace_state != SOF_MTRACE_DISABLED) in ipc4_mtrace_enable()
425 msg.extension = SOF_IPC4_MOD_EXT_MSG_PARAM_ID(SOF_IPC4_FW_PARAM_SYSTEM_TIME); in ipc4_mtrace_enable()
435 ret = iops->set_get_data(sdev, &msg, msg.data_size, true); in ipc4_mtrace_enable()
439 msg.extension = SOF_IPC4_MOD_EXT_MSG_PARAM_ID(SOF_IPC4_FW_PARAM_ENABLE_LOGS); in ipc4_mtrace_enable()
441 priv->state_info.enable = 1; in ipc4_mtrace_enable()
443 msg.data_size = sizeof(priv->state_info); in ipc4_mtrace_enable()
444 msg.data_ptr = &priv->state_info; in ipc4_mtrace_enable()
446 priv->mtrace_state = SOF_MTRACE_INITIALIZING; in ipc4_mtrace_enable()
447 ret = iops->set_get_data(sdev, &msg, msg.data_size, true); in ipc4_mtrace_enable()
449 priv->mtrace_state = SOF_MTRACE_DISABLED; in ipc4_mtrace_enable()
453 priv->mtrace_state = SOF_MTRACE_ENABLED; in ipc4_mtrace_enable()
460 struct sof_mtrace_priv *priv = sdev->fw_trace_data; in ipc4_mtrace_disable()
461 const struct sof_ipc_ops *iops = sdev->ipc->ops; in ipc4_mtrace_disable()
465 if (priv->mtrace_state == SOF_MTRACE_DISABLED) in ipc4_mtrace_disable()
472 msg.extension = SOF_IPC4_MOD_EXT_MSG_PARAM_ID(SOF_IPC4_FW_PARAM_ENABLE_LOGS); in ipc4_mtrace_disable()
474 priv->state_info.enable = 0; in ipc4_mtrace_disable()
476 msg.data_size = sizeof(priv->state_info); in ipc4_mtrace_disable()
477 msg.data_ptr = &priv->state_info; in ipc4_mtrace_disable()
478 iops->set_get_data(sdev, &msg, msg.data_size, true); in ipc4_mtrace_disable()
480 priv->mtrace_state = SOF_MTRACE_DISABLED; in ipc4_mtrace_disable()
482 for (i = 0; i < sdev->num_cores; i++) { in ipc4_mtrace_disable()
483 struct sof_mtrace_core_data *core_data = &priv->cores[i]; in ipc4_mtrace_disable()
485 core_data->host_read_ptr = 0; in ipc4_mtrace_disable()
486 core_data->dsp_write_ptr = 0; in ipc4_mtrace_disable()
487 wake_up(&core_data->trace_sleep); in ipc4_mtrace_disable()
499 struct sof_mtrace_priv *priv = sdev->fw_trace_data; in sof_mtrace_find_core_slots()
506 slot_desc_type_offset = sdev->debug_box.offset; in sof_mtrace_find_core_slots()
513 if (core >= sdev->num_cores) { in sof_mtrace_find_core_slots()
514 dev_dbg(sdev->dev, "core%u is invalid for slot%d\n", in sof_mtrace_find_core_slots()
519 core_data = &priv->cores[core]; in sof_mtrace_find_core_slots()
526 core_data->slot_offset = sdev->debug_box.offset; in sof_mtrace_find_core_slots()
527 core_data->slot_offset += SOF_IPC4_DEBUG_SLOT_SIZE * (i + 1); in sof_mtrace_find_core_slots()
528 dev_dbg(sdev->dev, "slot%d is used for core%u\n", i, core); in sof_mtrace_find_core_slots()
529 if (core_data->delayed_pos_update) { in sof_mtrace_find_core_slots()
531 core_data->delayed_pos_update = false; in sof_mtrace_find_core_slots()
534 dev_dbg(sdev->dev, "slot%d is not a log slot (%#x)\n", i, type); in sof_mtrace_find_core_slots()
541 struct sof_ipc4_fw_data *ipc4_data = sdev->private; in ipc4_mtrace_init()
545 if (sdev->fw_trace_data) { in ipc4_mtrace_init()
546 dev_err(sdev->dev, "fw_trace_data has been already allocated\n"); in ipc4_mtrace_init()
547 return -EBUSY; in ipc4_mtrace_init()
550 if (!ipc4_data->mtrace_log_bytes || in ipc4_mtrace_init()
551 ipc4_data->mtrace_type != SOF_IPC4_MTRACE_INTEL_CAVS_2) { in ipc4_mtrace_init()
552 sdev->fw_trace_is_supported = false; in ipc4_mtrace_init()
556 priv = devm_kzalloc(sdev->dev, struct_size(priv, cores, sdev->num_cores), in ipc4_mtrace_init()
559 return -ENOMEM; in ipc4_mtrace_init()
561 sdev->fw_trace_data = priv; in ipc4_mtrace_init()
564 priv->state_info.aging_timer_period = DEFAULT_AGING_TIMER_PERIOD_MS; in ipc4_mtrace_init()
565 priv->state_info.fifo_full_timer_period = DEFAULT_FIFO_FULL_TIMER_PERIOD_MS; in ipc4_mtrace_init()
567 priv->state_info.logs_priorities_mask[0] = DEFAULT_LOGS_PRIORITIES_MASK; in ipc4_mtrace_init()
569 for (i = 0; i < sdev->num_cores; i++) { in ipc4_mtrace_init()
570 struct sof_mtrace_core_data *core_data = &priv->cores[i]; in ipc4_mtrace_init()
572 init_waitqueue_head(&core_data->trace_sleep); in ipc4_mtrace_init()
573 mutex_init(&core_data->buffer_lock); in ipc4_mtrace_init()
574 core_data->sdev = sdev; in ipc4_mtrace_init()
575 core_data->id = i; in ipc4_mtrace_init()
584 sdev->fw_trace_is_supported = false; in ipc4_mtrace_init()
585 dev_dbg(sdev->dev, "initialization failed, fw tracing is disabled\n"); in ipc4_mtrace_init()
607 for (i = 0; i < sdev->num_cores; i++) in sof_ipc4_mtrace_update_pos_all_cores()
615 struct sof_mtrace_priv *priv = sdev->fw_trace_data; in sof_ipc4_mtrace_update_pos()
618 if (!sdev->fw_trace_is_supported || in sof_ipc4_mtrace_update_pos()
619 priv->mtrace_state == SOF_MTRACE_DISABLED) in sof_ipc4_mtrace_update_pos()
622 if (core >= sdev->num_cores) in sof_ipc4_mtrace_update_pos()
623 return -EINVAL; in sof_ipc4_mtrace_update_pos()
625 core_data = &priv->cores[core]; in sof_ipc4_mtrace_update_pos()
627 if (core_data->slot_offset == SOF_IPC4_INVALID_SLOT_OFFSET) { in sof_ipc4_mtrace_update_pos()
628 core_data->delayed_pos_update = true; in sof_ipc4_mtrace_update_pos()
633 sof_mailbox_read(sdev, core_data->slot_offset + sizeof(u32), in sof_ipc4_mtrace_update_pos()
634 &core_data->dsp_write_ptr, 4); in sof_ipc4_mtrace_update_pos()
635 core_data->dsp_write_ptr -= core_data->dsp_write_ptr % 4; in sof_ipc4_mtrace_update_pos()
638 dev_dbg(sdev->dev, "core%d, host read: %#x, dsp write: %#x", in sof_ipc4_mtrace_update_pos()
639 core, core_data->host_read_ptr, core_data->dsp_write_ptr); in sof_ipc4_mtrace_update_pos()
641 wake_up(&core_data->trace_sleep); in sof_ipc4_mtrace_update_pos()
650 * messages anymore, so check the log buffer status on all in ipc4_mtrace_fw_crashed()