-
Notifications
You must be signed in to change notification settings - Fork 133
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
ASoC: SOF: file layout profile handling with fallback mechanism (take 3) #4331
ASoC: SOF: file layout profile handling with fallback mechanism (take 3) #4331
Conversation
I assume this is only the infra change. Can you show an example of how this new infra is to be used? (I do like how this looks but an example is still useful). |
@paulstelian97, sure! diff --git a/sound/soc/sof/intel/pci-tgl.c b/sound/soc/sof/intel/pci-tgl.c
index ca37ff1bbd2a..24dc3efce1ed 100644
--- a/sound/soc/sof/intel/pci-tgl.c
+++ b/sound/soc/sof/intel/pci-tgl.c
@@ -29,7 +29,7 @@ static const struct sof_dev_desc tgl_desc = {
.irqindex_host_ipc = -1,
.chip_info = &tgl_chip_info,
.ipc_supported_mask = BIT(SOF_IPC) | BIT(SOF_INTEL_IPC4),
- .ipc_default = SOF_IPC,
+ .ipc_default = SOF_INTEL_IPC4,
.dspless_mode_supported = true, /* Only supported for HDaudio */
.default_fw_path = {
[SOF_IPC] = "intel/sof",
Before this series we would fail if a file is not present at the time when we try to load it later in the boot sequence, but with this change we can detect it earlier and do the fallback. |
Hrm, why it is printing it twice twice in case of neither is there??? Oops. |
OK, fixed it and reworded to: "Supported default profiles" |
I definitely like this, what happens if a non-default type was requested via module parameter and it wasn't found? (or even if the default was requested by parameter). Would the fallback still happen or would it explicitly be disabled? I definitely have some interest in this as I actually have the migrating to IPC4 task (for i.MX platforms) in my backlog (no target version yet), this change definitely should help smooth out the transition. |
It works in the same way, the module parameter takes the place of the default ipc type and the same course of events will happen. |
d14d318
to
8c4237f
Compare
Changes since v1:
|
sound/soc/sof/fw-file-profile.c
Outdated
if (profile->fw_lib_path) | ||
dev_dbg(dev, " Firmware lib path: %s\n", profile->fw_lib_path); | ||
|
||
dev_dbg(dev, " Topology file: %s/%s\n", profile->tplg_path, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you please increase the log levels when logging the loaded files? To be honest this is something request_firmware()
itself should do (imagine that: a "bootloader" that does not even log what it boots) but I guess this is unlikely to happen any time soon.
Some more context in
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't think normal users care about this at all and just going to make the kernel log noisy for no benefit.
Adding a debugfs file would be a better solution if we need it (separate files or one file which prints the paths and names?)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Define "normal users". Anyone staring at kernel logs and not caring what firmware and configuration files are in use is seriously shooting themselves in the foot.
The kernel squeals "TAINTED" as soon as something is slightly out of the ordinary but somehow loading unknown files from random locations (/lib/firmware/updates/
,
/lib/firmware/UTS_RELEASE/
, etc.) does not deserve a word.
And please don't get me started on the (lack of) security for which logging is one of the most basic requirements.
make the kernel log noisy for no benefit.
In "normal" usage, files are loaded only ONCE per boot so this would be obviously not noisy at all.
It would be printed more often only when running a test like "kmod-unload-load" but then such logs become even more relevant.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK.
Let's make the path, name prints dev_info()
There is one thing I'm not happy about is this:
dev_dbg(dev, "Loadable file profile for ipc type %d:\n", profile->ipc_type);
Should it be simply:
dev_info(dev, "Firmware paths/files for ipc type %d:\n", profile->ipc_type);
Despite the fact the the topology is not really a firmware and the libraries are under a path, we don't know what will be loaded from there?
8c4237f
to
e951ce8
Compare
Changes since v2:
|
e951ce8
to
ff194f1
Compare
Changes since v8:
|
Well, this PR is described as preparing the future, but there's one shortcoming that was identified. If we do the support for libraries later, it adds a second dependency between firmware and kernel, so why not do the right thing now? |
So, we should deal with the libraries first? I don't see how we could facilitate vendor key use for Lenovo, Dell, HP, ASUS, etc in a default path. We would need a 'huge' match table to set different vendor directories and in some cases different directories per vendors depending on keys? This PR is just moving the path handling into core to a common location and the last patch adds support for moving back (and forth) in IPC version if files for the selected version were missing, but it only deals with default paths, custom paths are used as provided. The followup series does have the definition of the default paths moved to core, so there we really should think how we can do this. I was thinking of tplg token to tell the lib location, but the same tplg can be used on different vendor's device, so that is not good. |
@plbossart, I do want to keep this and the next PR 'simple' by not introducing ABI (as in file location) changes if possible. Having said that and after some time to think about the libraries, I think what might make sense is: -- default library path -- -- customer library path -- I have no idea how the customer path can be provided, but it would be used together with the 'core' lib path: Deployment might be an issue for distributions due to the shared path, but that can be tuned? I kind of like the idea to have the default path for libraries pointing to the firmware location (less hassle in code and documentation). We can move the discussion to some better place (sof-docs?) and settle the final places. FWIW, this PR and the next one pending will gave us quite a bit of flexibility on moving things around - given that the kernel have those patches - since we can declare different 'default' layouts for IPC versions to cover the past, present and future. Solely on this PR: this is not introducing anything new in paths or how they are provided, and yes, at the moment we use the same path 'patching' for the fw path and the fw library path: |
My only objection is that "fw_path_postfix" needs to be used for firmware only. We need a separate variable for libraries. How "fw_libs_path_postfix" is set for customers is something we debate in the future. The only thing we need to consider NOW is that the hardware allows for two separate keys, so we cannot keep assuming that we have a common key between firmware and libs. For example, we could test on Up Extreme with the firmware signed with the production key and the libraries signed with the community key. this should work (famous last words I know). |
I haven't looked at all the details, only followed these discussions from a distance. However I'm pretty sure one of the main purposes of loadable libraries is to allow them to be signed with a variety of keys. Not as some future improvement but from the moment they're supported. Does that mean libraries should be located in some key-specific directories? Does this require some "huge" vendor table? No idea but about time this gets designed.
+1. Prototype code is super useful, among others because it helps discover gaps. Burying major design choices at the bottom of very long PRs is not so good. -- |
bfd1cf7
to
cd6cf2d
Compare
Changes since v9:
|
SOFCI TEST |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM - except for one confusing function name, see below @ujfalusi
sound/soc/sof/fw-file-profile.c
Outdated
@@ -94,37 +201,122 @@ sof_file_profile_for_ipc_type(struct device *dev, | |||
return ret; | |||
} | |||
|
|||
static void sof_print_profile_info(struct device *dev, | |||
static void | |||
sof_missing_firmware_notification(struct snd_sof_dev *sdev, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit-pick: usually "firmware notification" means some sort of firmware-generated IPC is received by the host driver. This is not what this function does. I think this is a user notification, but that's confusing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK, I will find a better name for the function.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
sof_log_missing_firmware_file()
cd6cf2d
to
6fa3957
Compare
Move the sof_of_machine_select() function to sof-of-dev.c file and provide an inline stub in case of non OF builds. Signed-off-by: Peter Ujfalusi <[email protected]>
Relocate the machine handling functions from sof-audio.c to core.c to maintain code separation. While doing the move, drop the redundant IS_ERR_OR_NULL(plat_data->pdev_mach) check from sof_machine_unregister() Signed-off-by: Peter Ujfalusi <[email protected]>
Add a struct sof_loadable_file_profile which can be filled by platforms (sof-acpi-dev.c, sof-of-dev.c and sof-acpi-dev.c) to be able to use common, generic code to handle path customization. Signed-off-by: Peter Ujfalusi <[email protected]>
Store the default IPC type and the firmware and topology path overrides to ipc_file_profile_base Signed-off-by: Peter Ujfalusi <[email protected]>
Store the default IPC type and the firmware and topology path overrides to ipc_file_profile_base Signed-off-by: Peter Ujfalusi <[email protected]>
Store the default IPC type and the overrides to ipc_file_profile_base Signed-off-by: Peter Ujfalusi <[email protected]>
Use the information stored in ipc_file_profile_base by platforms to construct the paths, filenames that are going to be used to load the firmware and topology files. Signed-off-by: Peter Ujfalusi <[email protected]>
The core is now using the information from ipc_file_profile_base to create the paths for the loadable files, no need to set it in here anymore. Signed-off-by: Peter Ujfalusi <[email protected]>
The core is now using the information from ipc_file_profile_base to create the paths for the loadable files, no need to set it in here anymore. Signed-off-by: Peter Ujfalusi <[email protected]>
The core is now using the information from ipc_file_profile_base to create the paths for the loadable files, no need to set it in here anymore. Signed-off-by: Peter Ujfalusi <[email protected]>
Add sof_init_environment() as a helper function to contain path and ops initialization. Signed-off-by: Peter Ujfalusi <[email protected]>
Manage the ipc4_data allocation in code instead of devm since the ops_init might be called more than once due to IPC type fallback. Signed-off-by: Peter Ujfalusi <[email protected]>
… missing If a firmware file is missing for the selected IPC type then try to switch to other supported IPC type and check if that one can be used instead. If for example a platform is changed to IPC4 as default version but the given machine does not yet have the needed topology file created then we will fall back to IPC3 which should have all the needed files. Relocate the sof_init_environment() to be done at a later phase, in sof_probe_continue(). This will only have changes in behavior if CONFIG_SND_SOC_SOF_PROBE_WORK_QUEUE is enabled (Intel HDA platforms) by not failing the module probe, but it is not going to be different case compared to for example failed firmware booting or topology loading error. Signed-off-by: Peter Ujfalusi <[email protected]>
Changes since v10:
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks very nice @ujfalusi ! Can you check one mem alloc question inline?
base_profile->fw_path); | ||
else if (base_profile->fw_path_postfix) | ||
dev_dbg(dev, "Path postfix appended to default fw path: %s\n", | ||
base_profile->fw_path_postfix); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess this is intentionally either-or?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yes it is intentional, if the path is provided as kernel parameter then we don't change it, user must know what he/she is doing.
@@ -55,7 +55,7 @@ int sof_apl_ops_init(struct snd_sof_dev *sdev) | |||
if (sdev->pdata->ipc_type == SOF_IPC_TYPE_4) { | |||
struct sof_ipc4_fw_data *ipc4_data; | |||
|
|||
sdev->private = devm_kzalloc(sdev->dev, sizeof(*ipc4_data), GFP_KERNEL); | |||
sdev->private = kzalloc(sizeof(*ipc4_data), GFP_KERNEL); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm, should we have a kfree() in hda_ops_free() then?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
see the change in hda-dai.c in hda_ops_free()
;)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ack @ujfalusi not sure how I missed that , but indeed it's there.
@@ -55,7 +55,7 @@ int sof_apl_ops_init(struct snd_sof_dev *sdev) | |||
if (sdev->pdata->ipc_type == SOF_IPC_TYPE_4) { | |||
struct sof_ipc4_fw_data *ipc4_data; | |||
|
|||
sdev->private = devm_kzalloc(sdev->dev, sizeof(*ipc4_data), GFP_KERNEL); | |||
sdev->private = kzalloc(sizeof(*ipc4_data), GFP_KERNEL); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ack @ujfalusi not sure how I missed that , but indeed it's there.
Hi,
replaces #4309 (it is an iteration on the same idea, but significantly different to confuse GH, I think).
This series aims to add support fro IPC type fallback in case the default firmware file or the topology file is missing from the filesystem.
If a user requested firmware is loaded (via module parameter) then the IPC type is adjusted to match with the loaded firmware to make sure that we are looking for the matching topology file.
I'm moving all logic to core from sof-acpi/of/pci-dev files, moving also the
sof_machine_*
functions locally.The change is gradual, first I just move the path/name configuration, then changing the order of initialization to be able to query the topology file earlier, then when all information is available, we can do the file existence checks and fallback handling.