Skip to content
Permalink
Browse files
ASOC: SOF: partition DSP ops in more detail
Add new abstraction to allow for multiple types of IPC for each
platform. This is a preparation step for the Intel IPCv4 which uses a
different firmware protocol, firmware handling and trace.

Signed-off-by: Pierre-Louis Bossart <pierre-louis.bossart@linux.intel.com>
  • Loading branch information
plbossart committed Jan 20, 2022
1 parent c8b33ee commit df9d3c13b1cfafc274d7a669915ed69d347e6785
Show file tree
Hide file tree
Showing 17 changed files with 364 additions and 212 deletions.
@@ -284,7 +284,7 @@ static irqreturn_t acp_irq_thread(int irq, void *context)

val = snd_sof_dsp_read(sdev, ACP_DSP_BAR, ACP_DSP_SW_INTR_STAT);
if (val & ACP_DSP_TO_HOST_IRQ) {
sof_ops(sdev)->irq_thread(irq, sdev);
sof_dsp_ipc_ops(sdev)->irq_thread(irq, sdev);
val |= ACP_DSP_TO_HOST_IRQ;
snd_sof_dsp_write(sdev, ACP_DSP_BAR, ACP_DSP_SW_INTR_STAT, val);
return IRQ_HANDLED;
@@ -122,8 +122,39 @@ static struct snd_soc_acpi_mach *amd_sof_machine_select(struct snd_sof_dev *sdev
return mach;
}

static const struct snd_sof_dsp_ipc_ops sof_renoir_ipc_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
.send_msg = acp_sof_ipc_send_msg,
.ipc_msg_data = acp_sof_ipc_msg_data,
.irq_thread = acp_sof_ipc_irq_thread,
.fw_ready = sof_fw_ready,
},
};

static const struct snd_sof_dsp_fw_ops sof_renoir_fw_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* Module loading */
.load_module = snd_sof_parse_module_memcpy,

.load_firmware = snd_sof_load_firmware_memcpy,
},
};

static const struct snd_sof_dsp_trace_ops sof_renoir_trace_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* Trace Logger */
.trace_init = acp_sof_trace_init,
.trace_release = acp_sof_trace_release,
},
};

/* AMD Renoir DSP ops */
const struct snd_sof_dsp_ops sof_renoir_ops = {
/* lower-level abstraction */
.ipc_ops = sof_renoir_ipc_ops,
.fw_ops = sof_renoir_fw_ops,
.trace_ops = sof_renoir_trace_ops,

/* probe and remove */
.probe = amd_sof_acp_probe,
.remove = amd_sof_acp_remove,
@@ -136,23 +167,15 @@ const struct snd_sof_dsp_ops sof_renoir_ops = {
.block_read = acp_dsp_block_read,
.block_write = acp_dsp_block_write,

/* Module loading */
.load_module = snd_sof_parse_module_memcpy,

/*Firmware loading */
.load_firmware = snd_sof_load_firmware_memcpy,
.pre_fw_run = acp_dsp_pre_fw_run,
.get_bar_index = acp_get_bar_index,

/* DSP core boot */
.run = acp_sof_dsp_run,

/*IPC */
.send_msg = acp_sof_ipc_send_msg,
.ipc_msg_data = acp_sof_ipc_msg_data,
.get_mailbox_offset = acp_sof_ipc_get_mailbox_offset,
.irq_thread = acp_sof_ipc_irq_thread,
.fw_ready = sof_fw_ready,

/* DAI drivers */
.drv = renoir_sof_dai,
@@ -174,9 +197,6 @@ const struct snd_sof_dsp_ops sof_renoir_ops = {
.machine_register = sof_machine_register,
.machine_unregister = sof_machine_unregister,

/* Trace Logger */
.trace_init = acp_sof_trace_init,
.trace_release = acp_sof_trace_release,
};
EXPORT_SYMBOL(sof_renoir_ops);

@@ -360,8 +360,9 @@ int snd_sof_device_probe(struct device *dev, struct snd_sof_pdata *plat_data)
/* check all mandatory ops */
if (!sof_ops(sdev) || !sof_ops(sdev)->probe || !sof_ops(sdev)->run ||
!sof_ops(sdev)->block_read || !sof_ops(sdev)->block_write ||
!sof_ops(sdev)->send_msg || !sof_ops(sdev)->load_firmware ||
!sof_ops(sdev)->ipc_msg_data || !sof_ops(sdev)->fw_ready) {
!sof_dsp_ipc_ops(sdev) || !sof_dsp_fw_ops(sdev) ||
!sof_dsp_ipc_ops(sdev)->send_msg || !sof_dsp_fw_ops(sdev)->load_firmware ||
!sof_dsp_ipc_ops(sdev)->ipc_msg_data || !sof_dsp_ipc_ops(sdev)->fw_ready) {
dev_err(dev, "error: missing mandatory ops\n");
return -EINVAL;
}
@@ -420,9 +420,9 @@ EXPORT_SYMBOL(snd_sof_dsp_dbg_dump);

static void snd_sof_ipc_dump(struct snd_sof_dev *sdev)
{
if (sof_ops(sdev)->ipc_dump && !sdev->ipc_dump_printed) {
if (sof_dsp_ipc_ops(sdev) && sof_dsp_ipc_ops(sdev)->ipc_dump && !sdev->ipc_dump_printed) {
dev_err(sdev->dev, "------------[ IPC dump start ]------------\n");
sof_ops(sdev)->ipc_dump(sdev);
sof_dsp_ipc_ops(sdev)->ipc_dump(sdev);
dev_err(sdev->dev, "------------[ IPC dump end ]------------\n");
if (!sof_debug_check_flag(SOF_DBG_PRINT_ALL_DUMPS))
sdev->ipc_dump_printed = true;
@@ -25,8 +25,48 @@ static const struct snd_sof_debugfs_map apl_dsp_debugfs[] = {
{"dsp", HDA_DSP_BAR, 0, 0x10000, SOF_DEBUGFS_ACCESS_ALWAYS},
};

static const struct snd_sof_dsp_ipc_ops sof_apl_ipc_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* doorbell */
.irq_thread = hda_dsp_ipc_irq_thread,

/* ipc */
.send_msg = hda_dsp_ipc_send_msg,
.fw_ready = sof_fw_ready,

.set_stream_data_offset = hda_set_stream_data_offset,
.ipc_msg_data = hda_ipc_msg_data,

.ipc_dump = hda_ipc_dump,
},
};

static const struct snd_sof_dsp_fw_ops sof_apl_fw_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* firmware loading */
.load_firmware = snd_sof_load_firmware_raw,

/* parse platform specific extended manifest */
.parse_platform_ext_manifest = hda_dsp_ext_man_get_cavs_config_data,
},
};

static const struct snd_sof_dsp_trace_ops sof_apl_trace_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* trace callback */
.trace_init = hda_dsp_trace_init,
.trace_release = hda_dsp_trace_release,
.trace_trigger = hda_dsp_trace_trigger,
},
};

/* apollolake ops */
const struct snd_sof_dsp_ops sof_apl_ops = {
/* lower-level abstraction */
.ipc_ops = sof_apl_ipc_ops,
.fw_ops = sof_apl_fw_ops,
.trace_ops = sof_apl_trace_ops,

/* probe/remove/shutdown */
.probe = hda_dsp_probe,
.remove = hda_dsp_remove,
@@ -46,18 +86,9 @@ const struct snd_sof_dsp_ops sof_apl_ops = {
.mailbox_read = sof_mailbox_read,
.mailbox_write = sof_mailbox_write,

/* doorbell */
.irq_thread = hda_dsp_ipc_irq_thread,

/* ipc */
.send_msg = hda_dsp_ipc_send_msg,
.fw_ready = sof_fw_ready,
.get_mailbox_offset = hda_dsp_ipc_get_mailbox_offset,
.get_window_offset = hda_dsp_ipc_get_window_offset,

.ipc_msg_data = hda_ipc_msg_data,
.set_stream_data_offset = hda_set_stream_data_offset,

/* machine driver */
.machine_select = hda_machine_select,
.machine_register = sof_machine_register,
@@ -68,7 +99,6 @@ const struct snd_sof_dsp_ops sof_apl_ops = {
.debug_map = apl_dsp_debugfs,
.debug_map_count = ARRAY_SIZE(apl_dsp_debugfs),
.dbg_dump = hda_dsp_dump,
.ipc_dump = hda_ipc_dump,
.debugfs_add_region_item = snd_sof_debugfs_add_region_item_iomem,

/* stream callbacks */
@@ -80,27 +110,16 @@ const struct snd_sof_dsp_ops sof_apl_ops = {
.pcm_pointer = hda_dsp_pcm_pointer,
.pcm_ack = hda_dsp_pcm_ack,

/* firmware loading */
.load_firmware = snd_sof_load_firmware_raw,

/* firmware run */
.run = hda_dsp_cl_boot_firmware,

/* pre/post fw run */
.pre_fw_run = hda_dsp_pre_fw_run,
.post_fw_run = hda_dsp_post_fw_run,

/* parse platform specific extended manifest */
.parse_platform_ext_manifest = hda_dsp_ext_man_get_cavs_config_data,

/* dsp core get/put */
.core_get = hda_dsp_core_get,

/* trace callback */
.trace_init = hda_dsp_trace_init,
.trace_release = hda_dsp_trace_release,
.trace_trigger = hda_dsp_trace_trigger,

/* client ops */
.register_ipc_clients = hda_register_clients,
.unregister_ipc_clients = hda_unregister_clients,
@@ -566,9 +566,34 @@ static struct snd_soc_dai_driver bdw_dai[] = {
},
};

static const struct snd_sof_dsp_ipc_ops sof_bdw_ipc_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* ipc */
.send_msg = bdw_send_msg,
.fw_ready = sof_fw_ready,

.ipc_msg_data = sof_ipc_msg_data,
.set_stream_data_offset = sof_set_stream_data_offset,
},
};

static const struct snd_sof_dsp_fw_ops sof_bdw_fw_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* module loading */
.load_module = snd_sof_parse_module_memcpy,

/* Firmware loading */
.load_firmware = snd_sof_load_firmware_memcpy,
},
};

/* broadwell ops */
static const struct snd_sof_dsp_ops sof_bdw_ops = {
/*Device init */
/* lower-level abstraction */
.ipc_ops = sof_bdw_ipc_ops,
.fw_ops = sof_bdw_fw_ops,

/* Device init */
.probe = bdw_probe,

/* DSP Core Control */
@@ -589,15 +614,9 @@ static const struct snd_sof_dsp_ops sof_bdw_ops = {
.mailbox_read = sof_mailbox_read,
.mailbox_write = sof_mailbox_write,

/* ipc */
.send_msg = bdw_send_msg,
.fw_ready = sof_fw_ready,
.get_mailbox_offset = bdw_get_mailbox_offset,
.get_window_offset = bdw_get_window_offset,

.ipc_msg_data = sof_ipc_msg_data,
.set_stream_data_offset = sof_set_stream_data_offset,

/* machine driver */
.machine_select = bdw_machine_select,
.machine_register = sof_machine_register,
@@ -614,12 +633,6 @@ static const struct snd_sof_dsp_ops sof_bdw_ops = {
.pcm_open = sof_stream_pcm_open,
.pcm_close = sof_stream_pcm_close,

/* Module loading */
.load_module = snd_sof_parse_module_memcpy,

/*Firmware loading */
.load_firmware = snd_sof_load_firmware_memcpy,

/* DAI drivers */
.drv = bdw_dai,
.num_drv = ARRAY_SIZE(bdw_dai),
@@ -215,8 +215,37 @@ static int byt_acpi_probe(struct snd_sof_dev *sdev)
return ret;
}

static const struct snd_sof_dsp_ipc_ops sof_byt_ipc_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* doorbell */
.irq_handler = atom_irq_handler,
.irq_thread = atom_irq_thread,

/* ipc */
.send_msg = atom_send_msg,
.fw_ready = sof_fw_ready,

.ipc_msg_data = sof_ipc_msg_data,
.set_stream_data_offset = sof_set_stream_data_offset,
},
};

static const struct snd_sof_dsp_fw_ops sof_byt_fw_ops[SOF_IPC_TYPE_COUNT] = {
[SOF_IPC] = {
/* module loading */
.load_module = snd_sof_parse_module_memcpy,

/* Firmware loading */
.load_firmware = snd_sof_load_firmware_memcpy,
},
};

/* baytrail ops */
static const struct snd_sof_dsp_ops sof_byt_ops = {
/* lower-level abstraction */
.ipc_ops = sof_byt_ipc_ops,
.fw_ops = sof_byt_fw_ops,

/* device init */
.probe = byt_acpi_probe,
.remove = byt_remove,
@@ -239,19 +268,9 @@ static const struct snd_sof_dsp_ops sof_byt_ops = {
.mailbox_read = sof_mailbox_read,
.mailbox_write = sof_mailbox_write,

/* doorbell */
.irq_handler = atom_irq_handler,
.irq_thread = atom_irq_thread,

/* ipc */
.send_msg = atom_send_msg,
.fw_ready = sof_fw_ready,
.get_mailbox_offset = atom_get_mailbox_offset,
.get_window_offset = atom_get_window_offset,

.ipc_msg_data = sof_ipc_msg_data,
.set_stream_data_offset = sof_set_stream_data_offset,

/* machine driver */
.machine_select = atom_machine_select,
.machine_register = sof_machine_register,
@@ -268,12 +287,6 @@ static const struct snd_sof_dsp_ops sof_byt_ops = {
.pcm_open = sof_stream_pcm_open,
.pcm_close = sof_stream_pcm_close,

/* module loading */
.load_module = snd_sof_parse_module_memcpy,

/*Firmware loading */
.load_firmware = snd_sof_load_firmware_memcpy,

/* PM */
.suspend = byt_suspend,
.resume = byt_resume,
@@ -299,6 +312,10 @@ static const struct sof_intel_dsp_desc byt_chip_info = {

/* cherrytrail and braswell ops */
static const struct snd_sof_dsp_ops sof_cht_ops = {
/* lower-level abstraction */
.ipc_ops = sof_byt_ipc_ops,
.fw_ops = sof_byt_fw_ops,

/* device init */
.probe = byt_acpi_probe,
.remove = byt_remove,
@@ -321,19 +338,9 @@ static const struct snd_sof_dsp_ops sof_cht_ops = {
.mailbox_read = sof_mailbox_read,
.mailbox_write = sof_mailbox_write,

/* doorbell */
.irq_handler = atom_irq_handler,
.irq_thread = atom_irq_thread,

/* ipc */
.send_msg = atom_send_msg,
.fw_ready = sof_fw_ready,
.get_mailbox_offset = atom_get_mailbox_offset,
.get_window_offset = atom_get_window_offset,

.ipc_msg_data = sof_ipc_msg_data,
.set_stream_data_offset = sof_set_stream_data_offset,

/* machine driver */
.machine_select = atom_machine_select,
.machine_register = sof_machine_register,
@@ -350,12 +357,6 @@ static const struct snd_sof_dsp_ops sof_cht_ops = {
.pcm_open = sof_stream_pcm_open,
.pcm_close = sof_stream_pcm_close,

/* module loading */
.load_module = snd_sof_parse_module_memcpy,

/*Firmware loading */
.load_firmware = snd_sof_load_firmware_memcpy,

/* PM */
.suspend = byt_suspend,
.resume = byt_resume,

0 comments on commit df9d3c1

Please sign in to comment.