Skip to content
Merged
8 changes: 8 additions & 0 deletions include/sound/sof.h
Original file line numberDiff line numberDiff line change
Expand Up@@ -39,6 +39,14 @@ enum sof_fw_state {
SOF_FW_CRASHED,
};

/* DSP power states */
Comment thread
plbossart marked this conversation as resolved.
enum sof_dsp_power_states {
SOF_DSP_PM_D0,
SOF_DSP_PM_D1,
SOF_DSP_PM_D2,
SOF_DSP_PM_D3,
};

Comment thread
plbossart marked this conversation as resolved.
/*
* SOF Platform data.
*/
Expand Down
33 changes: 26 additions & 7 deletions sound/soc/sof/Kconfig
Original file line numberDiff line numberDiff line change
Expand Up@@ -53,13 +53,21 @@ config SND_SOC_SOF_COMPRESS
select SND_SOC_COMPRESS

config SND_SOC_SOF_DEBUG_PROBES
bool "SOF enable data probing"
tristate
select SND_SOC_SOF_CLIENT
select SND_SOC_COMPRESS
help
This option enables the data probing feature that can be used to
gather data directly from specific points of the audio pipeline.
Say Y if you want to enable probes.
If unsure, select "N".
This option is not user-selectable but automagically handled by
'select' statements at a higher level.

config SND_SOC_SOF_CLIENT
tristate
select AUXILIARY_BUS
help
This option is not user-selectable but automagically handled by
'select' statements at a higher level.

config SND_SOC_SOF_DEVELOPER_SUPPORT
bool "SOF developer options support"
Expand DownExpand Up@@ -187,15 +195,26 @@ config SND_SOC_SOF_DEBUG_ENABLE_FIRMWARE_TRACE
If unsure, select "N".

config SND_SOC_SOF_DEBUG_IPC_FLOOD_TEST
bool "SOF enable IPC flood test"
tristate "SOF enable IPC flood test"
select SND_SOC_SOF_CLIENT
help
This option enables the IPC flood test which can be used to flood
the DSP with test IPCs and gather stats about response times.
This option enables a separate client device for IPC flood test
which can be used to flood the DSP with test IPCs and gather stats
about response times.
Say Y if you want to enable IPC flood test.
If unsure, select "N".

config SND_SOC_SOF_DEBUG_IPC_FLOOD_TEST_NUM
int "Number of IPC flood test clients"
range 1 32
default 2
depends on SND_SOC_SOF_DEBUG_IPC_FLOOD_TEST
help
Select the number of IPC flood test clients to be created.

config SND_SOC_SOF_DEBUG_IPC_MSG_INJECTOR
bool "SOF enable IPC message injector"
tristate "SOF enable IPC message injector"
select SND_SOC_SOF_CLIENT
help
This option enables the IPC message injector which can be used to send
crafted IPC messages to the DSP to test its robustness.
Expand Down
15 changes: 13 additions & 2 deletions sound/soc/sof/Makefile
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,36 @@
# SPDX-License-Identifier: (GPL-2.0-only OR BSD-3-Clause)

snd-sof-objs := core.o ops.o loader.o ipc.o pcm.o pm.o debug.o topology.o\
control.o trace.o utils.o sof-audio.o stream-ipc.o ipc4.o
control.o trace.o iomem-utils.o sof-audio.o stream-ipc.o ipc4.o
Comment thread
plbossart marked this conversation as resolved.
snd-sof-$(CONFIG_SND_SOC_SOF_CLIENT) += sof-client.o

snd-sof-$(CONFIG_SND_SOC_SOF_DEBUG_PROBES) += sof-probes.o
snd-sof-$(CONFIG_SND_SOC_SOF_COMPRESS) += compress.o

snd-sof-pci-objs := sof-pci-dev.o
snd-sof-acpi-objs := sof-acpi-dev.o
snd-sof-of-objs := sof-of-dev.o

snd-sof-ipc-flood-test-objs := sof-client-ipc-flood-test.o
snd-sof-ipc-msg-injector-objs := sof-client-ipc-msg-injector.o
snd-sof-probes-objs := sof-client-probes.o

snd-sof-nocodec-objs := nocodec.o

snd-sof-utils-objs := sof-utils.o

obj-$(CONFIG_SND_SOC_SOF) += snd-sof.o
obj-$(CONFIG_SND_SOC_SOF_NOCODEC) += snd-sof-nocodec.o

obj-$(CONFIG_SND_SOC_SOF) += snd-sof-utils.o

obj-$(CONFIG_SND_SOC_SOF_ACPI_DEV) += snd-sof-acpi.o
obj-$(CONFIG_SND_SOC_SOF_OF_DEV) += snd-sof-of.o
obj-$(CONFIG_SND_SOC_SOF_PCI_DEV) += snd-sof-pci.o

obj-$(CONFIG_SND_SOC_SOF_DEBUG_IPC_FLOOD_TEST) += snd-sof-ipc-flood-test.o
obj-$(CONFIG_SND_SOC_SOF_DEBUG_IPC_MSG_INJECTOR) += snd-sof-ipc-msg-injector.o
obj-$(CONFIG_SND_SOC_SOF_DEBUG_PROBES) += snd-sof-probes.o

obj-$(CONFIG_SND_SOC_SOF_INTEL_TOPLEVEL) += intel/
obj-$(CONFIG_SND_SOC_SOF_IMX_TOPLEVEL) += imx/
obj-$(CONFIG_SND_SOC_SOF_AMD_TOPLEVEL) += amd/
Expand Down
50 changes: 43 additions & 7 deletions sound/soc/sof/core.c
Original file line numberDiff line numberDiff line change
Expand Up@@ -14,9 +14,6 @@
#include <sound/sof.h>
#include "sof-priv.h"
#include "ops.h"
#if IS_ENABLED(CONFIG_SND_SOC_SOF_DEBUG_PROBES)
#include "sof-probes.h"
#endif

/* see SOF_DBG_ flags */
static int sof_core_debug = IS_ENABLED(CONFIG_SND_SOC_SOF_DEBUG_ENABLE_FIRMWARE_TRACE);
Expand DownExpand Up@@ -122,6 +119,27 @@ void sof_print_oops_and_stack(struct snd_sof_dev *sdev, const char *level,
}
EXPORT_SYMBOL(sof_print_oops_and_stack);

/* Helper to manage DSP state */
void sof_set_fw_state(struct snd_sof_dev *sdev, enum sof_fw_state new_state)
{
if (sdev->fw_state == new_state)
return;

dev_dbg(sdev->dev, "fw_state change: %d -> %d\n", sdev->fw_state, new_state);
sdev->fw_state = new_state;

switch (new_state) {
case SOF_FW_BOOT_NOT_STARTED:
case SOF_FW_BOOT_COMPLETE:
case SOF_FW_CRASHED:
sof_client_fw_state_dispatcher(sdev);
fallthrough;
default:
break;
Comment thread
plbossart marked this conversation as resolved.
}
}
EXPORT_SYMBOL(sof_set_fw_state);

/*
* FW Boot State Transition Diagram
*
Expand DownExpand Up@@ -266,6 +284,12 @@ static int sof_probe_continue(struct snd_sof_dev *sdev)
goto fw_trace_err;
}

ret = sof_register_clients(sdev);
if (ret < 0) {
dev_err(sdev->dev, "failed to register clients %d\n", ret);
goto sof_machine_err;
}

/*
* Some platforms in SOF, ex: BYT, may not have their platform PM
* callbacks set. Increment the usage count so as to
Expand All@@ -281,6 +305,8 @@ static int sof_probe_continue(struct snd_sof_dev *sdev)

return 0;

sof_machine_err:
snd_sof_machine_unregister(sdev, plat_data);
fw_trace_err:
snd_sof_free_trace(sdev);
fw_run_err:
Expand DownExpand Up@@ -329,10 +355,6 @@ int snd_sof_device_probe(struct device *dev, struct snd_sof_pdata *plat_data)

sdev->pdata = plat_data;
sdev->first_boot = true;
sof_set_fw_state(sdev, SOF_FW_BOOT_NOT_STARTED);
#if IS_ENABLED(CONFIG_SND_SOC_SOF_DEBUG_PROBES)
sdev->extractor_stream_tag = SOF_PROBE_INVALID_NODE_ID;
#endif
dev_set_drvdata(dev, sdev);

/* check all mandatory ops */
Expand All@@ -350,9 +372,14 @@ int snd_sof_device_probe(struct device *dev, struct snd_sof_pdata *plat_data)
INIT_LIST_HEAD(&sdev->widget_list);
INIT_LIST_HEAD(&sdev->dai_list);
INIT_LIST_HEAD(&sdev->route_list);
INIT_LIST_HEAD(&sdev->ipc_client_list);
INIT_LIST_HEAD(&sdev->ipc_rx_handler_list);
INIT_LIST_HEAD(&sdev->fw_state_handler_list);
spin_lock_init(&sdev->ipc_lock);
spin_lock_init(&sdev->hw_lock);
mutex_init(&sdev->power_state_access);
mutex_init(&sdev->ipc_client_mutex);
mutex_init(&sdev->client_event_handler_mutex);

/* set default timeouts if none provided */
if (plat_data->desc->ipc_timeout == 0)
Expand All@@ -364,6 +391,8 @@ int snd_sof_device_probe(struct device *dev, struct snd_sof_pdata *plat_data)
else
sdev->boot_timeout = plat_data->desc->boot_timeout;

sof_set_fw_state(sdev, SOF_FW_BOOT_NOT_STARTED);

if (IS_ENABLED(CONFIG_SND_SOC_SOF_PROBE_WORK_QUEUE)) {
INIT_WORK(&sdev->probe_work, sof_probe_work);
schedule_work(&sdev->probe_work);
Expand DownExpand Up@@ -391,6 +420,12 @@ int snd_sof_device_remove(struct device *dev)
if (IS_ENABLED(CONFIG_SND_SOC_SOF_PROBE_WORK_QUEUE))
cancel_work_sync(&sdev->probe_work);

/*
* Unregister any registered client device first before IPC and debugfs
* to allow client drivers to be removed cleanly
*/
sof_unregister_clients(sdev);

/*
* Unregister machine driver. This will unbind the snd_card which
* will remove the component driver and unload the topology
Expand DownExpand Up@@ -443,3 +478,4 @@ MODULE_AUTHOR("Liam Girdwood");
MODULE_DESCRIPTION("Sound Open Firmware (SOF) Core");
MODULE_LICENSE("Dual BSD/GPL");
MODULE_ALIAS("platform:sof-audio");
MODULE_IMPORT_NS(SND_SOC_SOF_CLIENT);
Loading