Re: [PATCH v6 05/45] drm/amd: Add a new helper for loading/validating microcode

2023-01-04 Thread Mario Limonciello

On 1/4/23 23:29, Lazar, Lijo wrote:



On 1/5/2023 10:53 AM, Mario Limonciello wrote:

On 1/4/23 23:07, Lazar, Lijo wrote:



On 1/5/2023 9:12 AM, Mario Limonciello wrote:

All microcode runs a basic validation after it's been loaded. Each
IP block as part of init will run both.

Introduce a wrapper for request_firmware and amdgpu_ucode_validate.
This wrapper will also remap any error codes from request_firmware
to -ENODEV.  This is so that early_init will fail if firmware couldn't
be loaded instead of the IP block being disabled.

Signed-off-by: Mario Limonciello 
---
v5->v6:
  * Fix argument to be ** not *
---
  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 36 
+++

  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h |  3 ++
  2 files changed, 39 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c

index eafcddce58d3..8ebfec12da87 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
@@ -1312,3 +1312,39 @@ void amdgpu_ucode_ip_version_decode(struct 
amdgpu_device *adev, int block_type,
  snprintf(ucode_prefix, len, "%s_%d_%d_%d", ip_name, maj, min, 
rev);

  }
+
+/*
+ * amdgpu_ucode_request - Fetch and validate amdgpu microcode
+ *
+ * @adev: amdgpu device
+ * @fw: pointer to load firmware to
+ * @fw_name: firmware to load
+ *
+ * This is a helper that will use request_firmware and 
amdgpu_ucode_validate
+ * to load and run basic validation on firmware. If the load fails, 
remap
+ * the error code to -ENODEV, so that early_init functions will 
fail to load.

+ */
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct 
firmware **fw,

+ const char *fw_name)
+{
+    int err = request_firmware(fw, fw_name, adev->dev);
+
+    if (err)
+    return -ENODEV;
+    err = amdgpu_ucode_validate(*fw);
+    if (err)
+    dev_dbg(adev->dev, "\"%s\" failed to validate\n", fw_name);
+


Missed this earlier. If validate fails, shouldn't this undo the 
request operation by calling release?


Actually that was original design, but there is one place in the 
codebase that expects that ucode validation can fail, and so leave the 
evaluate of error code and cleanup outside of helper.




I see. Does request_firmware assure that fw pointer be always NULL if it 
fails? Or should that be done here if request_ fails? In subsequent 
patches, I see clients calling release without checking what caused the 
failure.


Yes, according to docs 
(https://docs.kernel.org/next/driver-api/firmware/request_firmware.html#request-firmware-api-expected-driver-use)




Thanks,
Lijo



Thanks,
Lijo


+    return err;
+}
+
+/*
+ * amdgpu_ucode_release - Release firmware microcode
+ *
+ * @fw: pointer to firmware to release
+ */
+void amdgpu_ucode_release(const struct firmware **fw)
+{
+    release_firmware(*fw);
+    *fw = NULL;
+}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h

index 552e06929229..848579d4988b 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
@@ -544,6 +544,9 @@ void amdgpu_ucode_print_sdma_hdr(const struct 
common_firmware_header *hdr);
  void amdgpu_ucode_print_psp_hdr(const struct 
common_firmware_header *hdr);
  void amdgpu_ucode_print_gpu_info_hdr(const struct 
common_firmware_header *hdr);

  int amdgpu_ucode_validate(const struct firmware *fw);
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct 
firmware **fw,

+ const char *fw_name);
+void amdgpu_ucode_release(const struct firmware **fw);
  bool amdgpu_ucode_hdr_version(union amdgpu_firmware_header *hdr,
  uint16_t hdr_major, uint16_t hdr_minor);






Re: [PATCH v6 05/45] drm/amd: Add a new helper for loading/validating microcode

2023-01-04 Thread Lazar, Lijo




On 1/5/2023 10:53 AM, Mario Limonciello wrote:

On 1/4/23 23:07, Lazar, Lijo wrote:



On 1/5/2023 9:12 AM, Mario Limonciello wrote:

All microcode runs a basic validation after it's been loaded. Each
IP block as part of init will run both.

Introduce a wrapper for request_firmware and amdgpu_ucode_validate.
This wrapper will also remap any error codes from request_firmware
to -ENODEV.  This is so that early_init will fail if firmware couldn't
be loaded instead of the IP block being disabled.

Signed-off-by: Mario Limonciello 
---
v5->v6:
  * Fix argument to be ** not *
---
  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 36 +++
  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h |  3 ++
  2 files changed, 39 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c

index eafcddce58d3..8ebfec12da87 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
@@ -1312,3 +1312,39 @@ void amdgpu_ucode_ip_version_decode(struct 
amdgpu_device *adev, int block_type,
  snprintf(ucode_prefix, len, "%s_%d_%d_%d", ip_name, maj, min, 
rev);

  }
+
+/*
+ * amdgpu_ucode_request - Fetch and validate amdgpu microcode
+ *
+ * @adev: amdgpu device
+ * @fw: pointer to load firmware to
+ * @fw_name: firmware to load
+ *
+ * This is a helper that will use request_firmware and 
amdgpu_ucode_validate
+ * to load and run basic validation on firmware. If the load fails, 
remap
+ * the error code to -ENODEV, so that early_init functions will fail 
to load.

+ */
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct 
firmware **fw,

+ const char *fw_name)
+{
+    int err = request_firmware(fw, fw_name, adev->dev);
+
+    if (err)
+    return -ENODEV;
+    err = amdgpu_ucode_validate(*fw);
+    if (err)
+    dev_dbg(adev->dev, "\"%s\" failed to validate\n", fw_name);
+


Missed this earlier. If validate fails, shouldn't this undo the 
request operation by calling release?


Actually that was original design, but there is one place in the 
codebase that expects that ucode validation can fail, and so leave the 
evaluate of error code and cleanup outside of helper.




I see. Does request_firmware assure that fw pointer be always NULL if it 
fails? Or should that be done here if request_ fails? In subsequent 
patches, I see clients calling release without checking what caused the 
failure.


Thanks,
Lijo



Thanks,
Lijo


+    return err;
+}
+
+/*
+ * amdgpu_ucode_release - Release firmware microcode
+ *
+ * @fw: pointer to firmware to release
+ */
+void amdgpu_ucode_release(const struct firmware **fw)
+{
+    release_firmware(*fw);
+    *fw = NULL;
+}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h

index 552e06929229..848579d4988b 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
@@ -544,6 +544,9 @@ void amdgpu_ucode_print_sdma_hdr(const struct 
common_firmware_header *hdr);
  void amdgpu_ucode_print_psp_hdr(const struct common_firmware_header 
*hdr);
  void amdgpu_ucode_print_gpu_info_hdr(const struct 
common_firmware_header *hdr);

  int amdgpu_ucode_validate(const struct firmware *fw);
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct 
firmware **fw,

+ const char *fw_name);
+void amdgpu_ucode_release(const struct firmware **fw);
  bool amdgpu_ucode_hdr_version(union amdgpu_firmware_header *hdr,
  uint16_t hdr_major, uint16_t hdr_minor);




Re: [PATCH v6 05/45] drm/amd: Add a new helper for loading/validating microcode

2023-01-04 Thread Mario Limonciello

On 1/4/23 23:07, Lazar, Lijo wrote:



On 1/5/2023 9:12 AM, Mario Limonciello wrote:

All microcode runs a basic validation after it's been loaded. Each
IP block as part of init will run both.

Introduce a wrapper for request_firmware and amdgpu_ucode_validate.
This wrapper will also remap any error codes from request_firmware
to -ENODEV.  This is so that early_init will fail if firmware couldn't
be loaded instead of the IP block being disabled.

Signed-off-by: Mario Limonciello 
---
v5->v6:
  * Fix argument to be ** not *
---
  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 36 +++
  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h |  3 ++
  2 files changed, 39 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c

index eafcddce58d3..8ebfec12da87 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
@@ -1312,3 +1312,39 @@ void amdgpu_ucode_ip_version_decode(struct 
amdgpu_device *adev, int block_type,

  snprintf(ucode_prefix, len, "%s_%d_%d_%d", ip_name, maj, min, rev);
  }
+
+/*
+ * amdgpu_ucode_request - Fetch and validate amdgpu microcode
+ *
+ * @adev: amdgpu device
+ * @fw: pointer to load firmware to
+ * @fw_name: firmware to load
+ *
+ * This is a helper that will use request_firmware and 
amdgpu_ucode_validate
+ * to load and run basic validation on firmware. If the load fails, 
remap
+ * the error code to -ENODEV, so that early_init functions will fail 
to load.

+ */
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct 
firmware **fw,

+ const char *fw_name)
+{
+    int err = request_firmware(fw, fw_name, adev->dev);
+
+    if (err)
+    return -ENODEV;
+    err = amdgpu_ucode_validate(*fw);
+    if (err)
+    dev_dbg(adev->dev, "\"%s\" failed to validate\n", fw_name);
+


Missed this earlier. If validate fails, shouldn't this undo the request 
operation by calling release?


Actually that was original design, but there is one place in the 
codebase that expects that ucode validation can fail, and so leave the 
evaluate of error code and cleanup outside of helper.




Thanks,
Lijo


+    return err;
+}
+
+/*
+ * amdgpu_ucode_release - Release firmware microcode
+ *
+ * @fw: pointer to firmware to release
+ */
+void amdgpu_ucode_release(const struct firmware **fw)
+{
+    release_firmware(*fw);
+    *fw = NULL;
+}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h

index 552e06929229..848579d4988b 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
@@ -544,6 +544,9 @@ void amdgpu_ucode_print_sdma_hdr(const struct 
common_firmware_header *hdr);
  void amdgpu_ucode_print_psp_hdr(const struct common_firmware_header 
*hdr);
  void amdgpu_ucode_print_gpu_info_hdr(const struct 
common_firmware_header *hdr);

  int amdgpu_ucode_validate(const struct firmware *fw);
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct 
firmware **fw,

+ const char *fw_name);
+void amdgpu_ucode_release(const struct firmware **fw);
  bool amdgpu_ucode_hdr_version(union amdgpu_firmware_header *hdr,
  uint16_t hdr_major, uint16_t hdr_minor);




Re: [PATCH v6 05/45] drm/amd: Add a new helper for loading/validating microcode

2023-01-04 Thread Lazar, Lijo




On 1/5/2023 9:12 AM, Mario Limonciello wrote:

All microcode runs a basic validation after it's been loaded. Each
IP block as part of init will run both.

Introduce a wrapper for request_firmware and amdgpu_ucode_validate.
This wrapper will also remap any error codes from request_firmware
to -ENODEV.  This is so that early_init will fail if firmware couldn't
be loaded instead of the IP block being disabled.

Signed-off-by: Mario Limonciello 
---
v5->v6:
  * Fix argument to be ** not *
---
  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 36 +++
  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h |  3 ++
  2 files changed, 39 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
index eafcddce58d3..8ebfec12da87 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
@@ -1312,3 +1312,39 @@ void amdgpu_ucode_ip_version_decode(struct amdgpu_device 
*adev, int block_type,
  
  	snprintf(ucode_prefix, len, "%s_%d_%d_%d", ip_name, maj, min, rev);

  }
+
+/*
+ * amdgpu_ucode_request - Fetch and validate amdgpu microcode
+ *
+ * @adev: amdgpu device
+ * @fw: pointer to load firmware to
+ * @fw_name: firmware to load
+ *
+ * This is a helper that will use request_firmware and amdgpu_ucode_validate
+ * to load and run basic validation on firmware. If the load fails, remap
+ * the error code to -ENODEV, so that early_init functions will fail to load.
+ */
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
**fw,
+const char *fw_name)
+{
+   int err = request_firmware(fw, fw_name, adev->dev);
+
+   if (err)
+   return -ENODEV;
+   err = amdgpu_ucode_validate(*fw);
+   if (err)
+   dev_dbg(adev->dev, "\"%s\" failed to validate\n", fw_name);
+


Missed this earlier. If validate fails, shouldn't this undo the request 
operation by calling release?


Thanks,
Lijo


+   return err;
+}
+
+/*
+ * amdgpu_ucode_release - Release firmware microcode
+ *
+ * @fw: pointer to firmware to release
+ */
+void amdgpu_ucode_release(const struct firmware **fw)
+{
+   release_firmware(*fw);
+   *fw = NULL;
+}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
index 552e06929229..848579d4988b 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
@@ -544,6 +544,9 @@ void amdgpu_ucode_print_sdma_hdr(const struct 
common_firmware_header *hdr);
  void amdgpu_ucode_print_psp_hdr(const struct common_firmware_header *hdr);
  void amdgpu_ucode_print_gpu_info_hdr(const struct common_firmware_header 
*hdr);
  int amdgpu_ucode_validate(const struct firmware *fw);
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
**fw,
+const char *fw_name);
+void amdgpu_ucode_release(const struct firmware **fw);
  bool amdgpu_ucode_hdr_version(union amdgpu_firmware_header *hdr,
uint16_t hdr_major, uint16_t hdr_minor);
  


RE: [PATCH 2/2] drm/amd: update securedisplay_cmd to ta_securedisplay_cmd

2023-01-04 Thread Liu, Aaron
[AMD Official Use Only - General]

Squashed into one patch now.
Thanks Alex.

> -Original Message-
> From: Alex Deucher 
> Sent: Thursday, January 5, 2023 11:28 AM
> To: Liu, Aaron 
> Cc: amd-gfx@lists.freedesktop.org; Liu, HaoPing (Alan)
> ; Deucher, Alexander ;
> Xiao, Shane 
> Subject: Re: [PATCH 2/2] drm/amd: update securedisplay_cmd to
> ta_securedisplay_cmd
>
> These two patches should be squashed together to avoid breaking the build.
>
> Alex
>
> On Wed, Jan 4, 2023 at 8:04 PM Aaron Liu  wrote:
> >
> > This patch updates securedisplay_cmd to ta_securedisplay_cmd starting
> > from amd-ta_securedisplay-v27.00.00.08.
> >
> > Signed-off-by: Aaron Liu 
> > ---
> >  drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c   | 2 +-
> >  drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c | 8 
> >  drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h | 2 +-
> >  drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c | 2 +-
> >  4 files changed, 7 insertions(+), 7 deletions(-)
> >
> > diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
> > b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
> > index 0706afb11577..2bebda7de604 100644
> > --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
> > +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
> > @@ -1907,7 +1907,7 @@ int psp_rap_invoke(struct psp_context *psp,
> > uint32_t ta_cmd_id, enum ta_rap_stat  static int
> > psp_securedisplay_initialize(struct psp_context *psp)  {
> > int ret;
> > -   struct securedisplay_cmd *securedisplay_cmd;
> > +   struct ta_securedisplay_cmd *securedisplay_cmd;
> >
> > /*
> >  * TODO: bypass the initialize in sriov for now diff --git
> > a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
> > b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
> > index 2c1d82fc4c34..8ed0e073656f 100644
> > --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
> > +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
> > @@ -77,11 +77,11 @@ void psp_securedisplay_parse_resp_status(struct
> psp_context *psp,
> > }
> >  }
> >
> > -void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct
> > securedisplay_cmd **cmd,
> > +void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct
> > +ta_securedisplay_cmd **cmd,
> > enum ta_securedisplay_command command_id)  {
> > -   *cmd = (struct securedisplay_cmd *)psp-
> >securedisplay_context.context.mem_context.shared_buf;
> > -   memset(*cmd, 0, sizeof(struct securedisplay_cmd));
> > +   *cmd = (struct ta_securedisplay_cmd *)psp-
> >securedisplay_context.context.mem_context.shared_buf;
> > +   memset(*cmd, 0, sizeof(struct ta_securedisplay_cmd));
> > (*cmd)->status = TA_SECUREDISPLAY_STATUS__GENERIC_FAILURE;
> > (*cmd)->cmd_id = command_id;
> >  }
> > @@ -93,7 +93,7 @@ static ssize_t
> > amdgpu_securedisplay_debugfs_write(struct file *f, const char __u  {
> > struct amdgpu_device *adev = (struct amdgpu_device *)file_inode(f)-
> >i_private;
> > struct psp_context *psp = &adev->psp;
> > -   struct securedisplay_cmd *securedisplay_cmd;
> > +   struct ta_securedisplay_cmd *securedisplay_cmd;
> > struct drm_device *dev = adev_to_drm(adev);
> > uint32_t phy_id;
> > uint32_t op;
> > diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
> > b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
> > index fe98574748f4..456ad68ed4b2 100644
> > --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
> > +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
> > @@ -30,7 +30,7 @@
> >  void amdgpu_securedisplay_debugfs_init(struct amdgpu_device *adev);
> > void psp_securedisplay_parse_resp_status(struct psp_context *psp,
> > enum ta_securedisplay_status status); -void
> > psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct
> > securedisplay_cmd **cmd,
> > +void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct
> > +ta_securedisplay_cmd **cmd,
> > enum ta_securedisplay_command command_id);
> >
> >  #endif
> > diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
> > b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
> > index ad73e5855580..8841c447d0e2 100644
> > --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
> > +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
> > @@ -103,7 +103,7 @@ static void
> > amdgpu_dm_crtc_notify_ta_to_read(struct work_struct *work)  {
> > struct secure_display_context *secure_display_ctx;
> > struct psp_context *psp;
> > -   struct securedisplay_cmd *securedisplay_cmd;
> > +   struct ta_securedisplay_cmd *securedisplay_cmd;
> > struct drm_crtc *crtc;
> > struct dc_stream_state *stream;
> > uint8_t phy_inst;
> > --
> > 2.39.0
> >


0001-drm-amdgpu-update-ta_secureDisplay_if.h-to-v27.00.00.patch
Description: 0001-drm-amdgpu-update-ta_secureDisplay_if.h-to-v27.00.00.patch


[PATCH v6 44/45] drm/amd: Use `amdgpu_ucode_release` helper for si

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_release` helper is replacing all calls
to release_firmware.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c | 11 ++-
 1 file changed, 2 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c 
b/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c
index 49c398ec0aaf..d6d9e3b1b2c0 100644
--- a/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c
+++ b/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c
@@ -7714,20 +7714,13 @@ static int si_dpm_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_smc.bin", chip_name);
-   err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->pm.fw);
-
-out:
+   err = amdgpu_ucode_request(adev, &adev->pm.fw, fw_name);
if (err) {
DRM_ERROR("si_smc: Failed to load firmware. err = %d\"%s\"\n",
  err, fw_name);
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(&adev->pm.fw);
}
return err;
-
 }
 
 static int si_dpm_sw_init(void *handle)
-- 
2.34.1



[PATCH v6 42/45] drm/amd: Use `amdgpu_ucode_*` helpers for DMCU

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 11 ++-
 1 file changed, 2 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
index 61c192ead62f..79c4652e8e40 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
@@ -1881,20 +1881,13 @@ static int load_dmcu_fw(struct amdgpu_device *adev)
return 0;
}
 
-   r = request_firmware_direct(&adev->dm.fw_dmcu, fw_name_dmcu, adev->dev);
-   if (r == -ENOENT) {
+   r = amdgpu_ucode_request(adev, &adev->dm.fw_dmcu, fw_name_dmcu);
+   if (r == -ENODEV) {
/* DMCU firmware is not necessary, so don't raise a fuss if 
it's missing */
DRM_DEBUG_KMS("dm: DMCU firmware not found\n");
adev->dm.fw_dmcu = NULL;
return 0;
}
-   if (r) {
-   dev_err(adev->dev, "amdgpu_dm: Can't load firmware \"%s\"\n",
-   fw_name_dmcu);
-   return r;
-   }
-
-   r = amdgpu_ucode_validate(adev->dm.fw_dmcu);
if (r) {
dev_err(adev->dev, "amdgpu_dm: Can't validate firmware 
\"%s\"\n",
fw_name_dmcu);
-- 
2.34.1



[PATCH v6 41/45] drm/amd: Use `amdgpu_ucode_*` helpers for GPU info bin

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 14 +++---
 1 file changed, 3 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
index cdb681398a99..406d53ac3096 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
@@ -1983,17 +1983,10 @@ static int amdgpu_device_parse_gpu_info_fw(struct 
amdgpu_device *adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_gpu_info.bin", chip_name);
-   err = request_firmware(&adev->firmware.gpu_info_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->firmware.gpu_info_fw, fw_name);
if (err) {
dev_err(adev->dev,
-   "Failed to load gpu_info firmware \"%s\"\n",
-   fw_name);
-   goto out;
-   }
-   err = amdgpu_ucode_validate(adev->firmware.gpu_info_fw);
-   if (err) {
-   dev_err(adev->dev,
-   "Failed to validate gpu_info firmware \"%s\"\n",
+   "Failed to get gpu_info firmware \"%s\"\n",
fw_name);
goto out;
}
@@ -4030,8 +4023,7 @@ void amdgpu_device_fini_sw(struct amdgpu_device *adev)
 
amdgpu_fence_driver_sw_fini(adev);
amdgpu_device_ip_fini(adev);
-   release_firmware(adev->firmware.gpu_info_fw);
-   adev->firmware.gpu_info_fw = NULL;
+   amdgpu_ucode_release(&adev->firmware.gpu_info_fw);
adev->accel_working = false;
dma_fence_put(rcu_dereference_protected(adev->gang_submit, true));
 
-- 
2.34.1



[PATCH v6 45/45] drm/amd: make amdgpu_ucode_validate static

2023-01-04 Thread Mario Limonciello
No consumers outside of amdgpu_ucode.c use amdgpu_ucode_validate
anymore, so make the function static.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 2 +-
 drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h | 1 -
 2 files changed, 1 insertion(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
index 8ebfec12da87..47549d659d9b 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
@@ -504,7 +504,7 @@ void amdgpu_ucode_print_gpu_info_hdr(const struct 
common_firmware_header *hdr)
}
 }
 
-int amdgpu_ucode_validate(const struct firmware *fw)
+static int amdgpu_ucode_validate(const struct firmware *fw)
 {
const struct common_firmware_header *hdr =
(const struct common_firmware_header *)fw->data;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
index 848579d4988b..bee93ab4298f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
@@ -543,7 +543,6 @@ void amdgpu_ucode_print_rlc_hdr(const struct 
common_firmware_header *hdr);
 void amdgpu_ucode_print_sdma_hdr(const struct common_firmware_header *hdr);
 void amdgpu_ucode_print_psp_hdr(const struct common_firmware_header *hdr);
 void amdgpu_ucode_print_gpu_info_hdr(const struct common_firmware_header *hdr);
-int amdgpu_ucode_validate(const struct firmware *fw);
 int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
**fw,
 const char *fw_name);
 void amdgpu_ucode_release(const struct firmware **fw);
-- 
2.34.1



[PATCH v6 43/45] drm/amd: Use `amdgpu_ucode_release` helper for powerplay

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_release` helper is replacing all calls to
release_firmware.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c 
b/drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c
index 8f2cc6310340..11b7b4cffaae 100644
--- a/drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c
+++ b/drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c
@@ -111,8 +111,7 @@ static int pp_sw_fini(void *handle)
 
hwmgr_sw_fini(hwmgr);
 
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(&adev->pm.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v6 37/45] drm/amd: Use `amdgpu_ucode_*` helpers for SDMA on CIK

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/cik_sdma.c | 16 ++--
 1 file changed, 6 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/cik_sdma.c 
b/drivers/gpu/drm/amd/amdgpu/cik_sdma.c
index cbca9866645c..67d16236b216 100644
--- a/drivers/gpu/drm/amd/amdgpu/cik_sdma.c
+++ b/drivers/gpu/drm/amd/amdgpu/cik_sdma.c
@@ -73,10 +73,9 @@ u32 amdgpu_cik_gpu_check_soft_reset(struct amdgpu_device 
*adev);
 static void cik_sdma_free_microcode(struct amdgpu_device *adev)
 {
int i;
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(&adev->sdma.instance[i].fw);
 }
 
 /*
@@ -137,18 +136,15 @@ static int cik_sdma_init_microcode(struct amdgpu_device 
*adev)
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma.bin", chip_name);
else
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma1.bin", chip_name);
-   err = request_firmware(&adev->sdma.instance[i].fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->sdma.instance[i].fw, 
fw_name);
if (err)
goto out;
-   err = amdgpu_ucode_validate(adev->sdma.instance[i].fw);
}
 out:
if (err) {
pr_err("cik_sdma: Failed to load firmware \"%s\"\n", fw_name);
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(&adev->sdma.instance[i].fw);
}
return err;
 }
-- 
2.34.1



[PATCH v6 38/45] drm/amd: Use `amdgpu_ucode_*` helpers for UVD

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c | 14 +++---
 1 file changed, 3 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c
index 6eac649499d3..482fcf71d1c1 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c
@@ -260,19 +260,11 @@ int amdgpu_uvd_sw_init(struct amdgpu_device *adev)
return -EINVAL;
}
 
-   r = request_firmware(&adev->uvd.fw, fw_name, adev->dev);
-   if (r) {
-   dev_err(adev->dev, "amdgpu_uvd: Can't load firmware \"%s\"\n",
-   fw_name);
-   return r;
-   }
-
-   r = amdgpu_ucode_validate(adev->uvd.fw);
+   r = amdgpu_ucode_request(adev, &adev->uvd.fw, fw_name);
if (r) {
dev_err(adev->dev, "amdgpu_uvd: Can't validate firmware 
\"%s\"\n",
fw_name);
-   release_firmware(adev->uvd.fw);
-   adev->uvd.fw = NULL;
+   amdgpu_ucode_release(&adev->uvd.fw);
return r;
}
 
@@ -394,7 +386,7 @@ int amdgpu_uvd_sw_fini(struct amdgpu_device *adev)
amdgpu_ring_fini(&adev->uvd.inst[j].ring_enc[i]);
}
amdgpu_bo_free_kernel(&adev->uvd.ib_bo, NULL, &addr);
-   release_firmware(adev->uvd.fw);
+   amdgpu_ucode_release(&adev->uvd.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v6 40/45] drm/amd: Use `amdgpu_ucode_*` helpers for CGS

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c | 11 ++-
 1 file changed, 2 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c
index f1a050379190..456e385333b6 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c
@@ -411,17 +411,10 @@ static int amdgpu_cgs_get_firmware_info(struct cgs_device 
*cgs_device,
return -EINVAL;
}
 
-   err = request_firmware(&adev->pm.fw, fw_name, 
adev->dev);
-   if (err) {
-   DRM_ERROR("Failed to request firmware\n");
-   return err;
-   }
-
-   err = amdgpu_ucode_validate(adev->pm.fw);
+   err = amdgpu_ucode_request(adev, &adev->pm.fw, fw_name);
if (err) {
DRM_ERROR("Failed to load firmware \"%s\"", 
fw_name);
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(&adev->pm.fw);
return err;
}
 
-- 
2.34.1



[PATCH v6 39/45] drm/amd: Use `amdgpu_ucode_*` helpers for VCE

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c | 14 +++---
 1 file changed, 3 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c
index 02cb3a12dd76..ea78b7513182 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c
@@ -158,19 +158,11 @@ int amdgpu_vce_sw_init(struct amdgpu_device *adev, 
unsigned long size)
return -EINVAL;
}
 
-   r = request_firmware(&adev->vce.fw, fw_name, adev->dev);
-   if (r) {
-   dev_err(adev->dev, "amdgpu_vce: Can't load firmware \"%s\"\n",
-   fw_name);
-   return r;
-   }
-
-   r = amdgpu_ucode_validate(adev->vce.fw);
+   r = amdgpu_ucode_request(adev, &adev->vce.fw, fw_name);
if (r) {
dev_err(adev->dev, "amdgpu_vce: Can't validate firmware 
\"%s\"\n",
fw_name);
-   release_firmware(adev->vce.fw);
-   adev->vce.fw = NULL;
+   amdgpu_ucode_release(&adev->vce.fw);
return r;
}
 
@@ -226,7 +218,7 @@ int amdgpu_vce_sw_fini(struct amdgpu_device *adev)
for (i = 0; i < adev->vce.num_rings; i++)
amdgpu_ring_fini(&adev->vce.ring[i]);
 
-   release_firmware(adev->vce.fw);
+   amdgpu_ucode_release(&adev->vce.fw);
mutex_destroy(&adev->vce.idle_mutex);
 
return 0;
-- 
2.34.1



[PATCH v6 36/45] drm/amd: Use `amdgpu_ucode_*` helpers for SDMA3.0

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c | 18 ++
 1 file changed, 6 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c 
b/drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c
index 486d9b5c1b9e..e572389089d2 100644
--- a/drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c
@@ -250,10 +250,9 @@ static void sdma_v3_0_init_golden_registers(struct 
amdgpu_device *adev)
 static void sdma_v3_0_free_microcode(struct amdgpu_device *adev)
 {
int i;
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(&adev->sdma.instance[i].fw);
 }
 
 /**
@@ -309,10 +308,7 @@ static int sdma_v3_0_init_microcode(struct amdgpu_device 
*adev)
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma.bin", chip_name);
else
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma1.bin", chip_name);
-   err = request_firmware(&adev->sdma.instance[i].fw, fw_name, 
adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->sdma.instance[i].fw);
+   err = amdgpu_ucode_request(adev, &adev->sdma.instance[i].fw, 
fw_name);
if (err)
goto out;
hdr = (const struct sdma_firmware_header_v1_0 
*)adev->sdma.instance[i].fw->data;
@@ -332,10 +328,8 @@ static int sdma_v3_0_init_microcode(struct amdgpu_device 
*adev)
 out:
if (err) {
pr_err("sdma_v3_0: Failed to load firmware \"%s\"\n", fw_name);
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(&adev->sdma.instance[i].fw);
}
return err;
 }
-- 
2.34.1



[PATCH v6 29/45] drm/amd: Use `amdgpu_ucode_*` helpers for GFX6

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c | 30 +++
 1 file changed, 8 insertions(+), 22 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c
index 204b246f0e3f..438eab348fc8 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v6_0.c
@@ -338,10 +338,7 @@ static int gfx_v6_0_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.pfp_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
if (err)
goto out;
cp_hdr = (const struct gfx_firmware_header_v1_0 
*)adev->gfx.pfp_fw->data;
@@ -349,10 +346,7 @@ static int gfx_v6_0_init_microcode(struct amdgpu_device 
*adev)
adev->gfx.pfp_feature_version = 
le32_to_cpu(cp_hdr->ucode_feature_version);
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.me_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
if (err)
goto out;
cp_hdr = (const struct gfx_firmware_header_v1_0 *)adev->gfx.me_fw->data;
@@ -360,10 +354,7 @@ static int gfx_v6_0_init_microcode(struct amdgpu_device 
*adev)
adev->gfx.me_feature_version = 
le32_to_cpu(cp_hdr->ucode_feature_version);
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce.bin", chip_name);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.ce_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, fw_name);
if (err)
goto out;
cp_hdr = (const struct gfx_firmware_header_v1_0 *)adev->gfx.ce_fw->data;
@@ -371,10 +362,9 @@ static int gfx_v6_0_init_microcode(struct amdgpu_device 
*adev)
adev->gfx.ce_feature_version = 
le32_to_cpu(cp_hdr->ucode_feature_version);
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_rlc.bin", chip_name);
-   err = request_firmware(&adev->gfx.rlc_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.rlc_fw, fw_name);
if (err)
goto out;
-   err = amdgpu_ucode_validate(adev->gfx.rlc_fw);
rlc_hdr = (const struct rlc_firmware_header_v1_0 
*)adev->gfx.rlc_fw->data;
adev->gfx.rlc_fw_version = le32_to_cpu(rlc_hdr->header.ucode_version);
adev->gfx.rlc_feature_version = 
le32_to_cpu(rlc_hdr->ucode_feature_version);
@@ -382,14 +372,10 @@ static int gfx_v6_0_init_microcode(struct amdgpu_device 
*adev)
 out:
if (err) {
pr_err("gfx6: Failed to load firmware \"%s\"\n", fw_name);
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
+   amdgpu_ucode_release(&adev->gfx.pfp_fw);
+   amdgpu_ucode_release(&adev->gfx.me_fw);
+   amdgpu_ucode_release(&adev->gfx.ce_fw);
+   amdgpu_ucode_release(&adev->gfx.rlc_fw);
}
return err;
 }
-- 
2.34.1



[PATCH v6 35/45] drm/amd: Use `amdgpu_ucode_*` helpers for SDMA2.4

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c | 18 ++
 1 file changed, 6 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c 
b/drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c
index c52d246a1d96..fd2a7b66ac56 100644
--- a/drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c
+++ b/drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c
@@ -113,10 +113,9 @@ static void sdma_v2_4_init_golden_registers(struct 
amdgpu_device *adev)
 static void sdma_v2_4_free_microcode(struct amdgpu_device *adev)
 {
int i;
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(&adev->sdma.instance[i].fw);
 }
 
 /**
@@ -151,10 +150,7 @@ static int sdma_v2_4_init_microcode(struct amdgpu_device 
*adev)
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma.bin", chip_name);
else
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma1.bin", chip_name);
-   err = request_firmware(&adev->sdma.instance[i].fw, fw_name, 
adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->sdma.instance[i].fw);
+   err = amdgpu_ucode_request(adev, &adev->sdma.instance[i].fw, 
fw_name);
if (err)
goto out;
hdr = (const struct sdma_firmware_header_v1_0 
*)adev->sdma.instance[i].fw->data;
@@ -176,10 +172,8 @@ static int sdma_v2_4_init_microcode(struct amdgpu_device 
*adev)
 out:
if (err) {
pr_err("sdma_v2_4: Failed to load firmware \"%s\"\n", fw_name);
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(&adev->sdma.instance[i].fw);
}
return err;
 }
-- 
2.34.1



[PATCH v6 28/45] drm/amd: Optimize SRIOV switch/case for PSP microcode load

2023-01-04 Thread Mario Limonciello
Now that IP version decoding is used, a number of case statements
can be combined.

Reviewed-by: Alex Deucher 
Reviewed-by: Christian König 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c | 8 +---
 1 file changed, 1 insertion(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index aaef30bba97f..380e08affc25 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -132,14 +132,8 @@ static int psp_init_sriov_microcode(struct psp_context 
*psp)
 
switch (adev->ip_versions[MP0_HWIP][0]) {
case IP_VERSION(9, 0, 0):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
-   ret = psp_init_cap_microcode(psp, ucode_prefix);
-   break;
-   case IP_VERSION(11, 0, 9):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
-   ret = psp_init_cap_microcode(psp, ucode_prefix);
-   break;
case IP_VERSION(11, 0, 7):
+   case IP_VERSION(11, 0, 9):
adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
ret = psp_init_cap_microcode(psp, ucode_prefix);
break;
-- 
2.34.1



[PATCH v6 34/45] drm/amd: Use `amdgpu_ucode_*` helpers for GMC8

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c | 13 +++--
 1 file changed, 3 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c 
b/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
index 382dde1ce74c..561daac2e6f7 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
@@ -264,16 +264,10 @@ static int gmc_v8_0_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mc.bin", chip_name);
-   err = request_firmware(&adev->gmc.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gmc.fw);
-
-out:
+   err = amdgpu_ucode_request(adev, &adev->gmc.fw, fw_name);
if (err) {
pr_err("mc: Failed to load firmware \"%s\"\n", fw_name);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(&adev->gmc.fw);
}
return err;
 }
@@ -1203,8 +1197,7 @@ static int gmc_v8_0_sw_fini(void *handle)
kfree(adev->gmc.vm_fault_info);
amdgpu_gart_table_vram_free(adev);
amdgpu_bo_fini(adev);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(&adev->gmc.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v6 32/45] drm/amd: Use `amdgpu_ucode_*` helpers for GMC6

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c | 14 +++---
 1 file changed, 3 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c 
b/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
index ec291d28edff..d154ab48f507 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
@@ -131,19 +131,12 @@ static int gmc_v6_0_init_microcode(struct amdgpu_device 
*adev)
snprintf(fw_name, sizeof(fw_name), "amdgpu/si58_mc.bin");
else
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mc.bin", 
chip_name);
-   err = request_firmware(&adev->gmc.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-
-   err = amdgpu_ucode_validate(adev->gmc.fw);
-
-out:
+   err = amdgpu_ucode_request(adev, &adev->gmc.fw, fw_name);
if (err) {
dev_err(adev->dev,
   "si_mc: Failed to load firmware \"%s\"\n",
   fw_name);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(&adev->gmc.fw);
}
return err;
 }
@@ -894,8 +887,7 @@ static int gmc_v6_0_sw_fini(void *handle)
amdgpu_vm_manager_fini(adev);
amdgpu_gart_table_vram_free(adev);
amdgpu_bo_fini(adev);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(&adev->gmc.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v6 33/45] drm/amd: Use `amdgpu_ucode_*` helpers for GMC7

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c | 13 +++--
 1 file changed, 3 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c 
b/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
index 979da6f510e8..4412e8c65726 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
@@ -156,16 +156,10 @@ static int gmc_v7_0_init_microcode(struct amdgpu_device 
*adev)
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mc.bin", chip_name);
 
-   err = request_firmware(&adev->gmc.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gmc.fw);
-
-out:
+   err = amdgpu_ucode_request(adev, &adev->gmc.fw, fw_name);
if (err) {
pr_err("cik_mc: Failed to load firmware \"%s\"\n", fw_name);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(&adev->gmc.fw);
}
return err;
 }
@@ -1081,8 +1075,7 @@ static int gmc_v7_0_sw_fini(void *handle)
kfree(adev->gmc.vm_fault_info);
amdgpu_gart_table_vram_free(adev);
amdgpu_bo_fini(adev);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(&adev->gmc.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v6 31/45] drm/amd: Use `amdgpu_ucode_*` helpers for GFX8

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c | 94 ++-
 1 file changed, 33 insertions(+), 61 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c
index d47135606e3e..04577e5234ae 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c
@@ -924,20 +924,14 @@ static int gfx_v8_0_ring_test_ib(struct amdgpu_ring 
*ring, long timeout)
 
 static void gfx_v8_0_free_microcode(struct amdgpu_device *adev)
 {
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
+   amdgpu_ucode_release(&adev->gfx.pfp_fw);
+   amdgpu_ucode_release(&adev->gfx.me_fw);
+   amdgpu_ucode_release(&adev->gfx.ce_fw);
+   amdgpu_ucode_release(&adev->gfx.rlc_fw);
+   amdgpu_ucode_release(&adev->gfx.mec_fw);
if ((adev->asic_type != CHIP_STONEY) &&
(adev->asic_type != CHIP_TOPAZ))
-   release_firmware(adev->gfx.mec2_fw);
-   adev->gfx.mec2_fw = NULL;
+   amdgpu_ucode_release(&adev->gfx.mec2_fw);
 
kfree(adev->gfx.rlc.register_list_format);
 }
@@ -989,18 +983,15 @@ static int gfx_v8_0_init_microcode(struct amdgpu_device 
*adev)
 
if (adev->asic_type >= CHIP_POLARIS10 && adev->asic_type <= 
CHIP_POLARIS12) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp_2.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
-   if (err == -ENOENT) {
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
+   if (err == -ENODEV) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, 
fw_name);
}
} else {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
}
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.pfp_fw);
if (err)
goto out;
cp_hdr = (const struct gfx_firmware_header_v1_0 
*)adev->gfx.pfp_fw->data;
@@ -1009,18 +1000,15 @@ static int gfx_v8_0_init_microcode(struct amdgpu_device 
*adev)
 
if (adev->asic_type >= CHIP_POLARIS10 && adev->asic_type <= 
CHIP_POLARIS12) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me_2.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
-   if (err == -ENOENT) {
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
+   if (err == -ENODEV) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
}
} else {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
}
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.me_fw);
if (err)
goto out;
cp_hdr = (const struct gfx_firmware_header_v1_0 *)adev->gfx.me_fw->data;
@@ -1030,18 +1018,15 @@ static int gfx_v8_0_init_microcode(struct amdgpu_device 
*adev)
 
if (adev->asic_type >= CHIP_POLARIS10 && adev->asic_type <= 
CHIP_POLARIS12) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce_2.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, adev->dev);
-   if (err == -ENOENT) {
+   err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, fw_name);
+   if (err == -ENODEV) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_requ

[PATCH v6 30/45] drm/amd: Use `amdgpu_ucode_*` helpers for GFX7

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c | 68 +++
 1 file changed, 17 insertions(+), 51 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c
index 0f2976507e48..646999ad4f04 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c
@@ -887,6 +887,16 @@ static void gfx_v7_0_get_csb_buffer(struct amdgpu_device 
*adev, volatile u32 *bu
 static void gfx_v7_0_init_pg(struct amdgpu_device *adev);
 static void gfx_v7_0_get_cu_info(struct amdgpu_device *adev);
 
+static void gfx_v7_0_free_microcode(struct amdgpu_device *adev)
+{
+   amdgpu_ucode_release(&adev->gfx.pfp_fw);
+   amdgpu_ucode_release(&adev->gfx.me_fw);
+   amdgpu_ucode_release(&adev->gfx.ce_fw);
+   amdgpu_ucode_release(&adev->gfx.mec_fw);
+   amdgpu_ucode_release(&adev->gfx.mec2_fw);
+   amdgpu_ucode_release(&adev->gfx.rlc_fw);
+}
+
 /*
  * Core functions
  */
@@ -927,88 +937,44 @@ static int gfx_v7_0_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.pfp_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
if (err)
goto out;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.me_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
if (err)
goto out;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce.bin", chip_name);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.ce_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, fw_name);
if (err)
goto out;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mec.bin", chip_name);
-   err = request_firmware(&adev->gfx.mec_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.mec_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.mec_fw, fw_name);
if (err)
goto out;
 
if (adev->asic_type == CHIP_KAVERI) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mec2.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.mec2_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.mec2_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.mec2_fw, fw_name);
if (err)
goto out;
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_rlc.bin", chip_name);
-   err = request_firmware(&adev->gfx.rlc_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.rlc_fw, fw_name);
if (err)
goto out;
-   err = amdgpu_ucode_validate(adev->gfx.rlc_fw);
-
 out:
if (err) {
pr_err("gfx7: Failed to load firmware \"%s\"\n", fw_name);
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
-   release_firmware(adev->gfx.mec2_fw);
-   adev->gfx.mec2_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
+   gfx_v7_0_free_microcode(adev);
}
return err;
 }
 
-static void gfx_v7_0_free_microcode(struct amdgpu_device *adev)
-{
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
-   release_firmware(adev->gfx.mec2_fw);
-   adev->gfx.mec2_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
-}
-
 /**
  * gfx_v7_0_tiling_mode_table_init - init the hw tiling table
  *
-- 
2.34.1



[PATCH v6 24/45] drm/amd/display: Load DMUB microcode during early_init

2023-01-04 Thread Mario Limonciello
If DMUB is required for an ASIC, ensure that the microcode is available
and validates during early_init.

Any failures will cause the driver to fail to probe before the firmware
framebuffer has been removed.

Reviewed-by: Alex Deucher 
Reviewed-by: Harry Wentland 
Signed-off-by: Mario Limonciello 
---
 .../gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 89 ---
 1 file changed, 58 insertions(+), 31 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
index 4829b5431e4c..c8c5d37c8b3a 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
@@ -1945,7 +1945,6 @@ static int dm_dmub_sw_init(struct amdgpu_device *adev)
struct dmub_srv_fb_info *fb_info;
struct dmub_srv *dmub_srv;
const struct dmcub_firmware_header_v1_0 *hdr;
-   const char *fw_name_dmub;
enum dmub_asic dmub_asic;
enum dmub_status status;
int r;
@@ -1953,73 +1952,46 @@ static int dm_dmub_sw_init(struct amdgpu_device *adev)
switch (adev->ip_versions[DCE_HWIP][0]) {
case IP_VERSION(2, 1, 0):
dmub_asic = DMUB_ASIC_DCN21;
-   fw_name_dmub = FIRMWARE_RENOIR_DMUB;
-   if (ASICREV_IS_GREEN_SARDINE(adev->external_rev_id))
-   fw_name_dmub = FIRMWARE_GREEN_SARDINE_DMUB;
break;
case IP_VERSION(3, 0, 0):
-   if (adev->ip_versions[GC_HWIP][0] == IP_VERSION(10, 3, 0)) {
+   if (adev->ip_versions[GC_HWIP][0] == IP_VERSION(10, 3, 0))
dmub_asic = DMUB_ASIC_DCN30;
-   fw_name_dmub = FIRMWARE_SIENNA_CICHLID_DMUB;
-   } else {
+   else
dmub_asic = DMUB_ASIC_DCN30;
-   fw_name_dmub = FIRMWARE_NAVY_FLOUNDER_DMUB;
-   }
break;
case IP_VERSION(3, 0, 1):
dmub_asic = DMUB_ASIC_DCN301;
-   fw_name_dmub = FIRMWARE_VANGOGH_DMUB;
break;
case IP_VERSION(3, 0, 2):
dmub_asic = DMUB_ASIC_DCN302;
-   fw_name_dmub = FIRMWARE_DIMGREY_CAVEFISH_DMUB;
break;
case IP_VERSION(3, 0, 3):
dmub_asic = DMUB_ASIC_DCN303;
-   fw_name_dmub = FIRMWARE_BEIGE_GOBY_DMUB;
break;
case IP_VERSION(3, 1, 2):
case IP_VERSION(3, 1, 3):
dmub_asic = (adev->external_rev_id == YELLOW_CARP_B0) ? 
DMUB_ASIC_DCN31B : DMUB_ASIC_DCN31;
-   fw_name_dmub = FIRMWARE_YELLOW_CARP_DMUB;
break;
case IP_VERSION(3, 1, 4):
dmub_asic = DMUB_ASIC_DCN314;
-   fw_name_dmub = FIRMWARE_DCN_314_DMUB;
break;
case IP_VERSION(3, 1, 5):
dmub_asic = DMUB_ASIC_DCN315;
-   fw_name_dmub = FIRMWARE_DCN_315_DMUB;
break;
case IP_VERSION(3, 1, 6):
dmub_asic = DMUB_ASIC_DCN316;
-   fw_name_dmub = FIRMWARE_DCN316_DMUB;
break;
case IP_VERSION(3, 2, 0):
dmub_asic = DMUB_ASIC_DCN32;
-   fw_name_dmub = FIRMWARE_DCN_V3_2_0_DMCUB;
break;
case IP_VERSION(3, 2, 1):
dmub_asic = DMUB_ASIC_DCN321;
-   fw_name_dmub = FIRMWARE_DCN_V3_2_1_DMCUB;
break;
default:
/* ASIC doesn't support DMUB. */
return 0;
}
 
-   r = request_firmware_direct(&adev->dm.dmub_fw, fw_name_dmub, adev->dev);
-   if (r) {
-   DRM_ERROR("DMUB firmware loading failed: %d\n", r);
-   return 0;
-   }
-
-   r = amdgpu_ucode_validate(adev->dm.dmub_fw);
-   if (r) {
-   DRM_ERROR("Couldn't validate DMUB firmware: %d\n", r);
-   return 0;
-   }
-
hdr = (const struct dmcub_firmware_header_v1_0 *)adev->dm.dmub_fw->data;
adev->dm.dmcub_fw_version = le32_to_cpu(hdr->header.ucode_version);
 
@@ -4513,6 +4485,61 @@ DEVICE_ATTR_WO(s3_debug);
 
 #endif
 
+static int dm_init_microcode(struct amdgpu_device *adev)
+{
+   char *fw_name_dmub;
+   int r;
+
+   switch (adev->ip_versions[DCE_HWIP][0]) {
+   case IP_VERSION(2, 1, 0):
+   fw_name_dmub = FIRMWARE_RENOIR_DMUB;
+   if (ASICREV_IS_GREEN_SARDINE(adev->external_rev_id))
+   fw_name_dmub = FIRMWARE_GREEN_SARDINE_DMUB;
+   break;
+   case IP_VERSION(3, 0, 0):
+   if (adev->ip_versions[GC_HWIP][0] == IP_VERSION(10, 3, 0))
+   fw_name_dmub = FIRMWARE_SIENNA_CICHLID_DMUB;
+   else
+   fw_name_dmub = FIRMWARE_NAVY_FLOUNDER_DMUB;
+   break;
+   case IP_VERSION(3, 0, 1):
+   fw_name_dmub = FIRMWARE_VANGOGH_DMUB;
+   break;

[PATCH v6 27/45] drm/amd: Load SMU microcode during early_init

2023-01-04 Thread Mario Limonciello
This will ensure that the microcode is available before the firmware
framebuffer has been destroyed.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c | 12 +---
 1 file changed, 5 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c 
b/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
index 2fa79f892a92..ec52830dde24 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
@@ -623,6 +623,7 @@ static int smu_early_init(void *handle)
 {
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
struct smu_context *smu;
+   int r;
 
smu = kzalloc(sizeof(struct smu_context), GFP_KERNEL);
if (!smu)
@@ -640,7 +641,10 @@ static int smu_early_init(void *handle)
adev->powerplay.pp_handle = smu;
adev->powerplay.pp_funcs = &swsmu_pm_funcs;
 
-   return smu_set_funcs(adev);
+   r = smu_set_funcs(adev);
+   if (r)
+   return r;
+   return smu_init_microcode(smu);
 }
 
 static int smu_set_default_dpm_table(struct smu_context *smu)
@@ -1067,12 +1071,6 @@ static int smu_sw_init(void *handle)
smu->smu_dpm.dpm_level = AMD_DPM_FORCED_LEVEL_AUTO;
smu->smu_dpm.requested_dpm_level = AMD_DPM_FORCED_LEVEL_AUTO;
 
-   ret = smu_init_microcode(smu);
-   if (ret) {
-   dev_err(adev->dev, "Failed to load smu firmware!\n");
-   return ret;
-   }
-
ret = smu_smc_table_sw_init(smu);
if (ret) {
dev_err(adev->dev, "Failed to sw init smc table!\n");
-- 
2.34.1



[PATCH v6 25/45] drm/amd: Use `amdgpu_ucode_release` helper for DMUB

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 10 +++---
 1 file changed, 3 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
index c8c5d37c8b3a..61c192ead62f 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
@@ -1898,8 +1898,7 @@ static int load_dmcu_fw(struct amdgpu_device *adev)
if (r) {
dev_err(adev->dev, "amdgpu_dm: Can't validate firmware 
\"%s\"\n",
fw_name_dmcu);
-   release_firmware(adev->dm.fw_dmcu);
-   adev->dm.fw_dmcu = NULL;
+   amdgpu_ucode_release(&adev->dm.fw_dmcu);
return r;
}
 
@@ -2113,11 +2112,8 @@ static int dm_sw_fini(void *handle)
adev->dm.dmub_srv = NULL;
}
 
-   release_firmware(adev->dm.dmub_fw);
-   adev->dm.dmub_fw = NULL;
-
-   release_firmware(adev->dm.fw_dmcu);
-   adev->dm.fw_dmcu = NULL;
+   amdgpu_ucode_release(&adev->dm.dmub_fw);
+   amdgpu_ucode_release(&adev->dm.fw_dmcu);
 
return 0;
 }
-- 
2.34.1



[PATCH v6 26/45] drm/amd: Use `amdgpu_ucode_*` helpers for SMU

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c | 16 
 drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c | 16 
 2 files changed, 8 insertions(+), 24 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
index d4756bd30830..6492d69e2e60 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
@@ -109,10 +109,7 @@ int smu_v11_0_init_microcode(struct smu_context *smu)
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", ucode_prefix);
 
-   err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->pm.fw);
+   err = amdgpu_ucode_request(adev, &adev->pm.fw, fw_name);
if (err)
goto out;
 
@@ -130,12 +127,8 @@ int smu_v11_0_init_microcode(struct smu_context *smu)
}
 
 out:
-   if (err) {
-   DRM_ERROR("smu_v11_0: Failed to load firmware \"%s\"\n",
- fw_name);
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
-   }
+   if (err)
+   amdgpu_ucode_release(&adev->pm.fw);
return err;
 }
 
@@ -143,8 +136,7 @@ void smu_v11_0_fini_microcode(struct smu_context *smu)
 {
struct amdgpu_device *adev = smu->adev;
 
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(&adev->pm.fw);
adev->pm.fw_version = 0;
 }
 
diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
index 506a49a4b425..59d00fefc558 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
@@ -103,10 +103,7 @@ int smu_v13_0_init_microcode(struct smu_context *smu)
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", ucode_prefix);
 
-   err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->pm.fw);
+   err = amdgpu_ucode_request(adev, &adev->pm.fw, fw_name);
if (err)
goto out;
 
@@ -124,12 +121,8 @@ int smu_v13_0_init_microcode(struct smu_context *smu)
}
 
 out:
-   if (err) {
-   DRM_ERROR("smu_v13_0: Failed to load firmware \"%s\"\n",
- fw_name);
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
-   }
+   if (err)
+   amdgpu_ucode_release(&adev->pm.fw);
return err;
 }
 
@@ -137,8 +130,7 @@ void smu_v13_0_fini_microcode(struct smu_context *smu)
 {
struct amdgpu_device *adev = smu->adev;
 
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(&adev->pm.fw);
adev->pm.fw_version = 0;
 }
 
-- 
2.34.1



[PATCH v6 22/45] drm/amd: Load PSP microcode during early_init

2023-01-04 Thread Mario Limonciello
Simplifies the code so that all PSP versions will get the firmware
name from `amdgpu_ucode_ip_version_decode` and then use this filename
to load microcode as part of the early_init process.

Any failures will cause the driver to fail to probe before the firmware
framebuffer has been removed.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * rebase on earlier patches
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c  | 120 +--
 drivers/gpu/drm/amd/amdgpu/psp_v10_0.c   |  12 ---
 drivers/gpu/drm/amd/amdgpu/psp_v11_0.c   |  52 ++
 drivers/gpu/drm/amd/amdgpu/psp_v12_0.c   |  13 +--
 drivers/gpu/drm/amd/amdgpu/psp_v13_0.c   |  27 ++---
 drivers/gpu/drm/amd/amdgpu/psp_v13_0_4.c |  14 +--
 drivers/gpu/drm/amd/amdgpu/psp_v3_1.c|  16 +--
 7 files changed, 69 insertions(+), 185 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index a4a62753bfd6..beaca5846c73 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -122,6 +122,44 @@ static void 
psp_check_pmfw_centralized_cstate_management(struct psp_context *psp
}
 }
 
+static int psp_init_sriov_microcode(struct psp_context *psp)
+{
+   struct amdgpu_device *adev = psp->adev;
+   char ucode_prefix[30];
+   int ret = 0;
+
+   amdgpu_ucode_ip_version_decode(adev, MP0_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
+
+   switch (adev->ip_versions[MP0_HWIP][0]) {
+   case IP_VERSION(9, 0, 0):
+   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
+   ret = psp_init_cap_microcode(psp, ucode_prefix);
+   break;
+   case IP_VERSION(11, 0, 9):
+   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
+   ret = psp_init_cap_microcode(psp, ucode_prefix);
+   break;
+   case IP_VERSION(11, 0, 7):
+   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
+   ret = psp_init_cap_microcode(psp, ucode_prefix);
+   break;
+   case IP_VERSION(13, 0, 2):
+   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
+   ret = psp_init_cap_microcode(psp, ucode_prefix);
+   ret &= psp_init_ta_microcode(psp, ucode_prefix);
+   break;
+   case IP_VERSION(13, 0, 0):
+   adev->virt.autoload_ucode_id = 0;
+   break;
+   case IP_VERSION(13, 0, 10):
+   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MES1_DATA;
+   break;
+   default:
+   return -EINVAL;
+   }
+   return ret;
+}
+
 static int psp_early_init(void *handle)
 {
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
@@ -192,7 +230,10 @@ static int psp_early_init(void *handle)
 
psp_check_pmfw_centralized_cstate_management(psp);
 
-   return 0;
+   if (amdgpu_sriov_vf(adev))
+   return psp_init_sriov_microcode(psp);
+   else
+   return psp_init_microcode(psp);
 }
 
 void psp_ta_free_shared_buf(struct ta_mem_context *mem_ctx)
@@ -350,42 +391,6 @@ static bool psp_get_runtime_db_entry(struct amdgpu_device 
*adev,
return ret;
 }
 
-static int psp_init_sriov_microcode(struct psp_context *psp)
-{
-   struct amdgpu_device *adev = psp->adev;
-   int ret = 0;
-
-   switch (adev->ip_versions[MP0_HWIP][0]) {
-   case IP_VERSION(9, 0, 0):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
-   ret = psp_init_cap_microcode(psp, "vega10");
-   break;
-   case IP_VERSION(11, 0, 9):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
-   ret = psp_init_cap_microcode(psp, "navi12");
-   break;
-   case IP_VERSION(11, 0, 7):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
-   ret = psp_init_cap_microcode(psp, "sienna_cichlid");
-   break;
-   case IP_VERSION(13, 0, 2):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
-   ret = psp_init_cap_microcode(psp, "aldebaran");
-   ret &= psp_init_ta_microcode(psp, "aldebaran");
-   break;
-   case IP_VERSION(13, 0, 0):
-   adev->virt.autoload_ucode_id = 0;
-   break;
-   case IP_VERSION(13, 0, 10):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MES1_DATA;
-   break;
-   default:
-   ret = -EINVAL;
-   break;
-   }
-   return ret;
-}
-
 static int psp_sw_init(void *handle)
 {
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
@@ -401,15 +406,6 @@ static int psp_sw_init(void *handle)
ret = -ENOMEM;
}
 
-   if (amdgpu_sriov_vf(adev))
-   ret = psp_init_sriov_microcode(psp);
-   else
-   ret = psp_init_microcode(psp);
- 

[PATCH v6 21/45] drm/amd: Avoid BUG() for case of SRIOV missing IP version

2023-01-04 Thread Mario Limonciello
No need to crash the kernel.  AMDGPU will now fail to probe.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index d971e3785eaf..a4a62753bfd6 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -380,7 +380,7 @@ static int psp_init_sriov_microcode(struct psp_context *psp)
adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MES1_DATA;
break;
default:
-   BUG();
+   ret = -EINVAL;
break;
}
return ret;
-- 
2.34.1



[PATCH v6 23/45] drm/amd: Use `amdgpu_ucode_*` helpers for PSP

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c | 80 +++--
 1 file changed, 21 insertions(+), 59 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index beaca5846c73..aaef30bba97f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -510,20 +510,11 @@ static int psp_sw_fini(void *handle)
 
psp_memory_training_fini(psp);
 
-   release_firmware(psp->sos_fw);
-   psp->sos_fw = NULL;
-
-   release_firmware(psp->asd_fw);
-   psp->asd_fw = NULL;
-
-   release_firmware(psp->ta_fw);
-   psp->ta_fw = NULL;
-
-   release_firmware(psp->cap_fw);
-   psp->cap_fw = NULL;
-
-   release_firmware(psp->toc_fw);
-   psp->toc_fw = NULL;
+   amdgpu_ucode_release(&psp->sos_fw);
+   amdgpu_ucode_release(&psp->asd_fw);
+   amdgpu_ucode_release(&psp->ta_fw);
+   amdgpu_ucode_release(&psp->cap_fw);
+   amdgpu_ucode_release(&psp->toc_fw);
 
if (adev->ip_versions[MP0_HWIP][0] == IP_VERSION(11, 0, 0) ||
adev->ip_versions[MP0_HWIP][0] == IP_VERSION(11, 0, 7))
@@ -2912,11 +2903,7 @@ int psp_init_asd_microcode(struct psp_context *psp, 
const char *chip_name)
int err = 0;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_asd.bin", chip_name);
-   err = request_firmware(&adev->psp.asd_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-
-   err = amdgpu_ucode_validate(adev->psp.asd_fw);
+   err = amdgpu_ucode_request(adev, &adev->psp.asd_fw, fw_name);
if (err)
goto out;
 
@@ -2928,9 +2915,7 @@ int psp_init_asd_microcode(struct psp_context *psp, const 
char *chip_name)

le32_to_cpu(asd_hdr->header.ucode_array_offset_bytes);
return 0;
 out:
-   dev_err(adev->dev, "fail to initialize asd microcode\n");
-   release_firmware(adev->psp.asd_fw);
-   adev->psp.asd_fw = NULL;
+   amdgpu_ucode_release(&adev->psp.asd_fw);
return err;
 }
 
@@ -2942,11 +2927,7 @@ int psp_init_toc_microcode(struct psp_context *psp, 
const char *chip_name)
int err = 0;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_toc.bin", chip_name);
-   err = request_firmware(&adev->psp.toc_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-
-   err = amdgpu_ucode_validate(adev->psp.toc_fw);
+   err = amdgpu_ucode_request(adev, &adev->psp.toc_fw, fw_name);
if (err)
goto out;
 
@@ -2958,9 +2939,7 @@ int psp_init_toc_microcode(struct psp_context *psp, const 
char *chip_name)

le32_to_cpu(toc_hdr->header.ucode_array_offset_bytes);
return 0;
 out:
-   dev_err(adev->dev, "fail to request/validate toc microcode\n");
-   release_firmware(adev->psp.toc_fw);
-   adev->psp.toc_fw = NULL;
+   amdgpu_ucode_release(&adev->psp.toc_fw);
return err;
 }
 
@@ -3105,11 +3084,7 @@ int psp_init_sos_microcode(struct psp_context *psp, 
const char *chip_name)
int fw_index = 0;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_sos.bin", chip_name);
-   err = request_firmware(&adev->psp.sos_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-
-   err = amdgpu_ucode_validate(adev->psp.sos_fw);
+   err = amdgpu_ucode_request(adev, &adev->psp.sos_fw, fw_name);
if (err)
goto out;
 
@@ -3181,10 +3156,7 @@ int psp_init_sos_microcode(struct psp_context *psp, 
const char *chip_name)
 
return 0;
 out:
-   dev_err(adev->dev,
-   "failed to init sos firmware\n");
-   release_firmware(adev->psp.sos_fw);
-   adev->psp.sos_fw = NULL;
+   amdgpu_ucode_release(&adev->psp.sos_fw);
 
return err;
 }
@@ -3340,10 +3312,7 @@ int psp_init_ta_microcode(struct psp_context *psp, const 
char *chip_name)
int err;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ta.bin", chip_name);
-   err = request_firmware(&adev->psp.ta_fw, fw_name, adev->dev);
-   if (err)
-   return err;
-   err = amdgpu_ucode_validate(adev->psp.ta_fw);
+   err = amdgpu_ucode_request(adev, &adev->psp.ta_fw, fw_name);
if (err)
return err;
 
@@ -3360,11 +3329,8 @@ int psp_init_ta_microcode(struct psp_context *psp, const 
char *chip_name)
err = -EINVAL;
}
 
-   if (err) {
-   dev_err(adev->dev, "fail to initialize ta microcode\n");
-   release_firmware(adev->psp.ta_fw);
-   adev->psp.ta_fw = NULL;
-   }
+   if (err)
+   amdgpu_uc

[PATCH v6 18/45] drm/amd: Use `amdgpu_ucode_*` helpers for GFX11

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper will provide symmetery on unload.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c | 104 +
 drivers/gpu/drm/amd/amdgpu/imu_v11_0.c |   7 +-
 2 files changed, 39 insertions(+), 72 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c
index a56c6e106d00..d4f67624d05b 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c
@@ -431,18 +431,39 @@ static int gfx_v11_0_ring_test_ib(struct amdgpu_ring 
*ring, long timeout)
 
 static void gfx_v11_0_free_microcode(struct amdgpu_device *adev)
 {
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
+   amdgpu_ucode_release(&adev->gfx.pfp_fw);
+   amdgpu_ucode_release(&adev->gfx.me_fw);
+   amdgpu_ucode_release(&adev->gfx.rlc_fw);
+   amdgpu_ucode_release(&adev->gfx.mec_fw);
 
kfree(adev->gfx.rlc.register_list_format);
 }
 
+static int gfx_v11_0_init_toc_microcode(struct amdgpu_device *adev)
+{
+   const struct psp_firmware_header_v1_0 *toc_hdr;
+   int err = 0;
+   char fw_name[40];
+   char ucode_prefix[30];
+
+   amdgpu_ucode_ip_version_decode(adev, GC_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_toc.bin", ucode_prefix);
+   err = amdgpu_ucode_request(adev, &adev->psp.toc_fw, fw_name);
+   if (err)
+   goto out;
+
+   toc_hdr = (const struct psp_firmware_header_v1_0 
*)adev->psp.toc_fw->data;
+   adev->psp.toc.fw_version = le32_to_cpu(toc_hdr->header.ucode_version);
+   adev->psp.toc.feature_version = le32_to_cpu(toc_hdr->sos.fw_version);
+   adev->psp.toc.size_bytes = 
le32_to_cpu(toc_hdr->header.ucode_size_bytes);
+   adev->psp.toc.start_addr = (uint8_t *)toc_hdr +
+   
le32_to_cpu(toc_hdr->header.ucode_array_offset_bytes);
+   return 0;
+out:
+   amdgpu_ucode_release(&adev->psp.toc_fw);
+   return err;
+}
+
 static int gfx_v11_0_init_microcode(struct amdgpu_device *adev)
 {
char fw_name[40];
@@ -457,10 +478,7 @@ static int gfx_v11_0_init_microcode(struct amdgpu_device 
*adev)
amdgpu_ucode_ip_version_decode(adev, GC_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", ucode_prefix);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.pfp_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
if (err)
goto out;
/* check pfp fw hdr version to decide if enable rs64 for gfx11.*/
@@ -477,10 +495,7 @@ static int gfx_v11_0_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", ucode_prefix);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.me_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
if (err)
goto out;
if (adev->gfx.rs64_enable) {
@@ -493,10 +508,7 @@ static int gfx_v11_0_init_microcode(struct amdgpu_device 
*adev)
 
if (!amdgpu_sriov_vf(adev)) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_rlc.bin", 
ucode_prefix);
-   err = request_firmware(&adev->gfx.rlc_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.rlc_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.rlc_fw, fw_name);
if (err)
goto out;
rlc_hdr = (const struct rlc_firmware_header_v2_0 
*)adev->gfx.rlc_fw->data;
@@ -508,10 +520,7 @@ static int gfx_v11_0_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mec.bin", ucode_prefix);
-   err = request_firmware(&adev->gfx.mec_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.mec_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.mec_fw, fw_name);
if (err)
goto out;
if (adev->gfx.rs64_enable) {
@@ -530,54 +539,15 @@ static int gfx_v11_0_init_microcode(struct amdgpu_device 
*adev)
 
 out:
if (err) {
-   dev_err(adev->dev

[PATCH v6 16/45] drm/amd: Use `amdgpu_ucode_*` helpers for GFX10

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unload.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c | 71 --
 1 file changed, 20 insertions(+), 51 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c
index 49d34c7bbf20..140bb18ff768 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c
@@ -3891,18 +3891,12 @@ static int gfx_v10_0_ring_test_ib(struct amdgpu_ring 
*ring, long timeout)
 
 static void gfx_v10_0_free_microcode(struct amdgpu_device *adev)
 {
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
-   release_firmware(adev->gfx.mec2_fw);
-   adev->gfx.mec2_fw = NULL;
+   amdgpu_ucode_release(&adev->gfx.pfp_fw);
+   amdgpu_ucode_release(&adev->gfx.me_fw);
+   amdgpu_ucode_release(&adev->gfx.ce_fw);
+   amdgpu_ucode_release(&adev->gfx.rlc_fw);
+   amdgpu_ucode_release(&adev->gfx.mec_fw);
+   amdgpu_ucode_release(&adev->gfx.mec2_fw);
 
kfree(adev->gfx.rlc.register_list_format);
 }
@@ -4030,41 +4024,31 @@ static int gfx_v10_0_init_microcode(struct 
amdgpu_device *adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp%s.bin", chip_name, 
wks);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.pfp_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_PFP);
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me%s.bin", chip_name, 
wks);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.me_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_ME);
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce%s.bin", chip_name, 
wks);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.ce_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_CE);
 
if (!amdgpu_sriov_vf(adev)) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_rlc.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.rlc_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
+   err = amdgpu_ucode_request(adev, &adev->gfx.rlc_fw, fw_name);
/* don't check this.  There are apparently firmwares in the 
wild with
 * incorrect size in the header
 */
-   err = amdgpu_ucode_validate(adev->gfx.rlc_fw);
+   if (err == -ENODEV)
+   goto out;
if (err)
dev_dbg(adev->dev,
"gfx10: amdgpu_ucode_validate() failed 
\"%s\"\n",
@@ -4078,21 +4062,15 @@ static int gfx_v10_0_init_microcode(struct 
amdgpu_device *adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mec%s.bin", chip_name, 
wks);
-   err = request_firmware(&adev->gfx.mec_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.mec_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.mec_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_MEC1);
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_MEC1_JT);
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mec2%s.bin", chip_name, 
wks);
-   err = request_firmware(&adev->gfx.mec2_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.mec2_fw, fw_name);
if (!err) {
-   err = amdgpu_ucode_validate(adev->gfx.mec2_fw);
-   if (err)
-   goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_MEC2);
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_MEC2_JT);
} else {
@@ -4103,21 +4081,12 

[PATCH v6 20/45] drm/amd: Parse both v1 and v2 TA microcode headers using same function

2023-01-04 Thread Mario Limonciello
Several IP versions duplicate code and can't use the common helpers.
Move this code into a single function so that the helpers can be used.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Rebase on earlier patches
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c | 120 ++--
 drivers/gpu/drm/amd/amdgpu/psp_v10_0.c  |  64 +
 drivers/gpu/drm/amd/amdgpu/psp_v11_0.c  |  77 ++-
 drivers/gpu/drm/amd/amdgpu/psp_v12_0.c  |  62 +---
 4 files changed, 109 insertions(+), 214 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index 7a2fc920739b..d971e3785eaf 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -3272,41 +3272,75 @@ static int parse_ta_bin_descriptor(struct psp_context 
*psp,
return 0;
 }
 
-int psp_init_ta_microcode(struct psp_context *psp,
- const char *chip_name)
+static int parse_ta_v1_microcode(struct psp_context *psp)
 {
+   const struct ta_firmware_header_v1_0 *ta_hdr;
struct amdgpu_device *adev = psp->adev;
-   char fw_name[PSP_FW_NAME_LEN];
-   const struct ta_firmware_header_v2_0 *ta_hdr;
-   int err = 0;
-   int ta_index = 0;
 
-   if (!chip_name) {
-   dev_err(adev->dev, "invalid chip name for ta microcode\n");
+   ta_hdr = (const struct ta_firmware_header_v1_0 *)
+adev->psp.ta_fw->data;
+
+   if (le16_to_cpu(ta_hdr->header.header_version_major) != 1)
return -EINVAL;
+
+   adev->psp.xgmi_context.context.bin_desc.fw_version =
+   le32_to_cpu(ta_hdr->xgmi.fw_version);
+   adev->psp.xgmi_context.context.bin_desc.size_bytes =
+   le32_to_cpu(ta_hdr->xgmi.size_bytes);
+   adev->psp.xgmi_context.context.bin_desc.start_addr =
+   (uint8_t *)ta_hdr +
+   le32_to_cpu(ta_hdr->header.ucode_array_offset_bytes);
+   adev->psp.ta_fw_version = le32_to_cpu(ta_hdr->header.ucode_version);
+   adev->psp.ras_context.context.bin_desc.fw_version =
+   le32_to_cpu(ta_hdr->ras.fw_version);
+   adev->psp.ras_context.context.bin_desc.size_bytes =
+   le32_to_cpu(ta_hdr->ras.size_bytes);
+   adev->psp.ras_context.context.bin_desc.start_addr =
+   (uint8_t *)adev->psp.xgmi_context.context.bin_desc.start_addr +
+   le32_to_cpu(ta_hdr->ras.offset_bytes);
+   adev->psp.hdcp_context.context.bin_desc.fw_version =
+   le32_to_cpu(ta_hdr->hdcp.fw_version);
+   adev->psp.hdcp_context.context.bin_desc.size_bytes =
+   le32_to_cpu(ta_hdr->hdcp.size_bytes);
+   adev->psp.hdcp_context.context.bin_desc.start_addr =
+   (uint8_t *)ta_hdr +
+   le32_to_cpu(ta_hdr->header.ucode_array_offset_bytes);
+   adev->psp.ta_fw_version = le32_to_cpu(ta_hdr->header.ucode_version);
+   adev->psp.dtm_context.context.bin_desc.fw_version =
+   le32_to_cpu(ta_hdr->dtm.fw_version);
+   adev->psp.dtm_context.context.bin_desc.size_bytes =
+   le32_to_cpu(ta_hdr->dtm.size_bytes);
+   adev->psp.dtm_context.context.bin_desc.start_addr =
+   (uint8_t *)adev->psp.hdcp_context.context.bin_desc.start_addr +
+   le32_to_cpu(ta_hdr->dtm.offset_bytes);
+   if (adev->apu_flags & AMD_APU_IS_RENOIR) {
+   adev->psp.securedisplay_context.context.bin_desc.fw_version =
+   le32_to_cpu(ta_hdr->securedisplay.fw_version);
+   adev->psp.securedisplay_context.context.bin_desc.size_bytes =
+   le32_to_cpu(ta_hdr->securedisplay.size_bytes);
+   adev->psp.securedisplay_context.context.bin_desc.start_addr =
+   (uint8_t 
*)adev->psp.hdcp_context.context.bin_desc.start_addr +
+   le32_to_cpu(ta_hdr->securedisplay.offset_bytes);
}
 
-   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ta.bin", chip_name);
-   err = request_firmware(&adev->psp.ta_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
+   return 0;
+}
 
-   err = amdgpu_ucode_validate(adev->psp.ta_fw);
-   if (err)
-   goto out;
+static int parse_ta_v2_microcode(struct psp_context *psp)
+{
+   const struct ta_firmware_header_v2_0 *ta_hdr;
+   struct amdgpu_device *adev = psp->adev;
+   int err = 0;
+   int ta_index = 0;
 
ta_hdr = (const struct ta_firmware_header_v2_0 *)adev->psp.ta_fw->data;
 
-   if (le16_to_cpu(ta_hdr->header.header_version_major) != 2) {
-   dev_err(adev->dev, "unsupported TA header version\n");
-   err = -EINVAL;
-   goto out;
-   }
+   if (le16_to_cpu(ta_hdr->header.header_version_major) != 2)
+   return -EINVAL;
 
if (le32_to_cpu(ta_hdr->ta_fw_bin_count) >= UCODE_MAX_PSP_PACKAGING) {
  

[PATCH v6 19/45] drm/amd: Load GFX11 microcode during early_init

2023-01-04 Thread Mario Limonciello
If GFX11 microcode is required but not available during early init, the
firmware framebuffer will have already been released and the screen will
freeze.

Move the request for GFX11 microcode into the early_init phase
so that if it's not available, driver init will fail.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Rebase on earlier changes
---
 drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c | 26 +++---
 1 file changed, 7 insertions(+), 19 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c
index d4f67624d05b..5cc329cf66c4 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v11_0.c
@@ -439,14 +439,12 @@ static void gfx_v11_0_free_microcode(struct amdgpu_device 
*adev)
kfree(adev->gfx.rlc.register_list_format);
 }
 
-static int gfx_v11_0_init_toc_microcode(struct amdgpu_device *adev)
+static int gfx_v11_0_init_toc_microcode(struct amdgpu_device *adev, const char 
*ucode_prefix)
 {
const struct psp_firmware_header_v1_0 *toc_hdr;
int err = 0;
char fw_name[40];
-   char ucode_prefix[30];
 
-   amdgpu_ucode_ip_version_decode(adev, GC_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_toc.bin", ucode_prefix);
err = amdgpu_ucode_request(adev, &adev->psp.toc_fw, fw_name);
if (err)
@@ -534,6 +532,9 @@ static int gfx_v11_0_init_microcode(struct amdgpu_device 
*adev)
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_MEC1_JT);
}
 
+   if (adev->firmware.load_type == AMDGPU_FW_LOAD_RLC_BACKDOOR_AUTO)
+   err = gfx_v11_0_init_toc_microcode(adev, ucode_prefix);
+
/* only one MEC for gfx 11.0.0. */
adev->gfx.mec2_fw = NULL;
 
@@ -684,19 +685,11 @@ static void gfx_v11_0_mec_fini(struct amdgpu_device *adev)
amdgpu_bo_free_kernel(&adev->gfx.mec.mec_fw_data_obj, NULL, NULL);
 }
 
-static int gfx_v11_0_me_init(struct amdgpu_device *adev)
+static void gfx_v11_0_me_init(struct amdgpu_device *adev)
 {
-   int r;
-
bitmap_zero(adev->gfx.me.queue_bitmap, AMDGPU_MAX_GFX_QUEUES);
 
amdgpu_gfx_graphics_queue_acquire(adev);
-
-   r = gfx_v11_0_init_microcode(adev);
-   if (r)
-   DRM_ERROR("Failed to load gfx firmware!\n");
-
-   return r;
 }
 
 static int gfx_v11_0_mec_init(struct amdgpu_device *adev)
@@ -1309,9 +1302,7 @@ static int gfx_v11_0_sw_init(void *handle)
}
}
 
-   r = gfx_v11_0_me_init(adev);
-   if (r)
-   return r;
+   gfx_v11_0_me_init(adev);
 
r = gfx_v11_0_rlc_init(adev);
if (r) {
@@ -1379,9 +1370,6 @@ static int gfx_v11_0_sw_init(void *handle)
 
/* allocate visible FB for rlc auto-loading fw */
if (adev->firmware.load_type == AMDGPU_FW_LOAD_RLC_BACKDOOR_AUTO) {
-   r = gfx_v11_0_init_toc_microcode(adev);
-   if (r)
-   dev_err(adev->dev, "Failed to load toc firmware!\n");
r = gfx_v11_0_rlc_autoload_buffer_init(adev);
if (r)
return r;
@@ -4650,7 +4638,7 @@ static int gfx_v11_0_early_init(void *handle)
 
gfx_v11_0_init_rlcg_reg_access_ctrl(adev);
 
-   return 0;
+   return gfx_v11_0_init_microcode(adev);
 }
 
 static int gfx_v11_0_ras_late_init(void *handle)
-- 
2.34.1



[PATCH v6 17/45] drm/amd: Load GFX10 microcode during early_init

2023-01-04 Thread Mario Limonciello
Simplifies the code so that GFX10 will get the firmware
name from `amdgpu_ucode_ip_version_decode` and then use this filename
to load microcode as part of the early_init process.

Any failures will cause the driver to fail to probe before the firmware
framebuffer has been removed.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c | 84 ++
 1 file changed, 18 insertions(+), 66 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c
index 140bb18ff768..6983acc456b2 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v10_0.c
@@ -3968,9 +3968,9 @@ static void gfx_v10_0_check_gfxoff_flag(struct 
amdgpu_device *adev)
 
 static int gfx_v10_0_init_microcode(struct amdgpu_device *adev)
 {
-   const char *chip_name;
char fw_name[40];
-   char *wks = "";
+   char ucode_prefix[30];
+   const char *wks = "";
int err;
const struct rlc_firmware_header_v2_0 *rlc_hdr;
uint16_t version_major;
@@ -3978,71 +3978,31 @@ static int gfx_v10_0_init_microcode(struct 
amdgpu_device *adev)
 
DRM_DEBUG("\n");
 
-   switch (adev->ip_versions[GC_HWIP][0]) {
-   case IP_VERSION(10, 1, 10):
-   chip_name = "navi10";
-   break;
-   case IP_VERSION(10, 1, 1):
-   chip_name = "navi14";
-   if (!(adev->pdev->device == 0x7340 &&
- adev->pdev->revision != 0x00))
-   wks = "_wks";
-   break;
-   case IP_VERSION(10, 1, 2):
-   chip_name = "navi12";
-   break;
-   case IP_VERSION(10, 3, 0):
-   chip_name = "sienna_cichlid";
-   break;
-   case IP_VERSION(10, 3, 2):
-   chip_name = "navy_flounder";
-   break;
-   case IP_VERSION(10, 3, 1):
-   chip_name = "vangogh";
-   break;
-   case IP_VERSION(10, 3, 4):
-   chip_name = "dimgrey_cavefish";
-   break;
-   case IP_VERSION(10, 3, 5):
-   chip_name = "beige_goby";
-   break;
-   case IP_VERSION(10, 3, 3):
-   chip_name = "yellow_carp";
-   break;
-   case IP_VERSION(10, 3, 6):
-   chip_name = "gc_10_3_6";
-   break;
-   case IP_VERSION(10, 1, 3):
-   case IP_VERSION(10, 1, 4):
-   chip_name = "cyan_skillfish2";
-   break;
-   case IP_VERSION(10, 3, 7):
-   chip_name = "gc_10_3_7";
-   break;
-   default:
-   BUG();
-   }
+   if (adev->ip_versions[GC_HWIP][0] == IP_VERSION(10, 1, 1) &&
+  (!(adev->pdev->device == 0x7340 && adev->pdev->revision != 0x00)))
+   wks = "_wks";
+   amdgpu_ucode_ip_version_decode(adev, GC_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
 
-   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp%s.bin", chip_name, 
wks);
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp%s.bin", ucode_prefix, 
wks);
err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_PFP);
 
-   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me%s.bin", chip_name, 
wks);
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me%s.bin", ucode_prefix, 
wks);
err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_ME);
 
-   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce%s.bin", chip_name, 
wks);
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce%s.bin", ucode_prefix, 
wks);
err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_CE);
 
if (!amdgpu_sriov_vf(adev)) {
-   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_rlc.bin", 
chip_name);
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_rlc.bin", 
ucode_prefix);
err = amdgpu_ucode_request(adev, &adev->gfx.rlc_fw, fw_name);
/* don't check this.  There are apparently firmwares in the 
wild with
 * incorrect size in the header
@@ -4051,7 +4011,7 @@ static int gfx_v10_0_init_microcode(struct amdgpu_device 
*adev)
goto out;
if (err)
dev_dbg(adev->dev,
-   "gfx10: amdgpu_ucode_validate() failed 
\"%s\"\n",
+   "gfx10: amdgpu_ucode_request() failed \"%s\"\n",
fw_name);
rlc_hdr = (const struct rlc_firmware_header_v2_0 
*)adev->gfx.rlc_fw->data;
version_major = 
le16_to_cpu(rlc_hdr->heade

[PATCH v6 15/45] drm/amd: Load GFX9 microcode during early_init

2023-01-04 Thread Mario Limonciello
If GFX9 microcode is required but not available during early init, the
firmware framebuffer will have already been released and the screen will
freeze.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c | 58 +--
 1 file changed, 9 insertions(+), 49 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c
index ef2dbebbc90c..0dba690cf7dd 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c
@@ -1245,7 +1245,7 @@ static void gfx_v9_0_check_if_need_gfxoff(struct 
amdgpu_device *adev)
 }
 
 static int gfx_v9_0_init_cp_gfx_microcode(struct amdgpu_device *adev,
- const char *chip_name)
+ char *chip_name)
 {
char fw_name[30];
int err;
@@ -1278,7 +1278,7 @@ static int gfx_v9_0_init_cp_gfx_microcode(struct 
amdgpu_device *adev,
 }
 
 static int gfx_v9_0_init_rlc_microcode(struct amdgpu_device *adev,
- const char *chip_name)
+  char *chip_name)
 {
char fw_name[30];
int err;
@@ -1333,7 +1333,7 @@ static bool gfx_v9_0_load_mec2_fw_bin_support(struct 
amdgpu_device *adev)
 }
 
 static int gfx_v9_0_init_cp_compute_microcode(struct amdgpu_device *adev,
- const char *chip_name)
+ char *chip_name)
 {
char fw_name[30];
int err;
@@ -1379,58 +1379,24 @@ static int gfx_v9_0_init_cp_compute_microcode(struct 
amdgpu_device *adev,
 
 static int gfx_v9_0_init_microcode(struct amdgpu_device *adev)
 {
-   const char *chip_name;
+   char ucode_prefix[30];
int r;
 
DRM_DEBUG("\n");
-
-   switch (adev->ip_versions[GC_HWIP][0]) {
-   case IP_VERSION(9, 0, 1):
-   chip_name = "vega10";
-   break;
-   case IP_VERSION(9, 2, 1):
-   chip_name = "vega12";
-   break;
-   case IP_VERSION(9, 4, 0):
-   chip_name = "vega20";
-   break;
-   case IP_VERSION(9, 2, 2):
-   case IP_VERSION(9, 1, 0):
-   if (adev->apu_flags & AMD_APU_IS_RAVEN2)
-   chip_name = "raven2";
-   else if (adev->apu_flags & AMD_APU_IS_PICASSO)
-   chip_name = "picasso";
-   else
-   chip_name = "raven";
-   break;
-   case IP_VERSION(9, 4, 1):
-   chip_name = "arcturus";
-   break;
-   case IP_VERSION(9, 3, 0):
-   if (adev->apu_flags & AMD_APU_IS_RENOIR)
-   chip_name = "renoir";
-   else
-   chip_name = "green_sardine";
-   break;
-   case IP_VERSION(9, 4, 2):
-   chip_name = "aldebaran";
-   break;
-   default:
-   BUG();
-   }
+   amdgpu_ucode_ip_version_decode(adev, GC_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
 
/* No CPG in Arcturus */
if (adev->gfx.num_gfx_rings) {
-   r = gfx_v9_0_init_cp_gfx_microcode(adev, chip_name);
+   r = gfx_v9_0_init_cp_gfx_microcode(adev, ucode_prefix);
if (r)
return r;
}
 
-   r = gfx_v9_0_init_rlc_microcode(adev, chip_name);
+   r = gfx_v9_0_init_rlc_microcode(adev, ucode_prefix);
if (r)
return r;
 
-   r = gfx_v9_0_init_cp_compute_microcode(adev, chip_name);
+   r = gfx_v9_0_init_cp_compute_microcode(adev, ucode_prefix);
if (r)
return r;
 
@@ -2118,12 +2084,6 @@ static int gfx_v9_0_sw_init(void *handle)
 
adev->gfx.gfx_current_status = AMDGPU_GFX_NORMAL_MODE;
 
-   r = gfx_v9_0_init_microcode(adev);
-   if (r) {
-   DRM_ERROR("Failed to load gfx firmware!\n");
-   return r;
-   }
-
if (adev->gfx.rlc.funcs) {
if (adev->gfx.rlc.funcs->init) {
r = adev->gfx.rlc.funcs->init(adev);
@@ -4565,7 +4525,7 @@ static int gfx_v9_0_early_init(void *handle)
/* init rlcg reg access ctrl */
gfx_v9_0_init_rlcg_reg_access_ctrl(adev);
 
-   return 0;
+   return gfx_v9_0_init_microcode(adev);
 }
 
 static int gfx_v9_0_ecc_late_init(void *handle)
-- 
2.34.1



[PATCH v6 13/45] drm/amd: Remove superfluous assignment for `adev->mes.adev`

2023-01-04 Thread Mario Limonciello
`amdgpu_mes_init` already sets `adev->mes.adev`, so there is no need
to also set it in the IP specific versions.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/mes_v10_1.c | 1 -
 drivers/gpu/drm/amd/amdgpu/mes_v11_0.c | 1 -
 2 files changed, 2 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c 
b/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
index 7848b9de79ce..2e2062636d5f 100644
--- a/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
+++ b/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
@@ -924,7 +924,6 @@ static int mes_v10_1_sw_init(void *handle)
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
int pipe, r;
 
-   adev->mes.adev = adev;
adev->mes.funcs = &mes_v10_1_funcs;
adev->mes.kiq_hw_init = &mes_v10_1_kiq_hw_init;
 
diff --git a/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c 
b/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c
index a0125e103007..a36b0f14ff92 100644
--- a/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c
@@ -1013,7 +1013,6 @@ static int mes_v11_0_sw_init(void *handle)
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
int pipe, r;
 
-   adev->mes.adev = adev;
adev->mes.funcs = &mes_v11_0_funcs;
adev->mes.kiq_hw_init = &mes_v11_0_kiq_hw_init;
adev->mes.kiq_hw_fini = &mes_v11_0_kiq_hw_fini;
-- 
2.34.1



[PATCH v6 14/45] drm/amd: Use `amdgpu_ucode_*` helpers for GFX9

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper will provide symmetry on unload.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c | 82 +++
 1 file changed, 21 insertions(+), 61 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c
index f202b45c413c..ef2dbebbc90c 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v9_0.c
@@ -1078,18 +1078,12 @@ static int gfx_v9_0_ring_test_ib(struct amdgpu_ring 
*ring, long timeout)
 
 static void gfx_v9_0_free_microcode(struct amdgpu_device *adev)
 {
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
-   release_firmware(adev->gfx.mec2_fw);
-   adev->gfx.mec2_fw = NULL;
+   amdgpu_ucode_release(&adev->gfx.pfp_fw);
+   amdgpu_ucode_release(&adev->gfx.me_fw);
+   amdgpu_ucode_release(&adev->gfx.ce_fw);
+   amdgpu_ucode_release(&adev->gfx.rlc_fw);
+   amdgpu_ucode_release(&adev->gfx.mec_fw);
+   amdgpu_ucode_release(&adev->gfx.mec2_fw);
 
kfree(adev->gfx.rlc.register_list_format);
 }
@@ -1257,43 +1251,28 @@ static int gfx_v9_0_init_cp_gfx_microcode(struct 
amdgpu_device *adev,
int err;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.pfp_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_PFP);
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.me_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_ME);
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce.bin", chip_name);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.ce_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, fw_name);
if (err)
goto out;
amdgpu_gfx_cp_init_microcode(adev, AMDGPU_UCODE_ID_CP_CE);
 
 out:
if (err) {
-   dev_err(adev->dev,
-   "gfx9: Failed to init firmware \"%s\"\n",
-   fw_name);
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
+   amdgpu_ucode_release(&adev->gfx.pfp_fw);
+   amdgpu_ucode_release(&adev->gfx.me_fw);
+   amdgpu_ucode_release(&adev->gfx.ce_fw);
}
return err;
 }
@@ -1328,10 +1307,7 @@ static int gfx_v9_0_init_rlc_microcode(struct 
amdgpu_device *adev,
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_kicker_rlc.bin", 
chip_name);
else
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_rlc.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.rlc_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.rlc_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.rlc_fw, fw_name);
if (err)
goto out;
rlc_hdr = (const struct rlc_firmware_header_v2_0 
*)adev->gfx.rlc_fw->data;
@@ -1340,13 +1316,9 @@ static int gfx_v9_0_init_rlc_microcode(struct 
amdgpu_device *adev,
version_minor = le16_to_cpu(rlc_hdr->header.header_version_minor);
err = amdgpu_gfx_rlc_init_microcode(adev, version_major, version_minor);
 out:
-   if (err) {
-   dev_err(adev->dev,
-   "gfx9: Failed to init firmware \"%s\"\n",
-   fw_name);
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
-   }
+   if (err)
+   amdgpu_ucode_release(&adev->gfx.rlc_fw);
+
return err;
 }
 
@@ -1371,12 +1343,9 @@ static int gfx_v9_0_init_cp_compute_microcode(s

[PATCH v6 12/45] drm/amd: Use `amdgpu_ucode_*` helpers for MES

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper provides symmetry for releasing firmware.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c | 10 ++
 drivers/gpu/drm/amd/amdgpu/mes_v10_1.c  | 10 +-
 drivers/gpu/drm/amd/amdgpu/mes_v11_0.c  | 10 +-
 3 files changed, 4 insertions(+), 26 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
index dd8f35234507..82e27bd4f038 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
@@ -1438,11 +1438,7 @@ int amdgpu_mes_init_microcode(struct amdgpu_device 
*adev, int pipe)
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mes%s.bin",
ucode_prefix,
pipe == AMDGPU_MES_SCHED_PIPE ? "" : "1");
-   r = request_firmware(&adev->mes.fw[pipe], fw_name, adev->dev);
-   if (r)
-   goto out;
-
-   r = amdgpu_ucode_validate(adev->mes.fw[pipe]);
+   r = amdgpu_ucode_request(adev, &adev->mes.fw[pipe], fw_name);
if (r)
goto out;
 
@@ -1482,9 +1478,7 @@ int amdgpu_mes_init_microcode(struct amdgpu_device *adev, 
int pipe)
}
 
return 0;
-
 out:
-   release_firmware(adev->mes.fw[pipe]);
-   adev->mes.fw[pipe] = NULL;
+   amdgpu_ucode_release(&adev->mes.fw[pipe]);
return r;
 }
diff --git a/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c 
b/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
index 9c5ff8b7c202..7848b9de79ce 100644
--- a/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
+++ b/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
@@ -379,13 +379,6 @@ static const struct amdgpu_mes_funcs mes_v10_1_funcs = {
.resume_gang = mes_v10_1_resume_gang,
 };
 
-static void mes_v10_1_free_microcode(struct amdgpu_device *adev,
-enum admgpu_mes_pipe pipe)
-{
-   release_firmware(adev->mes.fw[pipe]);
-   adev->mes.fw[pipe] = NULL;
-}
-
 static int mes_v10_1_allocate_ucode_buffer(struct amdgpu_device *adev,
   enum admgpu_mes_pipe pipe)
 {
@@ -979,8 +972,7 @@ static int mes_v10_1_sw_fini(void *handle)
amdgpu_bo_free_kernel(&adev->mes.eop_gpu_obj[pipe],
  &adev->mes.eop_gpu_addr[pipe],
  NULL);
-
-   mes_v10_1_free_microcode(adev, pipe);
+   amdgpu_ucode_release(&adev->mes.fw[pipe]);
}
 
amdgpu_bo_free_kernel(&adev->gfx.kiq.ring.mqd_obj,
diff --git a/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c 
b/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c
index 3af77a32baac..a0125e103007 100644
--- a/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/mes_v11_0.c
@@ -459,13 +459,6 @@ static const struct amdgpu_mes_funcs mes_v11_0_funcs = {
.misc_op = mes_v11_0_misc_op,
 };
 
-static void mes_v11_0_free_microcode(struct amdgpu_device *adev,
-enum admgpu_mes_pipe pipe)
-{
-   release_firmware(adev->mes.fw[pipe]);
-   adev->mes.fw[pipe] = NULL;
-}
-
 static int mes_v11_0_allocate_ucode_buffer(struct amdgpu_device *adev,
   enum admgpu_mes_pipe pipe)
 {
@@ -1069,8 +1062,7 @@ static int mes_v11_0_sw_fini(void *handle)
amdgpu_bo_free_kernel(&adev->mes.eop_gpu_obj[pipe],
  &adev->mes.eop_gpu_addr[pipe],
  NULL);
-
-   mes_v11_0_free_microcode(adev, pipe);
+   amdgpu_ucode_release(&adev->mes.fw[pipe]);
}
 
amdgpu_bo_free_kernel(&adev->gfx.kiq.ring.mqd_obj,
-- 
2.34.1



[PATCH v6 11/45] drm/amd: Load MES microcode during early_init

2023-01-04 Thread Mario Limonciello
Add an early_init phase to MES for fetching and validating microcode
from the filesystem.

If MES microcode is required but not available during early init, the
firmware framebuffer will have already been released and the screen will
freeze.

Move the request for MES microcode into the early_init phase
so that if it's not available, early_init will fail.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c | 65 +
 drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h |  1 +
 drivers/gpu/drm/amd/amdgpu/mes_v10_1.c  | 97 +
 drivers/gpu/drm/amd/amdgpu/mes_v11_0.c  | 88 +-
 4 files changed, 100 insertions(+), 151 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
index 0c546245793b..dd8f35234507 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c
@@ -21,6 +21,8 @@
  *
  */
 
+#include 
+
 #include "amdgpu_mes.h"
 #include "amdgpu.h"
 #include "soc15_common.h"
@@ -1423,3 +1425,66 @@ int amdgpu_mes_self_test(struct amdgpu_device *adev)
kfree(vm);
return 0;
 }
+
+int amdgpu_mes_init_microcode(struct amdgpu_device *adev, int pipe)
+{
+   const struct mes_firmware_header_v1_0 *mes_hdr;
+   struct amdgpu_firmware_info *info;
+   char ucode_prefix[30];
+   char fw_name[40];
+   int r;
+
+   amdgpu_ucode_ip_version_decode(adev, GC_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mes%s.bin",
+   ucode_prefix,
+   pipe == AMDGPU_MES_SCHED_PIPE ? "" : "1");
+   r = request_firmware(&adev->mes.fw[pipe], fw_name, adev->dev);
+   if (r)
+   goto out;
+
+   r = amdgpu_ucode_validate(adev->mes.fw[pipe]);
+   if (r)
+   goto out;
+
+   mes_hdr = (const struct mes_firmware_header_v1_0 *)
+   adev->mes.fw[pipe]->data;
+   adev->mes.uc_start_addr[pipe] =
+   le32_to_cpu(mes_hdr->mes_uc_start_addr_lo) |
+   ((uint64_t)(le32_to_cpu(mes_hdr->mes_uc_start_addr_hi)) << 32);
+   adev->mes.data_start_addr[pipe] =
+   le32_to_cpu(mes_hdr->mes_data_start_addr_lo) |
+   ((uint64_t)(le32_to_cpu(mes_hdr->mes_data_start_addr_hi)) << 
32);
+
+   if (adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) {
+   int ucode, ucode_data;
+
+   if (pipe == AMDGPU_MES_SCHED_PIPE) {
+   ucode = AMDGPU_UCODE_ID_CP_MES;
+   ucode_data = AMDGPU_UCODE_ID_CP_MES_DATA;
+   } else {
+   ucode = AMDGPU_UCODE_ID_CP_MES1;
+   ucode_data = AMDGPU_UCODE_ID_CP_MES1_DATA;
+   }
+
+   info = &adev->firmware.ucode[ucode];
+   info->ucode_id = ucode;
+   info->fw = adev->mes.fw[pipe];
+   adev->firmware.fw_size +=
+   ALIGN(le32_to_cpu(mes_hdr->mes_ucode_size_bytes),
+ PAGE_SIZE);
+
+   info = &adev->firmware.ucode[ucode_data];
+   info->ucode_id = ucode_data;
+   info->fw = adev->mes.fw[pipe];
+   adev->firmware.fw_size +=
+   ALIGN(le32_to_cpu(mes_hdr->mes_ucode_data_size_bytes),
+ PAGE_SIZE);
+   }
+
+   return 0;
+
+out:
+   release_firmware(adev->mes.fw[pipe]);
+   adev->mes.fw[pipe] = NULL;
+   return r;
+}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h
index 97c05d08a551..547ec35691fa 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_mes.h
@@ -306,6 +306,7 @@ struct amdgpu_mes_funcs {
 
 int amdgpu_mes_ctx_get_offs(struct amdgpu_ring *ring, unsigned int id_offs);
 
+int amdgpu_mes_init_microcode(struct amdgpu_device *adev, int pipe);
 int amdgpu_mes_init(struct amdgpu_device *adev);
 void amdgpu_mes_fini(struct amdgpu_device *adev);
 
diff --git a/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c 
b/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
index 614394118a53..9c5ff8b7c202 100644
--- a/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
+++ b/drivers/gpu/drm/amd/amdgpu/mes_v10_1.c
@@ -379,82 +379,6 @@ static const struct amdgpu_mes_funcs mes_v10_1_funcs = {
.resume_gang = mes_v10_1_resume_gang,
 };
 
-static int mes_v10_1_init_microcode(struct amdgpu_device *adev,
-   enum admgpu_mes_pipe pipe)
-{
-   const char *chip_name;
-   char fw_name[30];
-   int err;
-   const struct mes_firmware_header_v1_0 *mes_hdr;
-   struct amdgpu_firmware_info *info;
-
-   switch (adev->ip_versions[GC_HWIP][0]) {
-   case IP_VERSION(10, 1, 10):
-   chip_name = "navi10";
-   break;
-   case IP_VERSION(10, 3, 0):
-   chip_name = "sienna_cichlid";
- 

[PATCH v6 10/45] drm/amd: Load VCN microcode during early_init

2023-01-04 Thread Mario Limonciello
Simplifies the code so that all VCN versions will get the firmware
name from `amdgpu_ucode_ip_version_decode` and then use this filename
to load microcode as part of the early_init process.

Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Fix whitespace problem in firmware file names
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c | 53 +++--
 drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h |  1 +
 drivers/gpu/drm/amd/amdgpu/vcn_v1_0.c   |  5 ++-
 drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c   |  5 ++-
 drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c   |  5 ++-
 drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c   |  5 ++-
 drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c   |  5 ++-
 7 files changed, 31 insertions(+), 48 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
index b37400107a37..0fb9a6d23065 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
@@ -80,10 +80,24 @@ MODULE_FIRMWARE(FIRMWARE_VCN4_0_4);
 
 static void amdgpu_vcn_idle_work_handler(struct work_struct *work);
 
+int amdgpu_vcn_early_init(struct amdgpu_device *adev)
+{
+   char ucode_prefix[30];
+   char fw_name[40];
+   int r;
+
+   amdgpu_ucode_ip_version_decode(adev, UVD_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", ucode_prefix);
+   r = amdgpu_ucode_request(adev, &adev->vcn.fw, fw_name);
+   if (r)
+   amdgpu_ucode_release(&adev->vcn.fw);
+
+   return r;
+}
+
 int amdgpu_vcn_sw_init(struct amdgpu_device *adev)
 {
unsigned long bo_size;
-   const char *fw_name;
const struct common_firmware_header *hdr;
unsigned char fw_check;
unsigned int fw_shared_size, log_offset;
@@ -99,46 +113,27 @@ int amdgpu_vcn_sw_init(struct amdgpu_device *adev)
switch (adev->ip_versions[UVD_HWIP][0]) {
case IP_VERSION(1, 0, 0):
case IP_VERSION(1, 0, 1):
-   if (adev->apu_flags & AMD_APU_IS_RAVEN2)
-   fw_name = FIRMWARE_RAVEN2;
-   else if (adev->apu_flags & AMD_APU_IS_PICASSO)
-   fw_name = FIRMWARE_PICASSO;
-   else
-   fw_name = FIRMWARE_RAVEN;
-   break;
case IP_VERSION(2, 5, 0):
-   fw_name = FIRMWARE_ARCTURUS;
if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
(adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
adev->vcn.indirect_sram = true;
break;
case IP_VERSION(2, 2, 0):
-   if (adev->apu_flags & AMD_APU_IS_RENOIR)
-   fw_name = FIRMWARE_RENOIR;
-   else
-   fw_name = FIRMWARE_GREEN_SARDINE;
-
if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
(adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
adev->vcn.indirect_sram = true;
break;
case IP_VERSION(2, 6, 0):
-   fw_name = FIRMWARE_ALDEBARAN;
if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
(adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
adev->vcn.indirect_sram = true;
break;
case IP_VERSION(2, 0, 0):
-   fw_name = FIRMWARE_NAVI10;
if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
(adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
adev->vcn.indirect_sram = true;
break;
case IP_VERSION(2, 0, 2):
-   if (adev->asic_type == CHIP_NAVI12)
-   fw_name = FIRMWARE_NAVI12;
-   else
-   fw_name = FIRMWARE_NAVI14;
if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
(adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
adev->vcn.indirect_sram = true;
@@ -146,58 +141,46 @@ int amdgpu_vcn_sw_init(struct amdgpu_device *adev)
case IP_VERSION(3, 0, 0):
case IP_VERSION(3, 0, 64):
case IP_VERSION(3, 0, 192):
-   if (adev->ip_versions[GC_HWIP][0] == IP_VERSION(10, 3, 0))
-   fw_name = FIRMWARE_SIENNA_CICHLID;
-   else
-   fw_name = FIRMWARE_NAVY_FLOUNDER;
if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
(adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
adev->vcn.indirect_sram = true;
break;
case IP_VERSION(3, 0, 2):
-   fw_name = FIRMWARE_VANGOGH;
if ((adev->firmware.load_type == AMDGPU_FW_LOAD_PSP) &&
(adev->pg_flags & AMD_PG_SUPPORT_VCN_DPG))
adev->vcn.indirect_sram = true;
break;
case IP_VERSION(3, 0, 16):
-   fw_na

[PATCH v6 07/45] drm/amd: Convert SDMA to use `amdgpu_ucode_ip_version_decode`

2023-01-04 Thread Mario Limonciello
Simplifies the code so that all SDMA versions will get the firmware
name from `amdgpu_ucode_ip_version_decode`.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c | 12 --
 drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.h |  4 +-
 drivers/gpu/drm/amd/amdgpu/sdma_v4_0.c   | 47 +---
 drivers/gpu/drm/amd/amdgpu/sdma_v5_0.c   | 30 +
 drivers/gpu/drm/amd/amdgpu/sdma_v5_2.c   | 55 +---
 drivers/gpu/drm/amd/amdgpu/sdma_v6_0.c   | 25 +--
 6 files changed, 17 insertions(+), 156 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
index a6a491569022..95e9450f3348 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
@@ -200,15 +200,21 @@ void amdgpu_sdma_destroy_inst_ctx(struct amdgpu_device 
*adev,
 }
 
 int amdgpu_sdma_init_microcode(struct amdgpu_device *adev,
-  char *fw_name, u32 instance,
-  bool duplicate)
+  u32 instance, bool duplicate)
 {
struct amdgpu_firmware_info *info = NULL;
const struct common_firmware_header *header = NULL;
int err = 0, i;
const struct sdma_firmware_header_v2_0 *sdma_hdr;
uint16_t version_major;
-
+   char ucode_prefix[30];
+   char fw_name[40];
+
+   amdgpu_ucode_ip_version_decode(adev, SDMA0_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
+   if (instance == 0)
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", 
ucode_prefix);
+   else
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s%d.bin", 
ucode_prefix, i);
err = amdgpu_ucode_request(adev, &adev->sdma.instance[instance].fw, 
fw_name);
if (err)
goto out;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.h
index 7d99205c2e01..2d16e6d36728 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.h
@@ -124,8 +124,8 @@ int amdgpu_sdma_process_ras_data_cb(struct amdgpu_device 
*adev,
 int amdgpu_sdma_process_ecc_irq(struct amdgpu_device *adev,
  struct amdgpu_irq_src *source,
  struct amdgpu_iv_entry *entry);
-int amdgpu_sdma_init_microcode(struct amdgpu_device *adev,
-char *fw_name, u32 instance, bool duplicate);
+int amdgpu_sdma_init_microcode(struct amdgpu_device *adev, u32 instance,
+  bool duplicate);
 void amdgpu_sdma_destroy_inst_ctx(struct amdgpu_device *adev,
 bool duplicate);
 void amdgpu_sdma_unset_buffer_funcs_helper(struct amdgpu_device *adev);
diff --git a/drivers/gpu/drm/amd/amdgpu/sdma_v4_0.c 
b/drivers/gpu/drm/amd/amdgpu/sdma_v4_0.c
index 4d780e4430e7..017ae298558e 100644
--- a/drivers/gpu/drm/amd/amdgpu/sdma_v4_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/sdma_v4_0.c
@@ -575,60 +575,17 @@ static void sdma_v4_0_setup_ulv(struct amdgpu_device 
*adev)
 // vega10 real chip need to use PSP to load firmware
 static int sdma_v4_0_init_microcode(struct amdgpu_device *adev)
 {
-   const char *chip_name;
-   char fw_name[30];
int ret, i;
 
-   DRM_DEBUG("\n");
-
-   switch (adev->ip_versions[SDMA0_HWIP][0]) {
-   case IP_VERSION(4, 0, 0):
-   chip_name = "vega10";
-   break;
-   case IP_VERSION(4, 0, 1):
-   chip_name = "vega12";
-   break;
-   case IP_VERSION(4, 2, 0):
-   chip_name = "vega20";
-   break;
-   case IP_VERSION(4, 1, 0):
-   case IP_VERSION(4, 1, 1):
-   if (adev->apu_flags & AMD_APU_IS_RAVEN2)
-   chip_name = "raven2";
-   else if (adev->apu_flags & AMD_APU_IS_PICASSO)
-   chip_name = "picasso";
-   else
-   chip_name = "raven";
-   break;
-   case IP_VERSION(4, 2, 2):
-   chip_name = "arcturus";
-   break;
-   case IP_VERSION(4, 1, 2):
-   if (adev->apu_flags & AMD_APU_IS_RENOIR)
-   chip_name = "renoir";
-   else
-   chip_name = "green_sardine";
-   break;
-   case IP_VERSION(4, 4, 0):
-   chip_name = "aldebaran";
-   break;
-   default:
-   BUG();
-   }
-
for (i = 0; i < adev->sdma.num_instances; i++) {
-   if (i == 0)
-   snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma.bin", chip_name);
-   else
-   snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma%d.bin", chip_name, i);
if (adev->ip_versions[SDMA0_HWIP][0] == IP_VERSION(4, 2, 2) ||
 adev->ip_versions[SDMA0_HWIP][0] == IP_VERSION(4, 4, 0)) {
/* Act

[PATCH v6 08/45] drm/amd: Make SDMA firmware load failures less noisy.

2023-01-04 Thread Mario Limonciello
When firmware is missing we get failures at every step.
```
[3.855086] amdgpu :04:00.0: Direct firmware load for 
amdgpu/green_sardine_sdma.bin failed with error -2
[3.855087] [drm:amdgpu_sdma_init_microcode [amdgpu]] *ERROR* SDMA: Failed 
to init firmware "amdgpu/green_sardine_sdma.bin"
[3.855398] [drm:sdma_v4_0_early_init [amdgpu]] *ERROR* Failed to load sdma 
firmware!
```
Realistically we don't need all of these, a user can tell from the first one
that request_firmware emitted what happened. Drop the others.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
index 95e9450f3348..0e1e2521fe25 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
@@ -280,10 +280,8 @@ int amdgpu_sdma_init_microcode(struct amdgpu_device *adev,
}
 
 out:
-   if (err) {
-   DRM_ERROR("SDMA: Failed to init firmware \"%s\"\n", fw_name);
+   if (err)
amdgpu_sdma_destroy_inst_ctx(adev, duplicate);
-   }
return err;
 }
 
-- 
2.34.1



[PATCH v6 06/45] drm/amd: Use `amdgpu_ucode_request` helper for SDMA

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c | 9 ++---
 1 file changed, 2 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
index ea5278f094c0..a6a491569022 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_sdma.c
@@ -154,16 +154,11 @@ int amdgpu_sdma_process_ecc_irq(struct amdgpu_device 
*adev,
 
 static int amdgpu_sdma_init_inst_ctx(struct amdgpu_sdma_instance *sdma_inst)
 {
-   int err = 0;
uint16_t version_major;
const struct common_firmware_header *header = NULL;
const struct sdma_firmware_header_v1_0 *hdr;
const struct sdma_firmware_header_v2_0 *hdr_v2;
 
-   err = amdgpu_ucode_validate(sdma_inst->fw);
-   if (err)
-   return err;
-
header = (const struct common_firmware_header *)
sdma_inst->fw->data;
version_major = le16_to_cpu(header->header_version_major);
@@ -195,7 +190,7 @@ void amdgpu_sdma_destroy_inst_ctx(struct amdgpu_device 
*adev,
int i;
 
for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
+   amdgpu_ucode_release(&adev->sdma.instance[i].fw);
if (duplicate)
break;
}
@@ -214,7 +209,7 @@ int amdgpu_sdma_init_microcode(struct amdgpu_device *adev,
const struct sdma_firmware_header_v2_0 *sdma_hdr;
uint16_t version_major;
 
-   err = request_firmware(&adev->sdma.instance[instance].fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->sdma.instance[instance].fw, 
fw_name);
if (err)
goto out;
 
-- 
2.34.1



[PATCH v6 09/45] drm/amd: Use `amdgpu_ucode_*` helpers for VCN

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry.

Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Adjust for amdgpu_ucode_release argument change
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c | 16 +++-
 1 file changed, 3 insertions(+), 13 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
index a23e26b272b4..b37400107a37 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
@@ -206,19 +206,9 @@ int amdgpu_vcn_sw_init(struct amdgpu_device *adev)
return -EINVAL;
}
 
-   r = request_firmware(&adev->vcn.fw, fw_name, adev->dev);
+   r = amdgpu_ucode_request(adev, &adev->vcn.fw, fw_name);
if (r) {
-   dev_err(adev->dev, "amdgpu_vcn: Can't load firmware \"%s\"\n",
-   fw_name);
-   return r;
-   }
-
-   r = amdgpu_ucode_validate(adev->vcn.fw);
-   if (r) {
-   dev_err(adev->dev, "amdgpu_vcn: Can't validate firmware 
\"%s\"\n",
-   fw_name);
-   release_firmware(adev->vcn.fw);
-   adev->vcn.fw = NULL;
+   amdgpu_ucode_release(&adev->vcn.fw);
return r;
}
 
@@ -333,7 +323,7 @@ int amdgpu_vcn_sw_fini(struct amdgpu_device *adev)
amdgpu_ring_fini(&adev->vcn.inst[j].ring_enc[i]);
}
 
-   release_firmware(adev->vcn.fw);
+   amdgpu_ucode_release(&adev->vcn.fw);
mutex_destroy(&adev->vcn.vcn1_jpeg1_workaround);
mutex_destroy(&adev->vcn.vcn_pg_lock);
 
-- 
2.34.1



[PATCH v6 05/45] drm/amd: Add a new helper for loading/validating microcode

2023-01-04 Thread Mario Limonciello
All microcode runs a basic validation after it's been loaded. Each
IP block as part of init will run both.

Introduce a wrapper for request_firmware and amdgpu_ucode_validate.
This wrapper will also remap any error codes from request_firmware
to -ENODEV.  This is so that early_init will fail if firmware couldn't
be loaded instead of the IP block being disabled.

Signed-off-by: Mario Limonciello 
---
v5->v6:
 * Fix argument to be ** not *
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 36 +++
 drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h |  3 ++
 2 files changed, 39 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
index eafcddce58d3..8ebfec12da87 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
@@ -1312,3 +1312,39 @@ void amdgpu_ucode_ip_version_decode(struct amdgpu_device 
*adev, int block_type,
 
snprintf(ucode_prefix, len, "%s_%d_%d_%d", ip_name, maj, min, rev);
 }
+
+/*
+ * amdgpu_ucode_request - Fetch and validate amdgpu microcode
+ *
+ * @adev: amdgpu device
+ * @fw: pointer to load firmware to
+ * @fw_name: firmware to load
+ *
+ * This is a helper that will use request_firmware and amdgpu_ucode_validate
+ * to load and run basic validation on firmware. If the load fails, remap
+ * the error code to -ENODEV, so that early_init functions will fail to load.
+ */
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
**fw,
+const char *fw_name)
+{
+   int err = request_firmware(fw, fw_name, adev->dev);
+
+   if (err)
+   return -ENODEV;
+   err = amdgpu_ucode_validate(*fw);
+   if (err)
+   dev_dbg(adev->dev, "\"%s\" failed to validate\n", fw_name);
+
+   return err;
+}
+
+/*
+ * amdgpu_ucode_release - Release firmware microcode
+ *
+ * @fw: pointer to firmware to release
+ */
+void amdgpu_ucode_release(const struct firmware **fw)
+{
+   release_firmware(*fw);
+   *fw = NULL;
+}
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
index 552e06929229..848579d4988b 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
@@ -544,6 +544,9 @@ void amdgpu_ucode_print_sdma_hdr(const struct 
common_firmware_header *hdr);
 void amdgpu_ucode_print_psp_hdr(const struct common_firmware_header *hdr);
 void amdgpu_ucode_print_gpu_info_hdr(const struct common_firmware_header *hdr);
 int amdgpu_ucode_validate(const struct firmware *fw);
+int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
**fw,
+const char *fw_name);
+void amdgpu_ucode_release(const struct firmware **fw);
 bool amdgpu_ucode_hdr_version(union amdgpu_firmware_header *hdr,
uint16_t hdr_major, uint16_t hdr_minor);
 
-- 
2.34.1



[PATCH v6 04/45] drm/amd: Convert SMUv13 microcode to use `amdgpu_ucode_ip_version_decode`

2023-01-04 Thread Mario Limonciello
The special case for the one dGPU has been moved into
`amdgpu_ucode_ip_version_decode`, so simplify this code.

Signed-off-by: Mario Limonciello 
Acked-by: Christian König 
Reviewed-by: Alex Deucher 
---
 drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c | 12 ++--
 1 file changed, 2 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
index 0ac9cac805f9..506a49a4b425 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
@@ -88,7 +88,6 @@ static const int link_speed[] = {25, 50, 80, 160};
 int smu_v13_0_init_microcode(struct smu_context *smu)
 {
struct amdgpu_device *adev = smu->adev;
-   const char *chip_name;
char fw_name[30];
char ucode_prefix[30];
int err = 0;
@@ -100,16 +99,9 @@ int smu_v13_0_init_microcode(struct smu_context *smu)
if (amdgpu_sriov_vf(adev))
return 0;
 
-   switch (adev->ip_versions[MP1_HWIP][0]) {
-   case IP_VERSION(13, 0, 2):
-   chip_name = "aldebaran_smc";
-   break;
-   default:
-   amdgpu_ucode_ip_version_decode(adev, MP1_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
-   chip_name = ucode_prefix;
-   }
+   amdgpu_ucode_ip_version_decode(adev, MP1_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
 
-   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", chip_name);
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", ucode_prefix);
 
err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
if (err)
-- 
2.34.1



[PATCH v6 03/45] drm/amd: Convert SMUv11 microcode to use `amdgpu_ucode_ip_version_decode`

2023-01-04 Thread Mario Limonciello
Remove the special casing from SMU v11 code. No intended functional
changes.

Signed-off-by: Mario Limonciello 
Acked-by: Christian König 
Reviewed-by: Alex Deucher 
---
 .../gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c| 35 ++-
 1 file changed, 3 insertions(+), 32 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
index ad66d57aa102..d4756bd30830 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
@@ -93,7 +93,7 @@ static void smu_v11_0_poll_baco_exit(struct smu_context *smu)
 int smu_v11_0_init_microcode(struct smu_context *smu)
 {
struct amdgpu_device *adev = smu->adev;
-   const char *chip_name;
+   char ucode_prefix[30];
char fw_name[SMU_FW_NAME_LEN];
int err = 0;
const struct smc_firmware_header_v1_0 *hdr;
@@ -105,38 +105,9 @@ int smu_v11_0_init_microcode(struct smu_context *smu)
 (adev->ip_versions[MP1_HWIP][0] == IP_VERSION(11, 0, 7
return 0;
 
-   switch (adev->ip_versions[MP1_HWIP][0]) {
-   case IP_VERSION(11, 0, 0):
-   chip_name = "navi10";
-   break;
-   case IP_VERSION(11, 0, 5):
-   chip_name = "navi14";
-   break;
-   case IP_VERSION(11, 0, 9):
-   chip_name = "navi12";
-   break;
-   case IP_VERSION(11, 0, 7):
-   chip_name = "sienna_cichlid";
-   break;
-   case IP_VERSION(11, 0, 11):
-   chip_name = "navy_flounder";
-   break;
-   case IP_VERSION(11, 0, 12):
-   chip_name = "dimgrey_cavefish";
-   break;
-   case IP_VERSION(11, 0, 13):
-   chip_name = "beige_goby";
-   break;
-   case IP_VERSION(11, 0, 2):
-   chip_name = "arcturus";
-   break;
-   default:
-   dev_err(adev->dev, "Unsupported IP version 0x%x\n",
-   adev->ip_versions[MP1_HWIP][0]);
-   return -EINVAL;
-   }
+   amdgpu_ucode_ip_version_decode(adev, MP1_HWIP, ucode_prefix, 
sizeof(ucode_prefix));
 
-   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_smc.bin", chip_name);
+   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", ucode_prefix);
 
err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
if (err)
-- 
2.34.1



[PATCH v6 02/45] drm/amd: Add a legacy mapping to "amdgpu_ucode_ip_version_decode"

2023-01-04 Thread Mario Limonciello
This will allow other parts of the driver that currently special
case firmware file names to before IP version style naming to just
have a single call to `amdgpu_ucode_ip_version_decode`.

Signed-off-by: Mario Limonciello 
Acked-by: Christian König 
Reviewed-by: Alex Deucher 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 221 ++
 1 file changed, 221 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
index 5cb62e6249c2..eafcddce58d3 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
@@ -1059,12 +1059,233 @@ int amdgpu_ucode_init_bo(struct amdgpu_device *adev)
return 0;
 }
 
+static const char *amdgpu_ucode_legacy_naming(struct amdgpu_device *adev, int 
block_type)
+{
+   if (block_type == MP0_HWIP) {
+   switch (adev->ip_versions[MP0_HWIP][0]) {
+   case IP_VERSION(9, 0, 0):
+   switch (adev->asic_type) {
+   case CHIP_VEGA10:
+   return "vega10";
+   case CHIP_VEGA12:
+   return "vega12";
+   default:
+   return NULL;
+   }
+   break;
+   case IP_VERSION(10, 0, 0):
+   case IP_VERSION(10, 0, 1):
+   if (adev->asic_type == CHIP_RAVEN) {
+   if (adev->apu_flags & AMD_APU_IS_RAVEN2)
+   return "raven2";
+   else if (adev->apu_flags & AMD_APU_IS_PICASSO)
+   return "picasso";
+   return "raven";
+   }
+   break;
+   case IP_VERSION(11, 0, 0):
+   return "navi10";
+   case IP_VERSION(11, 0, 2):
+   return "vega20";
+   case IP_VERSION(11, 0, 4):
+   return "arcturus";
+   case IP_VERSION(11, 0, 5):
+   return "navi14";
+   case IP_VERSION(11, 0, 7):
+   return "sienna_cichlid";
+   case IP_VERSION(11, 0, 9):
+   return "navi12";
+   case IP_VERSION(11, 0, 11):
+   return "navy_flounder";
+   case IP_VERSION(11, 0, 12):
+   return "dimgrey_cavefish";
+   case IP_VERSION(11, 0, 13):
+   return "beige_goby";
+   case IP_VERSION(11, 5, 0):
+   return "vangogh";
+   case IP_VERSION(12, 0, 1):
+   if (adev->asic_type == CHIP_RENOIR) {
+   if (adev->apu_flags & AMD_APU_IS_RENOIR)
+   return "renoir";
+   return "green_sardine";
+   }
+   break;
+   case IP_VERSION(13, 0, 2):
+   return "aldebaran";
+   case IP_VERSION(13, 0, 1):
+   case IP_VERSION(13, 0, 3):
+   return "yellow_carp";
+   }
+   } else if (block_type == MP1_HWIP) {
+   switch (adev->ip_versions[MP1_HWIP][0]) {
+   case IP_VERSION(9, 0, 0):
+   case IP_VERSION(10, 0, 0):
+   case IP_VERSION(10, 0, 1):
+   case IP_VERSION(11, 0, 2):
+   if (adev->asic_type == CHIP_ARCTURUS)
+   return "arcturus_smc";
+   return NULL;
+   case IP_VERSION(11, 0, 0):
+   return "navi10_smc";
+   case IP_VERSION(11, 0, 5):
+   return "navi14_smc";
+   case IP_VERSION(11, 0, 9):
+   return "navi12_smc";
+   case IP_VERSION(11, 0, 7):
+   return "sienna_cichlid_smc";
+   case IP_VERSION(11, 0, 11):
+   return "navy_flounder_smc";
+   case IP_VERSION(11, 0, 12):
+   return "dimgrey_cavefish_smc";
+   case IP_VERSION(11, 0, 13):
+   return "beige_goby_smc";
+   case IP_VERSION(13, 0, 2):
+   return "aldebaran_smc";
+   }
+   } else if (block_type == SDMA0_HWIP) {
+   switch (adev->ip_versions[SDMA0_HWIP][0]) {
+   case IP_VERSION(4, 0, 0):
+   return "vega10_sdma";
+   case IP_VERSION(4, 0, 1):
+   return "vega12_sdma";
+   case IP_VERSION(4, 1, 0):
+   case IP_VERSION(4, 1, 1):
+   if (adev->apu_flags & AMD_APU_IS_RAVEN2)
+   return "raven2_sdma";
+ 

[PATCH v6 01/45] drm/amd: Delay removal of the firmware framebuffer

2023-01-04 Thread Mario Limonciello
Removing the firmware framebuffer from the driver means that even
if the driver doesn't support the IP blocks in a GPU it will no
longer be functional after the driver fails to initialize.

This change will ensure that unsupported IP blocks at least cause
the driver to work with the EFI framebuffer.

Cc: sta...@vger.kernel.org
Suggested-by: Alex Deucher 
Reviewed-by: Alex Deucher 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 8 
 drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c| 6 --
 2 files changed, 8 insertions(+), 6 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
index 9a1a5c2864a0..cdb681398a99 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
@@ -37,6 +37,7 @@
 #include 
 
 #include 
+#include 
 #include 
 #include 
 #include 
@@ -89,6 +90,8 @@ MODULE_FIRMWARE("amdgpu/navi12_gpu_info.bin");
 #define AMDGPU_MAX_RETRY_LIMIT 2
 #define AMDGPU_RETRY_SRIOV_RESET(r) ((r) == -EBUSY || (r) == -ETIMEDOUT || (r) 
== -EINVAL)
 
+static const struct drm_driver amdgpu_kms_driver;
+
 const char *amdgpu_asic_name[] = {
"TAHITI",
"PITCAIRN",
@@ -3685,6 +3688,11 @@ int amdgpu_device_init(struct amdgpu_device *adev,
if (r)
return r;
 
+   /* Get rid of things like offb */
+   r = drm_aperture_remove_conflicting_pci_framebuffers(adev->pdev, 
&amdgpu_kms_driver);
+   if (r)
+   return r;
+
/* Enable TMZ based on IP_VERSION */
amdgpu_gmc_tmz_set(adev);
 
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
index db7e34eacc35..b9f14ec9edb2 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
@@ -23,7 +23,6 @@
  */
 
 #include 
-#include 
 #include 
 #include 
 #include 
@@ -2096,11 +2095,6 @@ static int amdgpu_pci_probe(struct pci_dev *pdev,
}
 #endif
 
-   /* Get rid of things like offb */
-   ret = drm_aperture_remove_conflicting_pci_framebuffers(pdev, 
&amdgpu_kms_driver);
-   if (ret)
-   return ret;
-
adev = devm_drm_dev_alloc(&pdev->dev, &amdgpu_kms_driver, 
typeof(*adev), ddev);
if (IS_ERR(adev))
return PTR_ERR(adev);
-- 
2.34.1



[PATCH v6 00/45] Recover from failure to probe GPU

2023-01-04 Thread Mario Limonciello
One of the first thing that KMS drivers do during initialization is
destroy the system firmware framebuffer by means of
`drm_aperture_remove_conflicting_pci_framebuffers`

This means that if for any reason the GPU failed to probe the user
will be stuck with at best a screen frozen at the last thing that
was shown before the KMS driver continued it's probe.

The problem is most pronounced when new GPU support is introduced
because users will need to have a recent linux-firmware snapshot
on their system when they boot a kernel with matching support.

However the problem is further exaggerated in the case of amdgpu because
it has migrated to "IP discovery" where amdgpu will attempt to load
on "ALL" AMD GPUs even if the driver is missing support for IP blocks
contained in that GPU.

IP discovery requires some probing and isn't run until after the
framebuffer has been destroyed.

This means a situation can occur where a user purchases a new GPU not
yet supported by a distribution and when booting the installer it will
"freeze" even if the distribution doesn't have the matching kernel support
for those IP blocks.

The perfect example of this is Ubuntu 22.10 and the new dGPUs just
launched by AMD.  The installation media ships with kernel 5.19 (which
has IP discovery) but the amdgpu support for those IP blocks landed in
kernel 6.0. The matching linux-firmware was released after 22.10's launch.
The screen will freeze without nomodeset. Even if a user manages to install
and then upgrades to kernel 6.0 after install they'll still have the
problem of missing firmware, and the same experience.

This is quite jarring for users, particularly if they don't know
that they have to use "nomodeset" to install.

To help the situation make changes to GPU discovery:
1) Delay releasing the firmware framebuffer until after early_init
completed.  This will help the situation of an older kernel that doesn't
yet support the IP blocks probing a new GPU. IP discovery will have failed.
2) Request loading all PSP, VCN, SDMA, SMU, DMCUB, MES and GC microcode
into memory during early_init. This will help the situation of new enough
kernel for the IP discovery phase to otherwise pass but missing microcode
from linux-firmware.git.

v5->v6:
 * Fix arguments for amdgpu_ucode_release to allow clearing pointer
 * Fix whitespace mistake in VCN
 * Pick up tags for 43 of the patches
v4->v5:
 * Rename amdgpu_ucode_load to amdgpu_ucode_request
 * Add and utilize amdgpu_ucode_release throughout existing patches
 * Update all amdgpu code to stop using request_firmware and
   release_firmware for microcode
 * Drop export of amdgpu_ucode_validate outside of amdgpu_ucode.c
 * Pick up relevant tags for some patches
v3->v4:
 * Rework to delay framebuffer release until early_init is done
 * Make IP load microcode during early init phase
 * Add SMU and DMCUB checks for early_init loading
 * Add some new helper code for wrapping request_firmware calls (needed for
   early_init to return something besides -ENOENT)
v2->v3:
 * Pick up tags for patches 1-10
 * Rework patch 11 to not validate during discovery
 * Fix bugs with GFX9 due to gfx.num_gfx_rings not being set during
   discovery
 * Fix naming scheme for SDMA on dGPUs
v1->v2:
 * Take the suggestion from v1 thread to delay the framebuffer release
   until ip discovery is done. This patch is CC to stable to that older
   stable kernels with IP discovery won't try to probe unknown IP.
 * Drop changes to drm aperature.
 * Fetch SDMA, VCN, MES, GC and PSP microcode during IP discovery.

Mario Limonciello (27):
  drm/amd: Delay removal of the firmware framebuffer
  drm/amd: Add a legacy mapping to "amdgpu_ucode_ip_version_decode"
  drm/amd: Convert SMUv11 microcode to use
`amdgpu_ucode_ip_version_decode`
  drm/amd: Convert SMUv13 microcode to use
`amdgpu_ucode_ip_version_decode`
  drm/amd: Add a new helper for loading/validating microcode
  drm/amd: Use `amdgpu_ucode_request` helper for SDMA
  drm/amd: Convert SDMA to use `amdgpu_ucode_ip_version_decode`
  drm/amd: Make SDMA firmware load failures less noisy.
  drm/amd: Use `amdgpu_ucode_*` helpers for VCN
  drm/amd: Load VCN microcode during early_init
  drm/amd: Load MES microcode during early_init
  drm/amd: Use `amdgpu_ucode_*` helpers for MES
  drm/amd: Remove superfluous assignment for `adev->mes.adev`
  drm/amd: Use `amdgpu_ucode_*` helpers for GFX9
  drm/amd: Load GFX9 microcode during early_init
  drm/amd: Use `amdgpu_ucode_*` helpers for GFX10
  drm/amd: Load GFX10 microcode during early_init
  drm/amd: Use `amdgpu_ucode_*` helpers for GFX11
  drm/amd: Load GFX11 microcode during early_init
  drm/amd: Parse both v1 and v2 TA microcode headers using same function
  drm/amd: Avoid BUG() for case of SRIOV missing IP version
  drm/amd: Load PSP microcode during early_init
  drm/amd: Use `amdgpu_ucode_*` helpers for PSP
  drm/amd/display: Load DMUB microcode during early_init
  drm/amd: Use `amdgpu_ucode_release` helper for DMUB
  drm/amd: Use `amd

[pull] amdgpu, amdkfd drm-fixes-6.2

2023-01-04 Thread Alex Deucher
Hi Dave, Daniel,

Fixes for 6.2.

The following changes since commit c8de526215fdab9f2dd0d9675582cf9f1391a919:

  Merge tag 'drm-misc-next-fixes-2023-01-03' of 
git://anongit.freedesktop.org/drm/drm-misc into drm-fixes (2023-01-03 21:02:57 
+0100)

are available in the Git repository at:

  https://gitlab.freedesktop.org/agd5f/linux.git 
tags/amd-drm-fixes-6.2-2023-01-04

for you to fetch changes up to 6fe6ece398f7431784847e922a2c8c385dc58a35:

  Revert "drm/amd/display: Enable Freesync Video Mode by default" (2023-01-04 
22:29:32 -0500)


amd-drm-fixes-6.2-2023-01-04:

amdgpu:
- DCN 3.2 fix
- Display fix

amdkfd:
- Fix kernel warning


Michel Dänzer (1):
  Revert "drm/amd/display: Enable Freesync Video Mode by default"

Mukul Joshi (1):
  drm/amdkfd: Fix kernel warning during topology setup

Samson Tam (1):
  drm/amd/display: Uninitialized variables causing 4k60 UCLK to stay at 
DPM1 and not DPM0

 drivers/gpu/drm/amd/amdgpu/amdgpu.h|  1 +
 drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c| 27 ++
 drivers/gpu/drm/amd/amdkfd/kfd_topology.c  |  2 +-
 drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c  | 12 ++
 .../dc/dml/dcn32/display_mode_vba_util_32.c|  6 ++---
 5 files changed, 39 insertions(+), 9 deletions(-)


Re: [PATCH 2/2] drm/amd: update securedisplay_cmd to ta_securedisplay_cmd

2023-01-04 Thread Alex Deucher
These two patches should be squashed together to avoid breaking the build.

Alex

On Wed, Jan 4, 2023 at 8:04 PM Aaron Liu  wrote:
>
> This patch updates securedisplay_cmd to ta_securedisplay_cmd
> starting from amd-ta_securedisplay-v27.00.00.08.
>
> Signed-off-by: Aaron Liu 
> ---
>  drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c   | 2 +-
>  drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c | 8 
>  drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h | 2 +-
>  drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c | 2 +-
>  4 files changed, 7 insertions(+), 7 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
> index 0706afb11577..2bebda7de604 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
> @@ -1907,7 +1907,7 @@ int psp_rap_invoke(struct psp_context *psp, uint32_t 
> ta_cmd_id, enum ta_rap_stat
>  static int psp_securedisplay_initialize(struct psp_context *psp)
>  {
> int ret;
> -   struct securedisplay_cmd *securedisplay_cmd;
> +   struct ta_securedisplay_cmd *securedisplay_cmd;
>
> /*
>  * TODO: bypass the initialize in sriov for now
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c 
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
> index 2c1d82fc4c34..8ed0e073656f 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
> @@ -77,11 +77,11 @@ void psp_securedisplay_parse_resp_status(struct 
> psp_context *psp,
> }
>  }
>
> -void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
> securedisplay_cmd **cmd,
> +void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
> ta_securedisplay_cmd **cmd,
> enum ta_securedisplay_command command_id)
>  {
> -   *cmd = (struct securedisplay_cmd 
> *)psp->securedisplay_context.context.mem_context.shared_buf;
> -   memset(*cmd, 0, sizeof(struct securedisplay_cmd));
> +   *cmd = (struct ta_securedisplay_cmd 
> *)psp->securedisplay_context.context.mem_context.shared_buf;
> +   memset(*cmd, 0, sizeof(struct ta_securedisplay_cmd));
> (*cmd)->status = TA_SECUREDISPLAY_STATUS__GENERIC_FAILURE;
> (*cmd)->cmd_id = command_id;
>  }
> @@ -93,7 +93,7 @@ static ssize_t amdgpu_securedisplay_debugfs_write(struct 
> file *f, const char __u
>  {
> struct amdgpu_device *adev = (struct amdgpu_device 
> *)file_inode(f)->i_private;
> struct psp_context *psp = &adev->psp;
> -   struct securedisplay_cmd *securedisplay_cmd;
> +   struct ta_securedisplay_cmd *securedisplay_cmd;
> struct drm_device *dev = adev_to_drm(adev);
> uint32_t phy_id;
> uint32_t op;
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h 
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
> index fe98574748f4..456ad68ed4b2 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
> @@ -30,7 +30,7 @@
>  void amdgpu_securedisplay_debugfs_init(struct amdgpu_device *adev);
>  void psp_securedisplay_parse_resp_status(struct psp_context *psp,
> enum ta_securedisplay_status status);
> -void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
> securedisplay_cmd **cmd,
> +void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
> ta_securedisplay_cmd **cmd,
> enum ta_securedisplay_command command_id);
>
>  #endif
> diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c 
> b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
> index ad73e5855580..8841c447d0e2 100644
> --- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
> +++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
> @@ -103,7 +103,7 @@ static void amdgpu_dm_crtc_notify_ta_to_read(struct 
> work_struct *work)
>  {
> struct secure_display_context *secure_display_ctx;
> struct psp_context *psp;
> -   struct securedisplay_cmd *securedisplay_cmd;
> +   struct ta_securedisplay_cmd *securedisplay_cmd;
> struct drm_crtc *crtc;
> struct dc_stream_state *stream;
> uint8_t phy_inst;
> --
> 2.39.0
>


[PATCH 8/8] drm/amd/pm: drop the support for manual fan speed setting on SMU13.0.7

2023-01-04 Thread Evan Quan
Due to lack of support from PMFW.

Signed-off-by: Evan Quan 
Change-Id: I8439e72b95ad2fdf8cfdf1edc4d9c8af58109dc3
---
 drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c | 5 +
 1 file changed, 5 insertions(+)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c
index 3608540f2034..c7fa203ec7e8 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c
@@ -1736,4 +1736,9 @@ void smu_v13_0_7_set_ppt_funcs(struct smu_context *smu)
  
BIT_ULL(AMD_SYSFS_IF_PP_DPM_DCEFCLK_BIT) |
  
BIT_ULL(AMD_SYSFS_IF_PP_SCLK_OD_BIT) |
  
BIT_ULL(AMD_SYSFS_IF_PP_MCLK_OD_BIT));
+   /* Drop the support for manual fan speed(RPM and PWM) setting */
+   smu->adev->pm.hwmon_if_attr_mode[AMD_HWMON_IF_PWM1_ENABLE_BIT] &= 
~S_IWUSR;
+   smu->adev->pm.hwmon_if_attr_mode[AMD_HWMON_IF_PWM1_BIT] &= ~S_IWUSR;
+   smu->adev->pm.hwmon_if_attr_mode[AMD_HWMON_IF_FAN1_ENABLE_BIT] &= 
~S_IWUSR;
+   smu->adev->pm.hwmon_if_attr_mode[AMD_HWMON_IF_FAN1_TARGET_BIT] &= 
~S_IWUSR;
 }
-- 
2.34.1



[PATCH 6/8] drm/amd/pm: refine the checks for hwmon interfaces support

2023-01-04 Thread Evan Quan
Make the code more clean and readable with no real logics
change.

Signed-off-by: Evan Quan 
Change-Id: I2c9e661ed6b855ea6ddd8554dd4f975cd2faa24f
---
 drivers/gpu/drm/amd/pm/amdgpu_pm.c | 329 ++---
 1 file changed, 206 insertions(+), 123 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/amdgpu_pm.c 
b/drivers/gpu/drm/amd/pm/amdgpu_pm.c
index c69db29eea24..dcfc0d605fc5 100644
--- a/drivers/gpu/drm/amd/pm/amdgpu_pm.c
+++ b/drivers/gpu/drm/amd/pm/amdgpu_pm.c
@@ -3155,161 +3155,242 @@ static umode_t hwmon_attributes_visible(struct 
kobject *kobj,
struct device *dev = kobj_to_dev(kobj);
struct amdgpu_device *adev = dev_get_drvdata(dev);
umode_t effective_mode = attr->mode;
+   uint32_t if_bit;
+
+   if (attr == &sensor_dev_attr_temp1_input.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP1_INPUT_BIT;
+   else if (attr == &sensor_dev_attr_temp1_crit.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP1_CRIT_BIT;
+   else if (attr == &sensor_dev_attr_temp1_crit_hyst.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP1_CRIT_HYST_BIT;
+   else if (attr == &sensor_dev_attr_temp2_input.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP2_INPUT_BIT;
+   else if (attr == &sensor_dev_attr_temp2_crit.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP2_CRIT_BIT;
+   else if (attr == &sensor_dev_attr_temp2_crit_hyst.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP2_CRIT_HYST_BIT;
+   else if (attr == &sensor_dev_attr_temp3_input.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP3_INPUT_BIT;
+   else if (attr == &sensor_dev_attr_temp3_crit.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP3_CRIT_BIT;
+   else if (attr == &sensor_dev_attr_temp3_crit_hyst.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP3_CRIT_HYST_BIT;
+   else if (attr == &sensor_dev_attr_temp1_emergency.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP1_EMERGENCY_BIT;
+   else if (attr == &sensor_dev_attr_temp2_emergency.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP2_EMERGENCY_BIT;
+   else if (attr == &sensor_dev_attr_temp3_emergency.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP3_EMERGENCY_BIT;
+   else if (attr == &sensor_dev_attr_temp1_label.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP1_LABEL_BIT;
+   else if (attr == &sensor_dev_attr_temp2_label.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP2_LABEL_BIT;
+   else if (attr == &sensor_dev_attr_temp3_label.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_TEMP3_LABEL_BIT;
+   else if (attr == &sensor_dev_attr_pwm1.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_PWM1_BIT;
+   else if (attr == &sensor_dev_attr_pwm1_enable.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_PWM1_ENABLE_BIT;
+   else if (attr == &sensor_dev_attr_pwm1_min.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_PWM1_MIN_BIT;
+   else if (attr == &sensor_dev_attr_pwm1_max.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_PWM1_MAX_BIT;
+   else if (attr == &sensor_dev_attr_fan1_input.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_FAN1_INPUT_BIT;
+   else if (attr == &sensor_dev_attr_fan1_min.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_FAN1_MIN_BIT;
+   else if (attr == &sensor_dev_attr_fan1_max.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_FAN1_MAX_BIT;
+   else if (attr == &sensor_dev_attr_fan1_target.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_FAN1_TARGET_BIT;
+   else if (attr == &sensor_dev_attr_fan1_enable.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_FAN1_ENABLE_BIT;
+   else if (attr == &sensor_dev_attr_in0_input.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_IN0_INPUT_BIT;
+   else if (attr == &sensor_dev_attr_in0_label.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_IN0_LABEL_BIT;
+   else if (attr == &sensor_dev_attr_in1_input.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_IN1_INPUT_BIT;
+   else if (attr == &sensor_dev_attr_in1_label.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_IN1_LABEL_BIT;
+   else if (attr == &sensor_dev_attr_power1_average.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_POWER1_AVERAGE_BIT;
+   else if (attr == &sensor_dev_attr_power1_cap_max.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_POWER1_CAP_MAX_BIT;
+   else if (attr == &sensor_dev_attr_power1_cap_min.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_POWER1_CAP_MIN_BIT;
+   else if (attr == &sensor_dev_attr_power1_cap.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_POWER1_CAP_BIT;
+   else if (attr == &sensor_dev_attr_power1_cap_default.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_POWER1_CAP_DEFAULT_BIT;
+   else if (attr == &sensor_dev_attr_power1_label.dev_attr.attr)
+   if_bit = AMD_HWMON_IF_POWER1_LABEL_BIT;
+   else if (a

[PATCH 7/8] drm/amd/pm: drop the support for manual fan speed setting on SMU13.0.0

2023-01-04 Thread Evan Quan
Due to lack of support from PMFW.

Signed-off-by: Evan Quan 
Change-Id: I5d466d3d521b26a484bd837e173b9b289d4020ec
---
 drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c | 5 +
 1 file changed, 5 insertions(+)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c
index 75c9f510e713..59cd68862973 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c
@@ -2061,4 +2061,9 @@ void smu_v13_0_0_set_ppt_funcs(struct smu_context *smu)
  
BIT_ULL(AMD_SYSFS_IF_PP_DPM_DCEFCLK_BIT) |
  
BIT_ULL(AMD_SYSFS_IF_PP_SCLK_OD_BIT) |
  
BIT_ULL(AMD_SYSFS_IF_PP_MCLK_OD_BIT));
+   /* Drop the support for manual fan speed(RPM and PWM) setting */
+   smu->adev->pm.hwmon_if_attr_mode[AMD_HWMON_IF_PWM1_ENABLE_BIT] &= 
~S_IWUSR;
+   smu->adev->pm.hwmon_if_attr_mode[AMD_HWMON_IF_PWM1_BIT] &= ~S_IWUSR;
+   smu->adev->pm.hwmon_if_attr_mode[AMD_HWMON_IF_FAN1_ENABLE_BIT] &= 
~S_IWUSR;
+   smu->adev->pm.hwmon_if_attr_mode[AMD_HWMON_IF_FAN1_TARGET_BIT] &= 
~S_IWUSR;
 }
-- 
2.34.1



[PATCH 5/8] drm/amdgpu: add bitmask controll for hwmon related interfaces

2023-01-04 Thread Evan Quan
Via this, the logic for adding/dropping the support for some specific
hwmon interface can be greatly simplified.

Signed-off-by: Evan Quan 
Change-Id: Ia85082c964d80d1c43dd2d8bf51592aba968e364
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_device.c |  7 ++-
 drivers/gpu/drm/amd/pm/inc/amdgpu_dpm.h| 52 ++
 2 files changed, 57 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
index b1943336551f..c7c95b3c370e 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
@@ -3640,13 +3640,16 @@ int amdgpu_device_init(struct amdgpu_device *adev,
ratelimit_set_flags(&adev->throttling_logging_rs, 
RATELIMIT_MSG_ON_RELEASE);
 
/*
-* At default, all sysfs interfaces are claimed to be supported.
-* And every sysfs interface is readable and writable. However,
+* At default, all sysfs and hwmon interfaces are claimed to be 
supported.
+* And every interface is readable and writable. However,
 * each ASIC can have its own setting by overriding these.
 */
adev->pm.sysfs_if_supported = AMD_SYSFS_IF_BITMASK_ALL_SUPPORTED;
for (i = 0; i < AMD_MAX_NUMBER_OF_SYSFS_IF_SUPPORTED; i++)
adev->pm.sysfs_if_attr_mode[i] = S_IRUGO | S_IWUGO;
+   adev->pm.hwmon_if_supported = AMD_HWMON_IF_BITMASK_ALL_SUPPORTED;
+   for (i = 0; i < AMD_MAX_NUMBER_OF_HWMON_IF_SUPPORTED; i++)
+   adev->pm.hwmon_if_attr_mode[i] = S_IRUGO | S_IWUSR;
 
/* Registers mapping */
/* TODO: block userspace mapping of io register */
diff --git a/drivers/gpu/drm/amd/pm/inc/amdgpu_dpm.h 
b/drivers/gpu/drm/amd/pm/inc/amdgpu_dpm.h
index bbee77087226..5635ac74bf62 100644
--- a/drivers/gpu/drm/amd/pm/inc/amdgpu_dpm.h
+++ b/drivers/gpu/drm/amd/pm/inc/amdgpu_dpm.h
@@ -345,6 +345,54 @@ struct config_table_setting
 #define AMD_SYSFS_IF_BITMASK(if_bit)   (1ULL << 
(if_bit))
 #define AMD_SYSFS_IF_BITMASK_ALL_SUPPORTED ULLONG_MAX
 
+/* Bitmasks for controlling which hwmon interface to support */
+#define AMD_HWMON_IF_TEMP1_INPUT_BIT   0U
+#define AMD_HWMON_IF_TEMP1_CRIT_BIT1U
+#define AMD_HWMON_IF_TEMP1_CRIT_HYST_BIT   2U
+#define AMD_HWMON_IF_TEMP2_INPUT_BIT   3U
+#define AMD_HWMON_IF_TEMP2_CRIT_BIT4U
+#define AMD_HWMON_IF_TEMP2_CRIT_HYST_BIT   5U
+#define AMD_HWMON_IF_TEMP3_INPUT_BIT   6U
+#define AMD_HWMON_IF_TEMP3_CRIT_BIT7U
+#define AMD_HWMON_IF_TEMP3_CRIT_HYST_BIT   8U
+#define AMD_HWMON_IF_TEMP1_EMERGENCY_BIT   9U
+#define AMD_HWMON_IF_TEMP2_EMERGENCY_BIT   10U
+#define AMD_HWMON_IF_TEMP3_EMERGENCY_BIT   11U
+#define AMD_HWMON_IF_TEMP1_LABEL_BIT   12U
+#define AMD_HWMON_IF_TEMP2_LABEL_BIT   13U
+#define AMD_HWMON_IF_TEMP3_LABEL_BIT   14U
+#define AMD_HWMON_IF_PWM1_BIT  15U
+#define AMD_HWMON_IF_PWM1_ENABLE_BIT   16U
+#define AMD_HWMON_IF_PWM1_MIN_BIT  17U
+#define AMD_HWMON_IF_PWM1_MAX_BIT  18U
+#define AMD_HWMON_IF_FAN1_INPUT_BIT19U
+#define AMD_HWMON_IF_FAN1_MIN_BIT  20U
+#define AMD_HWMON_IF_FAN1_MAX_BIT  21U
+#define AMD_HWMON_IF_FAN1_TARGET_BIT   22U
+#define AMD_HWMON_IF_FAN1_ENABLE_BIT   23U
+#define AMD_HWMON_IF_IN0_INPUT_BIT 24U
+#define AMD_HWMON_IF_IN0_LABEL_BIT 25U
+#define AMD_HWMON_IF_IN1_INPUT_BIT 26U
+#define AMD_HWMON_IF_IN1_LABEL_BIT 27U
+#define AMD_HWMON_IF_POWER1_AVERAGE_BIT28U
+#define AMD_HWMON_IF_POWER1_CAP_MAX_BIT29U
+#define AMD_HWMON_IF_POWER1_CAP_MIN_BIT30U
+#define AMD_HWMON_IF_POWER1_CAP_BIT31U
+#define AMD_HWMON_IF_POWER1_CAP_DEFAULT_BIT32U
+#define AMD_HWMON_IF_POWER1_LABEL_BIT  33U
+#define AMD_HWMON_IF_POWER2_AVERAGE_BIT34U
+#define AMD_HWMON_IF_POWER2_CAP_MAX_BIT35U
+#define AMD_HWMON_IF_POWER2_CAP_MIN_BIT36U
+#define AMD_HWMON_IF_POWER2_CAP_BIT37U
+#define AMD_HWMON_IF_POWER2_CAP_DEFAULT_BIT38U
+#define AMD_HWMON_IF_POWER2_LABEL_BIT  39U
+#define AMD_HWMON_IF_FREQ1_INPUT_BIT   4

[PATCH 4/8] drm/amd/pm: drop the support for legacy sysfs interfaces on SMU13.0.7

2023-01-04 Thread Evan Quan
Those legacy sysfs interfaces are actually not supported. Their
outputs are confusing.

Signed-off-by: Evan Quan 
Change-Id: Iba89f12ae3e79b856d6c0904b371590b6fd0d327
---
 drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c | 9 +
 1 file changed, 9 insertions(+)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c
index e87db7e02e8a..3608540f2034 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c
@@ -1727,4 +1727,13 @@ void smu_v13_0_7_set_ppt_funcs(struct smu_context *smu)
smu->pwr_src_map = smu_v13_0_7_pwr_src_map;
smu->workload_map = smu_v13_0_7_workload_map;
smu_v13_0_set_smu_mailbox_registers(smu);
+   /* Unset those legacy interfaces which are not supported */
+   smu->adev->pm.sysfs_if_supported &= 
~(BIT_ULL(AMD_SYSFS_IF_POWER_DPM_STATE_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_NUM_STATES_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_CUR_STATE_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_FORCE_STATE_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_TABLE_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_DPM_DCEFCLK_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_SCLK_OD_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_MCLK_OD_BIT));
 }
-- 
2.34.1



[PATCH 1/8] drm/amdgpu: add bitmask controll for power related sysfs interfaces

2023-01-04 Thread Evan Quan
Via this, the logic for adding/dropping the support for some specific
sysfs interface can be greatly simplified.

Signed-off-by: Evan Quan 
Change-Id: Ica470cb8afd5b6cf7cc2a47b8310746b6c3b6f97
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_device.c |   9 ++
 drivers/gpu/drm/amd/pm/amdgpu_pm.c | 115 +++--
 drivers/gpu/drm/amd/pm/inc/amdgpu_dpm.h|  37 +++
 drivers/gpu/drm/amd/pm/inc/amdgpu_pm.h |  16 +--
 4 files changed, 141 insertions(+), 36 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
index 2017b3466612..b1943336551f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
@@ -3639,6 +3639,15 @@ int amdgpu_device_init(struct amdgpu_device *adev,
ratelimit_state_init(&adev->throttling_logging_rs, (60 - 1) * HZ, 1);
ratelimit_set_flags(&adev->throttling_logging_rs, 
RATELIMIT_MSG_ON_RELEASE);
 
+   /*
+* At default, all sysfs interfaces are claimed to be supported.
+* And every sysfs interface is readable and writable. However,
+* each ASIC can have its own setting by overriding these.
+*/
+   adev->pm.sysfs_if_supported = AMD_SYSFS_IF_BITMASK_ALL_SUPPORTED;
+   for (i = 0; i < AMD_MAX_NUMBER_OF_SYSFS_IF_SUPPORTED; i++)
+   adev->pm.sysfs_if_attr_mode[i] = S_IRUGO | S_IWUGO;
+
/* Registers mapping */
/* TODO: block userspace mapping of io register */
if (adev->asic_type >= CHIP_BONAIRE) {
diff --git a/drivers/gpu/drm/amd/pm/amdgpu_pm.c 
b/drivers/gpu/drm/amd/pm/amdgpu_pm.c
index 236657eece47..fb6a7d45693a 100644
--- a/drivers/gpu/drm/amd/pm/amdgpu_pm.c
+++ b/drivers/gpu/drm/amd/pm/amdgpu_pm.c
@@ -1913,36 +1913,92 @@ static int ss_bias_attr_update(struct amdgpu_device 
*adev, struct amdgpu_device_
 }
 
 static struct amdgpu_device_attr amdgpu_device_attrs[] = {
-   AMDGPU_DEVICE_ATTR_RW(power_dpm_state,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(power_dpm_force_performance_level,
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RO(pp_num_states,
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RO(pp_cur_state, 
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_force_state,   
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_table, 
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_dpm_sclk,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_dpm_mclk,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_dpm_socclk,
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_dpm_fclk,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_dpm_vclk,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_dpm_dclk,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_dpm_dcefclk,   
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_dpm_pcie,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_sclk_od,   
ATTR_FLAG_BASIC),
-   AMDGPU_DEVICE_ATTR_RW(pp_mclk_od,   
ATTR_FLAG_BASIC),
-   AMDGPU_DEVICE_ATTR_RW(pp_power_profile_mode,
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(pp_od_clk_voltage,
ATTR_FLAG_BASIC),
-   AMDGPU_DEVICE_ATTR_RO(gpu_busy_percent, 
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RO(mem_busy_percent, 
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RO(pcie_bw,  
ATTR_FLAG_BASIC),
-   AMDGPU_DEVICE_ATTR_RW(pp_features,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RO(unique_id,
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RW(thermal_throttling_logging,   
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RO(gpu_metrics,  
ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
-   AMDGPU_DEVICE_ATTR_RO(smartshift_apu_power, 
ATTR_FLAG_BASIC,
+   AMDGPU_DEVICE_ATTR_RW(power_dpm_state,
+ AMD_SYSFS_IF_POWER_DPM_STATE_BIT,
+ ATTR_FLAG_BASIC|ATTR_FLAG_ONEVF),
+   AMDGPU_DEVICE_ATTR_RW(power_dpm_force_performance_level,
+ 
AMD_SYSFS_IF_POWER_DPM_FORCE_PERFORMANCE_LEVEL_BIT,
+ ATTR_FLAG_BASI

[PATCH 3/8] drm/amd/pm: drop the support for legacy sysfs interfaces on SMU13.0.0

2023-01-04 Thread Evan Quan
Those legacy sysfs interfaces are actually not supported. Their
outputs are confusing.

Signed-off-by: Evan Quan 
Change-Id: I95a772911a6f0ec89b0dfed08bef50f0060defad
---
 drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c | 9 +
 1 file changed, 9 insertions(+)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c
index 969e5f965540..75c9f510e713 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_0_ppt.c
@@ -2052,4 +2052,13 @@ void smu_v13_0_0_set_ppt_funcs(struct smu_context *smu)
smu->pwr_src_map = smu_v13_0_0_pwr_src_map;
smu->workload_map = smu_v13_0_0_workload_map;
smu_v13_0_0_set_smu_mailbox_registers(smu);
+   /* Unset those legacy interfaces which are not supported */
+   smu->adev->pm.sysfs_if_supported &= 
~(BIT_ULL(AMD_SYSFS_IF_POWER_DPM_STATE_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_NUM_STATES_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_CUR_STATE_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_FORCE_STATE_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_TABLE_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_DPM_DCEFCLK_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_SCLK_OD_BIT) |
+ 
BIT_ULL(AMD_SYSFS_IF_PP_MCLK_OD_BIT));
 }
-- 
2.34.1



[PATCH 2/8] drm/amd/pm: refine the checks for sysfs interfaces support

2023-01-04 Thread Evan Quan
Make the code more clean and readable with no real logics
change.

Signed-off-by: Evan Quan 
Change-Id: I21c879fa9abad9f6da3b5289adf3124950d2f4eb
---
 drivers/gpu/drm/amd/pm/amdgpu_pm.c | 200 ++---
 1 file changed, 98 insertions(+), 102 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/amdgpu_pm.c 
b/drivers/gpu/drm/amd/pm/amdgpu_pm.c
index fb6a7d45693a..c69db29eea24 100644
--- a/drivers/gpu/drm/amd/pm/amdgpu_pm.c
+++ b/drivers/gpu/drm/amd/pm/amdgpu_pm.c
@@ -2006,9 +2006,6 @@ static int default_attr_update(struct amdgpu_device 
*adev, struct amdgpu_device_
   uint32_t mask, enum amdgpu_device_attr_states 
*states)
 {
struct device_attribute *dev_attr = &attr->dev_attr;
-   uint32_t mp1_ver = adev->ip_versions[MP1_HWIP][0];
-   uint32_t gc_ver = adev->ip_versions[GC_HWIP][0];
-   const char *attr_name = dev_attr->attr.name;
 
if (!(attr->flags & mask) ||
  !(AMD_SYSFS_IF_BITMASK(attr->if_bit) & 
adev->pm.sysfs_if_supported))  {
@@ -2016,112 +2013,14 @@ static int default_attr_update(struct amdgpu_device 
*adev, struct amdgpu_device_
return 0;
}
 
-#define DEVICE_ATTR_IS(_name)  (!strcmp(attr_name, #_name))
-
-   if (DEVICE_ATTR_IS(pp_dpm_socclk)) {
-   if (gc_ver < IP_VERSION(9, 0, 0))
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(pp_dpm_dcefclk)) {
-   if (gc_ver < IP_VERSION(9, 0, 0) ||
-   gc_ver == IP_VERSION(9, 4, 1) ||
-   gc_ver == IP_VERSION(9, 4, 2))
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(pp_dpm_fclk)) {
-   if (mp1_ver < IP_VERSION(10, 0, 0))
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(pp_od_clk_voltage)) {
-   *states = ATTR_STATE_UNSUPPORTED;
-   if (amdgpu_dpm_is_overdrive_supported(adev))
-   *states = ATTR_STATE_SUPPORTED;
-   } else if (DEVICE_ATTR_IS(mem_busy_percent)) {
-   if (adev->flags & AMD_IS_APU || gc_ver == IP_VERSION(9, 0, 1))
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(pcie_bw)) {
-   /* PCIe Perf counters won't work on APU nodes */
-   if (adev->flags & AMD_IS_APU)
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(unique_id)) {
-   switch (gc_ver) {
-   case IP_VERSION(9, 0, 1):
-   case IP_VERSION(9, 4, 0):
-   case IP_VERSION(9, 4, 1):
-   case IP_VERSION(9, 4, 2):
-   case IP_VERSION(10, 3, 0):
-   case IP_VERSION(11, 0, 0):
-   *states = ATTR_STATE_SUPPORTED;
-   break;
-   default:
-   *states = ATTR_STATE_UNSUPPORTED;
-   }
-   } else if (DEVICE_ATTR_IS(pp_features)) {
-   if (adev->flags & AMD_IS_APU || gc_ver < IP_VERSION(9, 0, 0))
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(gpu_metrics)) {
-   if (gc_ver < IP_VERSION(9, 1, 0))
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(pp_dpm_vclk)) {
-   if (!(gc_ver == IP_VERSION(10, 3, 1) ||
- gc_ver == IP_VERSION(10, 3, 0) ||
- gc_ver == IP_VERSION(10, 1, 2) ||
- gc_ver == IP_VERSION(11, 0, 0) ||
- gc_ver == IP_VERSION(11, 0, 2)))
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(pp_dpm_dclk)) {
-   if (!(gc_ver == IP_VERSION(10, 3, 1) ||
- gc_ver == IP_VERSION(10, 3, 0) ||
- gc_ver == IP_VERSION(10, 1, 2) ||
- gc_ver == IP_VERSION(11, 0, 0) ||
- gc_ver == IP_VERSION(11, 0, 2)))
-   *states = ATTR_STATE_UNSUPPORTED;
-   } else if (DEVICE_ATTR_IS(pp_power_profile_mode)) {
-   if (amdgpu_dpm_get_power_profile_mode(adev, NULL) == 
-EOPNOTSUPP)
-   *states = ATTR_STATE_UNSUPPORTED;
-   else if (gc_ver == IP_VERSION(10, 3, 0) && 
amdgpu_sriov_vf(adev))
-   *states = ATTR_STATE_UNSUPPORTED;
-   }
-
-   switch (gc_ver) {
-   case IP_VERSION(9, 4, 1):
-   case IP_VERSION(9, 4, 2):
-   /* the Mi series card does not support standalone 
mclk/socclk/fclk level setting */
-   if (DEVICE_ATTR_IS(pp_dpm_mclk) ||
-   DEVICE_ATTR_IS(pp_dpm_socclk) ||
-   DEVICE_ATTR_IS(pp_dpm_fclk)) {
-   dev_attr->attr.mode &= ~S_IWUGO;
-   dev_attr->store = NULL;
-   }
-   break;
-   case IP_VERSION(10, 3, 0):
-   if (D

RE: [PATCH 1/2] drm/amdgpu: update ta_secureDisplay_if.h to v27.00.00.08

2023-01-04 Thread Liu, HaoPing (Alan)
[AMD Official Use Only - General]

Reviewed-by: Alan Liu 

-Original Message-
From: Liu, Aaron  
Sent: Thursday, January 5, 2023 9:04 AM
To: amd-gfx@lists.freedesktop.org
Cc: Liu, HaoPing (Alan) ; Deucher, Alexander 
; Xiao, Shane ; Liu, Aaron 

Subject: [PATCH 1/2] drm/amdgpu: update ta_secureDisplay_if.h to v27.00.00.08

1. Rename securedisplay_cmd to ta_securedisplay_cmd.
2. Rename ta_securedisplay_max_phy to ta_securedisplay_phy_ID.

Signed-off-by: Aaron Liu 
Signed-off-by: Shane Xiao 
---
 .../gpu/drm/amd/amdgpu/ta_secureDisplay_if.h  | 24 +--
 1 file changed, 12 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/ta_secureDisplay_if.h 
b/drivers/gpu/drm/amd/amdgpu/ta_secureDisplay_if.h
index cf8ff064dc72..00d8bdb8254f 100644
--- a/drivers/gpu/drm/amd/amdgpu/ta_secureDisplay_if.h
+++ b/drivers/gpu/drm/amd/amdgpu/ta_secureDisplay_if.h
@@ -55,10 +55,10 @@ enum ta_securedisplay_status {
TA_SECUREDISPLAY_STATUS__MAX = 0x7FFF,/* 
Maximum Value for status*/
 };
 
-/** @enum ta_securedisplay_max_phy
+/** @enum ta_securedisplay_phy_ID
  *Physical ID number to use for reading corresponding DIO Scratch register 
for ROI
  */
-enum  ta_securedisplay_max_phy {
+enum  ta_securedisplay_phy_ID {
TA_SECUREDISPLAY_PHY0   = 0,
TA_SECUREDISPLAY_PHY1   = 1,
TA_SECUREDISPLAY_PHY2   = 2,
@@ -139,16 +139,16 @@ union ta_securedisplay_cmd_output {
uint32_t   reserved[4];
 };
 
-/** @struct securedisplay_cmd
- *Secure Display Command which is shared buffer memory
- */
-struct securedisplay_cmd {
-   uint32_t cmd_id;/* +0  
Bytes Command ID */
-   enum ta_securedisplay_status status; /* +4  Bytes Status of 
Secure Display TA */
-   uint32_t reserved[2];   /* +8  
Bytes Reserved */
-   union ta_securedisplay_cmd_input securedisplay_in_message;  /* +16 
Bytes Input Buffer */
-   union ta_securedisplay_cmd_outputsecuredisplay_out_message;/* +32 
Bytes Output Buffer */
-   /**@note Total 48 Bytes */
+/** @struct ta_securedisplay_cmd
+*Secure display command which is shared buffer memory
+*/
+struct ta_securedisplay_cmd {
+uint32_t   cmd_id; 
/**< +0  Bytes Command ID */
+enum ta_securedisplay_status   status; 
/**< +4  Bytes Status code returned by the secure display TA */
+uint32_t   reserved[2];
/**< +8  Bytes Reserved */
+union ta_securedisplay_cmd_input   
securedisplay_in_message;   /**< +16 Bytes Command input buffer */
+union ta_securedisplay_cmd_output  
securedisplay_out_message;  /**< +32 Bytes Command output buffer */
+/**@note Total 48 Bytes */
 };
 
 #endif   //_TA_SECUREDISPLAY_IF_H
-- 
2.39.0


RE: [PATCH 2/2] drm/amd: update securedisplay_cmd to ta_securedisplay_cmd

2023-01-04 Thread Liu, HaoPing (Alan)
[AMD Official Use Only - General]

Reviewed-by: Alan Liu 

-Original Message-
From: Liu, Aaron  
Sent: Thursday, January 5, 2023 9:04 AM
To: amd-gfx@lists.freedesktop.org
Cc: Liu, HaoPing (Alan) ; Deucher, Alexander 
; Xiao, Shane ; Liu, Aaron 

Subject: [PATCH 2/2] drm/amd: update securedisplay_cmd to ta_securedisplay_cmd

This patch updates securedisplay_cmd to ta_securedisplay_cmd starting from 
amd-ta_securedisplay-v27.00.00.08.

Signed-off-by: Aaron Liu 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c   | 2 +-
 drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c | 8 
 drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h | 2 +-
 drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c | 2 +-
 4 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index 0706afb11577..2bebda7de604 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -1907,7 +1907,7 @@ int psp_rap_invoke(struct psp_context *psp, uint32_t 
ta_cmd_id, enum ta_rap_stat  static int psp_securedisplay_initialize(struct 
psp_context *psp)  {
int ret;
-   struct securedisplay_cmd *securedisplay_cmd;
+   struct ta_securedisplay_cmd *securedisplay_cmd;
 
/*
 * TODO: bypass the initialize in sriov for now diff --git 
a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
index 2c1d82fc4c34..8ed0e073656f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
@@ -77,11 +77,11 @@ void psp_securedisplay_parse_resp_status(struct psp_context 
*psp,
}
 }
 
-void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
securedisplay_cmd **cmd,
+void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
+ta_securedisplay_cmd **cmd,
enum ta_securedisplay_command command_id)  {
-   *cmd = (struct securedisplay_cmd 
*)psp->securedisplay_context.context.mem_context.shared_buf;
-   memset(*cmd, 0, sizeof(struct securedisplay_cmd));
+   *cmd = (struct ta_securedisplay_cmd 
*)psp->securedisplay_context.context.mem_context.shared_buf;
+   memset(*cmd, 0, sizeof(struct ta_securedisplay_cmd));
(*cmd)->status = TA_SECUREDISPLAY_STATUS__GENERIC_FAILURE;
(*cmd)->cmd_id = command_id;
 }
@@ -93,7 +93,7 @@ static ssize_t amdgpu_securedisplay_debugfs_write(struct file 
*f, const char __u  {
struct amdgpu_device *adev = (struct amdgpu_device 
*)file_inode(f)->i_private;
struct psp_context *psp = &adev->psp;
-   struct securedisplay_cmd *securedisplay_cmd;
+   struct ta_securedisplay_cmd *securedisplay_cmd;
struct drm_device *dev = adev_to_drm(adev);
uint32_t phy_id;
uint32_t op;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
index fe98574748f4..456ad68ed4b2 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
@@ -30,7 +30,7 @@
 void amdgpu_securedisplay_debugfs_init(struct amdgpu_device *adev);  void 
psp_securedisplay_parse_resp_status(struct psp_context *psp,
enum ta_securedisplay_status status); -void 
psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
securedisplay_cmd **cmd,
+void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
+ta_securedisplay_cmd **cmd,
enum ta_securedisplay_command command_id);
 
 #endif
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
index ad73e5855580..8841c447d0e2 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
@@ -103,7 +103,7 @@ static void amdgpu_dm_crtc_notify_ta_to_read(struct 
work_struct *work)  {
struct secure_display_context *secure_display_ctx;
struct psp_context *psp;
-   struct securedisplay_cmd *securedisplay_cmd;
+   struct ta_securedisplay_cmd *securedisplay_cmd;
struct drm_crtc *crtc;
struct dc_stream_state *stream;
uint8_t phy_inst;
--
2.39.0


[PATCH 2/2] drm/amd: update securedisplay_cmd to ta_securedisplay_cmd

2023-01-04 Thread Aaron Liu
This patch updates securedisplay_cmd to ta_securedisplay_cmd
starting from amd-ta_securedisplay-v27.00.00.08.

Signed-off-by: Aaron Liu 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c   | 2 +-
 drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c | 8 
 drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h | 2 +-
 drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c | 2 +-
 4 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index 0706afb11577..2bebda7de604 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -1907,7 +1907,7 @@ int psp_rap_invoke(struct psp_context *psp, uint32_t 
ta_cmd_id, enum ta_rap_stat
 static int psp_securedisplay_initialize(struct psp_context *psp)
 {
int ret;
-   struct securedisplay_cmd *securedisplay_cmd;
+   struct ta_securedisplay_cmd *securedisplay_cmd;
 
/*
 * TODO: bypass the initialize in sriov for now
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
index 2c1d82fc4c34..8ed0e073656f 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.c
@@ -77,11 +77,11 @@ void psp_securedisplay_parse_resp_status(struct psp_context 
*psp,
}
 }
 
-void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
securedisplay_cmd **cmd,
+void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
ta_securedisplay_cmd **cmd,
enum ta_securedisplay_command command_id)
 {
-   *cmd = (struct securedisplay_cmd 
*)psp->securedisplay_context.context.mem_context.shared_buf;
-   memset(*cmd, 0, sizeof(struct securedisplay_cmd));
+   *cmd = (struct ta_securedisplay_cmd 
*)psp->securedisplay_context.context.mem_context.shared_buf;
+   memset(*cmd, 0, sizeof(struct ta_securedisplay_cmd));
(*cmd)->status = TA_SECUREDISPLAY_STATUS__GENERIC_FAILURE;
(*cmd)->cmd_id = command_id;
 }
@@ -93,7 +93,7 @@ static ssize_t amdgpu_securedisplay_debugfs_write(struct file 
*f, const char __u
 {
struct amdgpu_device *adev = (struct amdgpu_device 
*)file_inode(f)->i_private;
struct psp_context *psp = &adev->psp;
-   struct securedisplay_cmd *securedisplay_cmd;
+   struct ta_securedisplay_cmd *securedisplay_cmd;
struct drm_device *dev = adev_to_drm(adev);
uint32_t phy_id;
uint32_t op;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
index fe98574748f4..456ad68ed4b2 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_securedisplay.h
@@ -30,7 +30,7 @@
 void amdgpu_securedisplay_debugfs_init(struct amdgpu_device *adev);
 void psp_securedisplay_parse_resp_status(struct psp_context *psp,
enum ta_securedisplay_status status);
-void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
securedisplay_cmd **cmd,
+void psp_prep_securedisplay_cmd_buf(struct psp_context *psp, struct 
ta_securedisplay_cmd **cmd,
enum ta_securedisplay_command command_id);
 
 #endif
diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
index ad73e5855580..8841c447d0e2 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crc.c
@@ -103,7 +103,7 @@ static void amdgpu_dm_crtc_notify_ta_to_read(struct 
work_struct *work)
 {
struct secure_display_context *secure_display_ctx;
struct psp_context *psp;
-   struct securedisplay_cmd *securedisplay_cmd;
+   struct ta_securedisplay_cmd *securedisplay_cmd;
struct drm_crtc *crtc;
struct dc_stream_state *stream;
uint8_t phy_inst;
-- 
2.39.0



[PATCH 1/2] drm/amdgpu: update ta_secureDisplay_if.h to v27.00.00.08

2023-01-04 Thread Aaron Liu
1. Rename securedisplay_cmd to ta_securedisplay_cmd.
2. Rename ta_securedisplay_max_phy to ta_securedisplay_phy_ID.

Signed-off-by: Aaron Liu 
Signed-off-by: Shane Xiao 
---
 .../gpu/drm/amd/amdgpu/ta_secureDisplay_if.h  | 24 +--
 1 file changed, 12 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/ta_secureDisplay_if.h 
b/drivers/gpu/drm/amd/amdgpu/ta_secureDisplay_if.h
index cf8ff064dc72..00d8bdb8254f 100644
--- a/drivers/gpu/drm/amd/amdgpu/ta_secureDisplay_if.h
+++ b/drivers/gpu/drm/amd/amdgpu/ta_secureDisplay_if.h
@@ -55,10 +55,10 @@ enum ta_securedisplay_status {
TA_SECUREDISPLAY_STATUS__MAX = 0x7FFF,/* 
Maximum Value for status*/
 };
 
-/** @enum ta_securedisplay_max_phy
+/** @enum ta_securedisplay_phy_ID
  *Physical ID number to use for reading corresponding DIO Scratch register 
for ROI
  */
-enum  ta_securedisplay_max_phy {
+enum  ta_securedisplay_phy_ID {
TA_SECUREDISPLAY_PHY0   = 0,
TA_SECUREDISPLAY_PHY1   = 1,
TA_SECUREDISPLAY_PHY2   = 2,
@@ -139,16 +139,16 @@ union ta_securedisplay_cmd_output {
uint32_t   reserved[4];
 };
 
-/** @struct securedisplay_cmd
- *Secure Display Command which is shared buffer memory
- */
-struct securedisplay_cmd {
-   uint32_t cmd_id;/* +0  
Bytes Command ID */
-   enum ta_securedisplay_status status; /* +4  Bytes Status of 
Secure Display TA */
-   uint32_t reserved[2];   /* +8  
Bytes Reserved */
-   union ta_securedisplay_cmd_input securedisplay_in_message;  /* +16 
Bytes Input Buffer */
-   union ta_securedisplay_cmd_outputsecuredisplay_out_message;/* +32 
Bytes Output Buffer */
-   /**@note Total 48 Bytes */
+/** @struct ta_securedisplay_cmd
+*Secure display command which is shared buffer memory
+*/
+struct ta_securedisplay_cmd {
+uint32_t   cmd_id; 
/**< +0  Bytes Command ID */
+enum ta_securedisplay_status   status; 
/**< +4  Bytes Status code returned by the secure display TA */
+uint32_t   reserved[2];
/**< +8  Bytes Reserved */
+union ta_securedisplay_cmd_input   
securedisplay_in_message;   /**< +16 Bytes Command input buffer */
+union ta_securedisplay_cmd_output  
securedisplay_out_message;  /**< +32 Bytes Command output buffer */
+/**@note Total 48 Bytes */
 };
 
 #endif   //_TA_SECUREDISPLAY_IF_H
-- 
2.39.0



Re: [PATCH] drm/amd/display: fix array-bounds errors in dc_stream_remove_writeback()

2023-01-04 Thread Hamza Mahfooz

On 12/25/22 10:10, wenyang.li...@foxmail.com wrote:

From: Wen Yang 

The following errors occurred when using gcc 7.5.0-3ubuntu1~18.04:
drivers/gpu/drm/amd/amdgpu/../display/dc/core/dc_stream.c: In function 
‘dc_stream_remove_writeback’:
drivers/gpu/drm/amd/amdgpu/../display/dc/core/dc_stream.c:543:55: warning: 
array subscript is above array bounds [-Warray-bounds]
  stream->writeback_info[j] = stream->writeback_info[i];
  ~~^~~
Add a check to make sure that num_wb_info won't overflowing the writeback_info 
buffer.

Fixes: 6fbefb84a98e ("drm/amd/display: Add DC core changes for DCN2")

Signed-off-by: Wen Yang 
Cc: Aurabindo Pillai 
Cc: Hamza Mahfooz 
Cc: Guenter Roeck 
Cc: Alex Deucher 
Cc: Harry Wentland 
Cc: Leo Li 
Cc: amd-gfx@lists.freedesktop.org
Cc: dri-de...@lists.freedesktop.org
Cc: linux-ker...@vger.kernel.org


Applied, thanks!


---
  drivers/gpu/drm/amd/display/dc/core/dc_stream.c | 9 -
  1 file changed, 8 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_stream.c 
b/drivers/gpu/drm/amd/display/dc/core/dc_stream.c
index 20e534f73513..9825c30f2ca0 100644
--- a/drivers/gpu/drm/amd/display/dc/core/dc_stream.c
+++ b/drivers/gpu/drm/amd/display/dc/core/dc_stream.c
@@ -481,6 +481,7 @@ bool dc_stream_add_writeback(struct dc *dc,
}
  
  	if (!isDrc) {

+   ASSERT(stream->num_wb_info + 1 <= MAX_DWB_PIPES);
stream->writeback_info[stream->num_wb_info++] = *wb_info;
}
  
@@ -526,6 +527,11 @@ bool dc_stream_remove_writeback(struct dc *dc,

return false;
}
  
+	if (stream->num_wb_info > MAX_DWB_PIPES) {

+   dm_error("DC: num_wb_info is invalid!\n");
+   return false;
+   }
+
  //stream->writeback_info[dwb_pipe_inst].wb_enabled = false;
for (i = 0; i < stream->num_wb_info; i++) {
/*dynamic update*/
@@ -540,7 +546,8 @@ bool dc_stream_remove_writeback(struct dc *dc,
if (stream->writeback_info[i].wb_enabled) {
if (j < i)
/* trim the array */
-   stream->writeback_info[j] = 
stream->writeback_info[i];
+   memcpy(&stream->writeback_info[j], 
&stream->writeback_info[i],
+   sizeof(struct 
dc_writeback_info));
j++;
}
}


--
Hamza



Re: [PATCH] drm/amd/display: Remove redundant logs from DSC code

2023-01-04 Thread Hamza Mahfooz

On 12/16/22 05:35, Praful Swarnakar wrote:

[Why & How]
Remove redundant log in DSC that just add additional blank prints

Signed-off-by: Praful Swarnakar 


Applied, thanks!


---
  drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c | 1 -
  drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c | 1 -
  2 files changed, 2 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c 
b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c
index af9411ee3c74..f2b6d40e4f5c 100644
--- a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c
+++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c
@@ -7510,7 +7510,6 @@ bool dp_set_dsc_pps_sdp(struct pipe_ctx *pipe_ctx, bool 
enable, bool immediate_u
dsc_cfg.is_odm = pipe_ctx->next_odm_pipe ? true : false;
dsc_cfg.dc_dsc_cfg = stream->timing.dsc_cfg;
  
-		DC_LOG_DSC(" ");

dsc->funcs->dsc_get_packed_pps(dsc, &dsc_cfg, 
&dsc_packed_pps[0]);
memcpy(&stream->dsc_packed_pps[0], &dsc_packed_pps[0], 
sizeof(stream->dsc_packed_pps));
if (dc_is_dp_signal(stream->signal)) {
diff --git a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c 
b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c
index 784a8b6f360d..c08c01e05dcf 100644
--- a/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c
+++ b/drivers/gpu/drm/amd/display/dc/dcn20/dcn20_dsc.c
@@ -200,7 +200,6 @@ static void dsc2_set_config(struct 
display_stream_compressor *dsc, const struct
bool is_config_ok;
struct dcn20_dsc *dsc20 = TO_DCN20_DSC(dsc);
  
-	DC_LOG_DSC(" ");

DC_LOG_DSC("Setting DSC Config at DSC inst %d", dsc->inst);
dsc_config_log(dsc, dsc_cfg);
is_config_ok = dsc_prepare_config(dsc_cfg, &dsc20->reg_vals, 
dsc_optc_cfg);


--
Hamza



[PATCH] drm/amdgpu: Fix potential NULL dereference

2023-01-04 Thread Luben Tuikov
Fix potential NULL dereference, in the case when "man", the resource manager
might be NULL, when/if we print debug information.

Cc: Alex Deucher 
Cc: Christian König 
Cc: AMD Graphics 
Cc: Dan Carpenter 
Cc: kernel test robot 
Fixes: 7554886daa31ea ("drm/amdgpu: Fix size validation for non-exclusive 
domains (v4)")
Signed-off-by: Luben Tuikov 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_object.c | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c
index af716afad9a59a..d1c90015651ba5 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c
@@ -470,8 +470,9 @@ static bool amdgpu_bo_validate_size(struct amdgpu_device 
*adev,
return true;
 
 fail:
-   DRM_DEBUG("BO size %lu > total memory in domain: %llu\n", size,
- man->size);
+   if (man)
+   DRM_DEBUG("BO size %lu > total memory in domain: %llu\n", size,
+ man->size);
return false;
 }
 

base-commit: b45d1c2754f5080acf2096ffcb17bcfeee7f5c2f
-- 
2.39.0



Re: [PATCH 1/2] drm/amdgpu: return the PCIe gen and lanes from the INFO

2023-01-04 Thread Marek Olšák
Yes, it's meant to be like a spec sheet. We are not interested in the
current bandwidth utilization.

Marek

On Wed, Jan 4, 2023 at 10:33 AM Lazar, Lijo  wrote:

> [AMD Official Use Only - General]
>
> To clarify, with DPM in place, the current bandwidth will be changing
> based on the load.
>
> If apps/umd already has a way to know the current bandwidth utilisation,
> then possible maximum also could be part of the same API. Otherwise, this
> only looks like duplicate information. We have the same information in
> sysfs DPM nodes.
>
> BTW, I don't know to what extent app/umd really makes use of this. Take
> that memory frequency as an example (I'm reading it as 16GHz). It only
> looks like a spec sheet.
>
> Thanks,
> Lijo
> --
> *From:* Marek Olšák 
> *Sent:* Wednesday, January 4, 2023 8:40:00 PM
> *To:* Lazar, Lijo 
> *Cc:* amd-gfx@lists.freedesktop.org 
> *Subject:* Re: [PATCH 1/2] drm/amdgpu: return the PCIe gen and lanes from
> the INFO
>
> On Wed, Jan 4, 2023 at 9:19 AM Lazar, Lijo  wrote:
>
>
>
> On 1/4/2023 7:43 PM, Marek Olšák wrote:
> > On Wed, Jan 4, 2023 at 6:50 AM Lazar, Lijo  > > wrote:
> >
> >
> >
> > On 1/4/2023 4:11 AM, Marek Olšák wrote:
> >  > I see. Well, those sysfs files are not usable, and I don't think
> it
> >  > would be important even if they were usable, but for completeness:
> >  >
> >  > The ioctl returns:
> >  >  pcie_gen = 1
> >  >  pcie_num_lanes = 16
> >  >
> >  > Theoretical bandwidth from those values: 4.0 GB/s
> >  > My DMA test shows this write bandwidth: 3.5 GB/s
> >  > It matches the expectation.
> >  >
> >  > Let's see the devices (there is only 1 GPU Navi21 in the system):
> >  > $ lspci |egrep '(PCI|VGA).*Navi'
> >  > 0a:00.0 PCI bridge: Advanced Micro Devices, Inc. [AMD/ATI] Navi
> > 10 XL
> >  > Upstream Port of PCI Express Switch (rev c3)
> >  > 0b:00.0 PCI bridge: Advanced Micro Devices, Inc. [AMD/ATI] Navi
> > 10 XL
> >  > Downstream Port of PCI Express Switch
> >  > 0c:00.0 VGA compatible controller: Advanced Micro Devices, Inc.
> >  > [AMD/ATI] Navi 21 [Radeon RX 6800/6800 XT / 6900 XT] (rev c3)
> >  >
> >  > Let's read sysfs:
> >  >
> >  > $ cat /sys/bus/pci/devices/:0a:00.0/current_link_width
> >  > 16
> >  > $ cat /sys/bus/pci/devices/:0b:00.0/current_link_width
> >  > 16
> >  > $ cat /sys/bus/pci/devices/:0c:00.0/current_link_width
> >  > 16
> >  > $ cat /sys/bus/pci/devices/:0a:00.0/current_link_speed
> >  > 2.5 GT/s PCIe
> >  > $ cat /sys/bus/pci/devices/:0b:00.0/current_link_speed
> >  > 16.0 GT/s PCIe
> >  > $ cat /sys/bus/pci/devices/:0c:00.0/current_link_speed
> >  > 16.0 GT/s PCIe
> >  >
> >  > Problem 1: None of the speed numbers match 4 GB/s.
> >
> > US bridge = 2.5GT/s means operating at PCIe Gen 1 speed. Total
> > theoretical bandwidth is then derived based on encoding and total
> > number
> > of lanes.
> >
> >  > Problem 2: Userspace doesn't know the bus index of the bridges,
> > and it's
> >  > not clear which bridge should be used.
> >
> > In general, modern ones have this arch= US->DS->EP. US is the one
> > connected to physical link.
> >
> >  > Problem 3: The PCIe gen number is missing.
> >
> > Current link speed is based on whether it's Gen1/2/3/4/5.
> >
> > BTW, your patch makes use of capabilities flags which gives the
> maximum
> > supported speed/width by the device. It may not necessarily reflect
> the
> > current speed/width negotiated. I guess in NV, this info is already
> > obtained from PMFW and made available through metrics table.
> >
> >
> > It computes the minimum of the device PCIe gen and the motherboard/slot
> > PCIe gen to get the final value. These 2 lines do that. The low 16 bits
> > of the mask contain the device PCIe gen mask. The high 16 bits of the
> > mask contain the slot PCIe gen mask.
> > + pcie_gen_mask = adev->pm.pcie_gen_mask & (adev->pm.pcie_gen_mask >>
> 16);
> > + dev_info->pcie_gen = fls(pcie_gen_mask);
> >
>
> With DPM in place on some ASICs, how much does this static info help for
> upper level apps?
>
>
> It helps UMDs make better decisions if they know the maximum achievable
> bandwidth. UMDs also compute the maximum memory bandwidth and compute
> performance (FLOPS). Right now it's printed by Mesa to give users detailed
> information about their GPU. For example:
>
> $ AMD_DEBUG=info glxgears
> Device info:
> name = NAVI21
> marketing_name = AMD Radeon RX 6800
> num_se = 3
> num_rb = 12
> num_cu = 60
> max_gpu_freq = 2475 MHz
> max_gflops = 19008 GFLOPS
> l0_cache_size = 16 KB
> l1_cache_size = 128 KB
> l2_cache_size = 4096 KB
> l3_cache_size = 128 MB
> memory_channels = 16 (TCC blocks)
> memory_size = 16 GB (16384 MB)
> memory_freq = 16 GHz
>   

[PATCH 12/14] drm/amd/display: Do not add '-mhard-float' to dml_ccflags for clang

2023-01-04 Thread Nathan Chancellor
When clang's -Qunused-arguments is dropped from KBUILD_CPPFLAGS, it
warns:

  clang-16: error: argument unused during compilation: '-mhard-float' 
[-Werror,-Wunused-command-line-argument]

Similar to commit 84edc2eff827 ("selftest/fpu: avoid clang warning"),
just add this flag to GCC builds. Commit 0f0727d971f6 ("drm/amd/display:
readd -msse2 to prevent Clang from emitting libcalls to undefined SW FP
routines") added '-msse2' to prevent clang from emitting software
floating point routines.

Signed-off-by: Nathan Chancellor 
---
Cc: harry.wentl...@amd.com
Cc: sunpeng...@amd.com
Cc: rodrigo.sique...@amd.com
Cc: alexander.deuc...@amd.com
Cc: christian.koe...@amd.com
Cc: xinhui@amd.com
Cc: amd-gfx@lists.freedesktop.org
Cc: dri-de...@lists.freedesktop.org
---
 drivers/gpu/drm/amd/display/dc/dml/Makefile | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/drivers/gpu/drm/amd/display/dc/dml/Makefile 
b/drivers/gpu/drm/amd/display/dc/dml/Makefile
index 0ecea87cf48f..9d0f79dff2e3 100644
--- a/drivers/gpu/drm/amd/display/dc/dml/Makefile
+++ b/drivers/gpu/drm/amd/display/dc/dml/Makefile
@@ -26,7 +26,8 @@
 # subcomponents.
 
 ifdef CONFIG_X86
-dml_ccflags := -mhard-float -msse
+dml_ccflags-$(CONFIG_CC_IS_GCC) := -mhard-float
+dml_ccflags := $(dml_ccflags-y) -msse
 endif
 
 ifdef CONFIG_PPC64

-- 
2.39.0


[PATCH 00/14] Remove clang's -Qunused-arguments from KBUILD_CPPFLAGS

2023-01-04 Thread Nathan Chancellor
Hi all,

Clang can emit a few different warnings when it encounters a flag that it
recognizes but does not support internally. These warnings are elevated to
errors within {as,cc}-option via -Werror to catch unsupported flags that should
not be added to KBUILD_{A,C}FLAGS; see commit c3f0d0bc5b01 ("kbuild, LLVMLinux:
Add -Werror to cc-option to support clang").

If an unsupported flag is unconditionally to KBUILD_{A,C}FLAGS, all subsequent
{as,cc}-option will always fail, preventing supported and even potentially
necessary flags from getting adding to the tool flags.

One would expect these warnings to be visible in the kernel build logs since
they are added to KBUILD_{A,C}FLAGS but unfortunately, these warnings are
hidden with clang's -Qunused-arguments flag, which is added to KBUILD_CPPFLAGS
and used for both compiling and assembling files.

Patches 1-4 address the internal inconsistencies of invoking the assembler
within kbuild by using KBUILD_AFLAGS consistently and using '-x
assembler-with-cpp' over '-x assembler'. This matches how assembly files are
built across the kernel and helps avoid problems in situations where macro
definitions or warning flags are present in KBUILD_AFLAGS, which cause
instances of -Wunused-command-line-argument when the preprocessor is not called
to consume them. There were a couple of places in architecture code where this
change would break things so those are fixed first.

Patches 5-12 clean up warnings that will show up when -Qunused-argument is
dropped. I hope none of these are controversial.

Patch 13 turns two warnings into errors so that the presence of unused flags
cannot be easily ignored.

Patch 14 drops -Qunused-argument. This is done last so that it can be easily
reverted if need be.

This series has seen my personal test framework, which tests several different
configurations and architectures, with LLVM tip of tree (16.0.0). I have done
defconfig, allmodconfig, and allnoconfig builds for arm, arm64, i386, mips,
powerpc, riscv, s390, and x86_64 with GCC 12.2.0 as well but I am hoping the
rest of the test infrastructure will catch any lurking problems.

I would like this series to stay together so that there is no opportunity for
breakage so please consider giving acks so that this can be carried via the
kbuild tree.

---
Nathan Chancellor (12):
  MIPS: Always use -Wa,-msoft-float and eliminate GAS_HAS_SET_HARDFLOAT
  MIPS: Prefer cc-option for additions to cflags
  powerpc: Remove linker flag from KBUILD_AFLAGS
  powerpc/vdso: Remove unused '-s' flag from ASFLAGS
  powerpc/vdso: Improve linker flags
  powerpc/vdso: Remove an unsupported flag from vgettimeofday-32.o with 
clang
  s390/vdso: Drop unused '-s' flag from KBUILD_AFLAGS_64
  s390/vdso: Drop '-shared' from KBUILD_CFLAGS_64
  s390/purgatory: Remove unused '-MD' and unnecessary '-c' flags
  drm/amd/display: Do not add '-mhard-float' to dml_ccflags for clang
  kbuild: Turn a couple more of clang's unused option warnings into errors
  kbuild: Stop using '-Qunused-arguments' with clang

Nick Desaulniers (2):
  x86/boot/compressed: prefer cc-option for CFLAGS additions
  kbuild: Update assembler calls to use proper flags and language target

 Makefile|  1 -
 arch/mips/Makefile  | 13 ++---
 arch/mips/include/asm/asmmacro-32.h |  4 +--
 arch/mips/include/asm/asmmacro.h| 42 ++---
 arch/mips/include/asm/fpregdef.h| 14 --
 arch/mips/include/asm/mipsregs.h| 20 +++---
 arch/mips/kernel/genex.S|  2 +-
 arch/mips/kernel/r2300_fpu.S|  4 +--
 arch/mips/kernel/r4k_fpu.S  | 12 -
 arch/mips/kvm/fpu.S |  6 ++---
 arch/mips/loongson2ef/Platform  |  2 +-
 arch/powerpc/Makefile   |  2 +-
 arch/powerpc/kernel/vdso/Makefile   | 25 +++--
 arch/s390/kernel/vdso64/Makefile|  4 +--
 arch/s390/purgatory/Makefile|  2 +-
 arch/x86/boot/compressed/Makefile   |  2 +-
 drivers/gpu/drm/amd/display/dc/dml/Makefile |  3 ++-
 scripts/Kconfig.include |  2 +-
 scripts/Makefile.clang  |  2 ++
 scripts/Makefile.compiler   |  8 +++---
 scripts/as-version.sh   |  2 +-
 21 files changed, 74 insertions(+), 98 deletions(-)
---
base-commit: 88603b6dc419445847923fcb7fe5080067a30f98
change-id: 20221228-drop-qunused-arguments-0c5c7dae54fb

Best regards,
-- 
Nathan Chancellor 


[PATCH 5.4 1/1] drm/amdkfd: Check for null pointer after calling kmemdup

2023-01-04 Thread Dragos-Marian Panait
From: Jiasheng Jiang 

[ Upstream commit abfaf0eee97925905e742aa3b0b72e04a918fa9e ]

As the possible failure of the allocation, kmemdup() may return NULL
pointer.
Therefore, it should be better to check the 'props2' in order to prevent
the dereference of NULL pointer.

Fixes: 3a87177eb141 ("drm/amdkfd: Add topology support for dGPUs")
Signed-off-by: Jiasheng Jiang 
Reviewed-by: Felix Kuehling 
Signed-off-by: Felix Kuehling 
Signed-off-by: Alex Deucher 
Signed-off-by: Dragos-Marian Panait 
---
 drivers/gpu/drm/amd/amdkfd/kfd_crat.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_crat.c 
b/drivers/gpu/drm/amd/amdkfd/kfd_crat.c
index 3685e89415d5..6066cd7a9d8c 100644
--- a/drivers/gpu/drm/amd/amdkfd/kfd_crat.c
+++ b/drivers/gpu/drm/amd/amdkfd/kfd_crat.c
@@ -407,6 +407,9 @@ static int kfd_parse_subtype_iolink(struct 
crat_subtype_iolink *iolink,
return -ENODEV;
/* same everything but the other direction */
props2 = kmemdup(props, sizeof(*props2), GFP_KERNEL);
+   if (!props2)
+   return -ENOMEM;
+
props2->node_from = id_to;
props2->node_to = id_from;
props2->kobj = NULL;
-- 
2.38.1



[PATCH 5.10 1/1] drm/amdkfd: Check for null pointer after calling kmemdup

2023-01-04 Thread Dragos-Marian Panait
From: Jiasheng Jiang 

[ Upstream commit abfaf0eee97925905e742aa3b0b72e04a918fa9e ]

As the possible failure of the allocation, kmemdup() may return NULL
pointer.
Therefore, it should be better to check the 'props2' in order to prevent
the dereference of NULL pointer.

Fixes: 3a87177eb141 ("drm/amdkfd: Add topology support for dGPUs")
Signed-off-by: Jiasheng Jiang 
Reviewed-by: Felix Kuehling 
Signed-off-by: Felix Kuehling 
Signed-off-by: Alex Deucher 
Signed-off-by: Dragos-Marian Panait 
---
 drivers/gpu/drm/amd/amdkfd/kfd_crat.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_crat.c 
b/drivers/gpu/drm/amd/amdkfd/kfd_crat.c
index 86b4dadf772e..02e3c650ed1c 100644
--- a/drivers/gpu/drm/amd/amdkfd/kfd_crat.c
+++ b/drivers/gpu/drm/amd/amdkfd/kfd_crat.c
@@ -408,6 +408,9 @@ static int kfd_parse_subtype_iolink(struct 
crat_subtype_iolink *iolink,
return -ENODEV;
/* same everything but the other direction */
props2 = kmemdup(props, sizeof(*props2), GFP_KERNEL);
+   if (!props2)
+   return -ENOMEM;
+
props2->node_from = id_to;
props2->node_to = id_from;
props2->kobj = NULL;
-- 
2.38.1



[PATCH 5.10 0/1] drm/amdkfd: Check for null pointer after calling kmemdup

2023-01-04 Thread Dragos-Marian Panait
The following commit is needed to fix CVE-2022-3108:
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=abfaf0eee97925905e742aa3b0b72e04a918fa9e

Jiasheng Jiang (1):
  drm/amdkfd: Check for null pointer after calling kmemdup

 drivers/gpu/drm/amd/amdkfd/kfd_crat.c | 3 +++
 1 file changed, 3 insertions(+)


base-commit: 0fe4548663f7dc2c3b549ef54ce9bb6d40a235be
-- 
2.38.1



[PATCH 5.4 0/1] drm/amdkfd: Check for null pointer after calling kmemdup

2023-01-04 Thread Dragos-Marian Panait
The following commit is needed to fix CVE-2022-3108:
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=abfaf0eee97925905e742aa3b0b72e04a918fa9e

Jiasheng Jiang (1):
  drm/amdkfd: Check for null pointer after calling kmemdup

 drivers/gpu/drm/amd/amdkfd/kfd_crat.c | 3 +++
 1 file changed, 3 insertions(+)


base-commit: 851c2b5fb7936d54e1147f76f88e2675f9f82b52
-- 
2.38.1



Re: [PATCH 4.19 1/1] drm/amdkfd: Check for null pointer after calling kmemdup

2023-01-04 Thread Dragos-Marian Panait



On 04.01.2023 16:48, Greg KH wrote:

On Wed, Jan 04, 2023 at 09:35:03AM -0500, Alex Deucher wrote:

On Wed, Jan 4, 2023 at 8:23 AM Christian König  wrote:

Am 04.01.23 um 13:41 schrieb Greg KH:

On Tue, Jan 03, 2023 at 08:43:08PM +0200, Dragos-Marian Panait wrote:

From: Jiasheng Jiang 

[ Upstream commit abfaf0eee97925905e742aa3b0b72e04a918fa9e ]

As the possible failure of the allocation, kmemdup() may return NULL
pointer.
Therefore, it should be better to check the 'props2' in order to prevent
the dereference of NULL pointer.

Fixes: 3a87177eb141 ("drm/amdkfd: Add topology support for dGPUs")
Signed-off-by: Jiasheng Jiang 
Reviewed-by: Felix Kuehling 
Signed-off-by: Felix Kuehling 
Signed-off-by: Alex Deucher 
Signed-off-by: Dragos-Marian Panait 
---
   drivers/gpu/drm/amd/amdkfd/kfd_crat.c | 3 +++
   1 file changed, 3 insertions(+)

For obvious reasons, I can't take a patch for 4.19.y and not newer
kernel releases, right?

Please provide backports for all kernels if you really need to see this
merged.  And note, it's not a real bug at all, and given that a CVE was
allocated for it that makes me want to even more reject it to show the
whole folly of that mess.

Well as far as I can see this is nonsense to back port.

The code in question is only used only once during driver load and then
never again, that exactly this allocation fails while tons of other are
made before and after is extremely unlikely.

It's nice to have it fixed in newer kernels, but not worth a backport
and certainly not stuff for a CVE.

It's already fixed in Linus' tree:
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=abfaf0eee97925905e742aa3b0b72e04a918fa9e

Yes, that's what the above commit shows...

confused,

greg k-h
Just for completeness, I also sent out patches for 5.4 and 5.10 stable 
branches.
5.15 stable branch already has this change: 
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/commit/?h=linux-5.15.y&id=5609b7803947eea1711516dd8659c7ed39f5a868


Dragos


Re: [PATCH] drm/amd/display: drop unnecessary NULL checks in debugfs

2023-01-04 Thread Hamza Mahfooz

On 12/27/22 12:04, Alexey Kodanev wrote:

pipe_ctx pointer cannot be NULL when getting the address of
an element of the pipe_ctx array. Moreover, the MAX_PIPES is
defined as 6, so pipe_ctx is not NULL after the loop either.

Detected using the static analysis tool - Svace.
Signed-off-by: Alexey Kodanev 


Applied, thanks!


---
  .../amd/display/amdgpu_dm/amdgpu_dm_debugfs.c | 72 +--
  1 file changed, 16 insertions(+), 56 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c
index 461037a3dd75..cec16eaf2fb0 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_debugfs.c
@@ -1375,16 +1375,11 @@ static ssize_t dp_dsc_clock_en_read(struct file *f, 
char __user *buf,
  
  	for (i = 0; i < MAX_PIPES; i++) {

pipe_ctx = 
&aconnector->dc_link->dc->current_state->res_ctx.pipe_ctx[i];
-   if (pipe_ctx && pipe_ctx->stream &&
+   if (pipe_ctx->stream &&
pipe_ctx->stream->link == aconnector->dc_link)
break;
}
  
-	if (!pipe_ctx) {

-   kfree(rd_buf);
-   return -ENXIO;
-   }
-
dsc = pipe_ctx->stream_res.dsc;
if (dsc)
dsc->funcs->dsc_read_state(dsc, &dsc_state);
@@ -1481,12 +1476,12 @@ static ssize_t dp_dsc_clock_en_write(struct file *f, 
const char __user *buf,
  
  	for (i = 0; i < MAX_PIPES; i++) {

pipe_ctx = 
&aconnector->dc_link->dc->current_state->res_ctx.pipe_ctx[i];
-   if (pipe_ctx && pipe_ctx->stream &&
+   if (pipe_ctx->stream &&
pipe_ctx->stream->link == aconnector->dc_link)
break;
}
  
-	if (!pipe_ctx || !pipe_ctx->stream)

+   if (!pipe_ctx->stream)
goto done;
  
  	// Get CRTC state

@@ -1566,16 +1561,11 @@ static ssize_t dp_dsc_slice_width_read(struct file *f, 
char __user *buf,
  
  	for (i = 0; i < MAX_PIPES; i++) {

pipe_ctx = 
&aconnector->dc_link->dc->current_state->res_ctx.pipe_ctx[i];
-   if (pipe_ctx && pipe_ctx->stream &&
+   if (pipe_ctx->stream &&
pipe_ctx->stream->link == aconnector->dc_link)
break;
}
  
-	if (!pipe_ctx) {

-   kfree(rd_buf);
-   return -ENXIO;
-   }
-
dsc = pipe_ctx->stream_res.dsc;
if (dsc)
dsc->funcs->dsc_read_state(dsc, &dsc_state);
@@ -1670,12 +1660,12 @@ static ssize_t dp_dsc_slice_width_write(struct file *f, 
const char __user *buf,
  
  	for (i = 0; i < MAX_PIPES; i++) {

pipe_ctx = 
&aconnector->dc_link->dc->current_state->res_ctx.pipe_ctx[i];
-   if (pipe_ctx && pipe_ctx->stream &&
+   if (pipe_ctx->stream &&
pipe_ctx->stream->link == aconnector->dc_link)
break;
}
  
-	if (!pipe_ctx || !pipe_ctx->stream)

+   if (!pipe_ctx->stream)
goto done;
  
  	// Safely get CRTC state

@@ -1755,16 +1745,11 @@ static ssize_t dp_dsc_slice_height_read(struct file *f, 
char __user *buf,
  
  	for (i = 0; i < MAX_PIPES; i++) {

pipe_ctx = 
&aconnector->dc_link->dc->current_state->res_ctx.pipe_ctx[i];
-   if (pipe_ctx && pipe_ctx->stream &&
+   if (pipe_ctx->stream &&
pipe_ctx->stream->link == aconnector->dc_link)
break;
}
  
-	if (!pipe_ctx) {

-   kfree(rd_buf);
-   return -ENXIO;
-   }
-
dsc = pipe_ctx->stream_res.dsc;
if (dsc)
dsc->funcs->dsc_read_state(dsc, &dsc_state);
@@ -1859,12 +1844,12 @@ static ssize_t dp_dsc_slice_height_write(struct file 
*f, const char __user *buf,
  
  	for (i = 0; i < MAX_PIPES; i++) {

pipe_ctx = 
&aconnector->dc_link->dc->current_state->res_ctx.pipe_ctx[i];
-   if (pipe_ctx && pipe_ctx->stream &&
+   if (pipe_ctx->stream &&
pipe_ctx->stream->link == aconnector->dc_link)
break;
}
  
-	if (!pipe_ctx || !pipe_ctx->stream)

+   if (!pipe_ctx->stream)
goto done;
  
  	// Get CRTC state

@@ -1940,16 +1925,11 @@ static ssize_t dp_dsc_bits_per_pixel_read(struct file 
*f, char __user *buf,
  
  	for (i = 0; i < MAX_PIPES; i++) {

pipe_ctx = 
&aconnector->dc_link->dc->current_state->res_ctx.pipe_ctx[i];
-   if (pipe_ctx && pipe_ctx->stream &&
+   if (pipe_ctx->stream &&
pipe_ctx->stream->link == aconnector->dc_link)
break;
}
  
-	if (!pipe_ctx) {

-   kfree(rd_buf);
-   return -ENXIO;
-   }
-
dsc = pipe_ctx->stream_res.dsc;
if (dsc)
dsc->funcs->dsc_read_s

Re: [PATCH v5 45/45] drm/amd: make amdgpu_ucode_validate static

2023-01-04 Thread Alex Deucher
Other than the patches I commented directly on, this series is:
Reviewed-by: Alex Deucher 

On Wed, Jan 4, 2023 at 11:45 AM Mario Limonciello
 wrote:
>
> No consumers outside of amdgpu_ucode.c use amdgpu_ucode_validate
> anymore, so make the function static.
>
> Signed-off-by: Mario Limonciello 
> ---
>  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 2 +-
>  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h | 1 -
>  2 files changed, 1 insertion(+), 2 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
> index dc6af1fffdd9..b759a4300d7a 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
> @@ -504,7 +504,7 @@ void amdgpu_ucode_print_gpu_info_hdr(const struct 
> common_firmware_header *hdr)
> }
>  }
>
> -int amdgpu_ucode_validate(const struct firmware *fw)
> +static int amdgpu_ucode_validate(const struct firmware *fw)
>  {
> const struct common_firmware_header *hdr =
> (const struct common_firmware_header *)fw->data;
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
> index 7fd2f04f7f98..28fc2960edfe 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
> @@ -543,7 +543,6 @@ void amdgpu_ucode_print_rlc_hdr(const struct 
> common_firmware_header *hdr);
>  void amdgpu_ucode_print_sdma_hdr(const struct common_firmware_header *hdr);
>  void amdgpu_ucode_print_psp_hdr(const struct common_firmware_header *hdr);
>  void amdgpu_ucode_print_gpu_info_hdr(const struct common_firmware_header 
> *hdr);
> -int amdgpu_ucode_validate(const struct firmware *fw);
>  int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
> **fw,
>  const char *fw_name);
>  void amdgpu_ucode_release(const struct firmware *fw);
> --
> 2.34.1
>


RE: [PATCH v5 10/45] drm/amd: Load VCN microcode during early_init

2023-01-04 Thread Limonciello, Mario
[Public]



> -Original Message-
> From: Alex Deucher 
> Sent: Wednesday, January 4, 2023 11:16
> To: Limonciello, Mario 
> Cc: Deucher, Alexander ; linux-
> ker...@vger.kernel.org; Pan, Xinhui ; Lazar, Lijo
> ; Javier Martinez Canillas ; dri-
> de...@lists.freedesktop.org; amd-gfx@lists.freedesktop.org; Carlos Soriano
> Sanchez ; Koenig, Christian
> 
> Subject: Re: [PATCH v5 10/45] drm/amd: Load VCN microcode during
> early_init
> 
> On Wed, Jan 4, 2023 at 11:42 AM Mario Limonciello
>  wrote:
> >
> > Simplifies the code so that all VCN versions will get the firmware
> > name from `amdgpu_ucode_ip_version_decode` and then use this
> filename
> > to load microcode as part of the early_init process.
> >
> > Signed-off-by: Mario Limonciello 
> > ---
> >  drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c | 91 +-
> ---
> >  drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h |  1 +
> >  drivers/gpu/drm/amd/amdgpu/vcn_v1_0.c   |  5 +-
> >  drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c   |  5 +-
> >  drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c   |  5 +-
> >  drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c   |  5 +-
> >  drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c   |  5 +-
> >  7 files changed, 50 insertions(+), 67 deletions(-)
> >
> > diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
> > index b5692f825589..55bbe4c8ff5b 100644
> > --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
> > +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
> > @@ -36,25 +36,25 @@
> >  #include "soc15d.h"
> >
> >  /* Firmware Names */
> > -#define FIRMWARE_RAVEN "amdgpu/raven_vcn.bin"
> > -#define FIRMWARE_PICASSO   "amdgpu/picasso_vcn.bin"
> > -#define FIRMWARE_RAVEN2"amdgpu/raven2_vcn.bin"
> > -#define FIRMWARE_ARCTURUS  "amdgpu/arcturus_vcn.bin"
> > -#define FIRMWARE_RENOIR"amdgpu/renoir_vcn.bin"
> > -#define FIRMWARE_GREEN_SARDINE "amdgpu/green_sardine_vcn.bin"
> > -#define FIRMWARE_NAVI10"amdgpu/navi10_vcn.bin"
> > -#define FIRMWARE_NAVI14"amdgpu/navi14_vcn.bin"
> > -#define FIRMWARE_NAVI12"amdgpu/navi12_vcn.bin"
> > -#define FIRMWARE_SIENNA_CICHLID
> "amdgpu/sienna_cichlid_vcn.bin"
> > -#define FIRMWARE_NAVY_FLOUNDER "amdgpu/navy_flounder_vcn.bin"
> > -#define FIRMWARE_VANGOGH   "amdgpu/vangogh_vcn.bin"
> > -#define FIRMWARE_DIMGREY_CAVEFISH
> "amdgpu/dimgrey_cavefish_vcn.bin"
> > -#define FIRMWARE_ALDEBARAN "amdgpu/aldebaran_vcn.bin"
> > -#define FIRMWARE_BEIGE_GOBY"amdgpu/beige_goby_vcn.bin"
> > -#define FIRMWARE_YELLOW_CARP   "amdgpu/yellow_carp_vcn.bin"
> > -#define FIRMWARE_VCN_3_1_2 "amdgpu/vcn_3_1_2.bin"
> > -#define FIRMWARE_VCN4_0_0  "amdgpu/vcn_4_0_0.bin"
> > -#define FIRMWARE_VCN4_0_2  "amdgpu/vcn_4_0_2.bin"
> > +#define FIRMWARE_RAVEN "amdgpu/raven_vcn.bin"
> > +#define FIRMWARE_PICASSO   "amdgpu/picasso_vcn.bin"
> > +#define FIRMWARE_RAVEN2"amdgpu/raven2_vcn.bin"
> > +#define FIRMWARE_ARCTURUS  "amdgpu/arcturus_vcn.bin"
> > +#define FIRMWARE_RENOIR"amdgpu/renoir_vcn.bin"
> > +#define FIRMWARE_GREEN_SARDINE "amdgpu/green_sardine_vcn.bin"
> > +#define FIRMWARE_NAVI10"amdgpu/navi10_vcn.bin"
> > +#define FIRMWARE_NAVI14"amdgpu/navi14_vcn.bin"
> > +#define FIRMWARE_NAVI12"amdgpu/navi12_vcn.bin"
> > +#define FIRMWARE_SIENNA_CICHLID
> "amdgpu/sienna_cichlid_vcn.bin"
> > +#define FIRMWARE_NAVY_FLOUNDER "amdgpu/navy_flounder_vcn.bin"
> > +#define FIRMWARE_VANGOGH   "amdgpu/vangogh_vcn.bin"
> > +#define FIRMWARE_DIMGREY_CAVEFISH
> "amdgpu/dimgrey_cavefish_vcn.bin"
> > +#define FIRMWARE_ALDEBARAN "amdgpu/aldebaran_vcn.bin"
> > +#define FIRMWARE_BEIGE_GOBY"amdgpu/beige_goby_vcn.bin"
> > +#define FIRMWARE_YELLOW_CARP   "amdgpu/yellow_carp_vcn.bin"
> > +#define FIRMWARE_VCN_3_1_2 "amdgpu/vcn_3_1_2.bin"
> > +#define FIRMWARE_VCN4_0_0  "amdgpu/vcn_4_0_0.bin"
> > +#define FIRMWARE_VCN4_0_2  "amdgpu/vcn_4_0_2.bin"
> >  #define FIRMWARE_VCN4_0_4  "amdgpu/vcn_4_0_4.bin"
> 
> Is this just a whitespace change?

Ah yeah; it was from various rebases moving things around and I missed it.
Will undo it for v6.

> 
> Alex
> 
> >
> >  MODULE_FIRMWARE(FIRMWARE_RAVEN);
> > @@ -80,10 +80,24 @@ MODULE_FIRMWARE(FIRMWARE_VCN4_0_4);
> >
> >  static void amdgpu_vcn_idle_work_handler(struct work_struct *work);
> >
> > +int amdgpu_vcn_early_init(struct amdgpu_device *adev)
> > +{
> > +   char ucode_prefix[30];
> > +   char fw_name[40];
> > +   int r;
> > +
> > +   amdgpu_ucode_ip_version_decode(adev, UVD_HWIP, ucode_prefix,
> sizeof(ucode_prefix));
> > +   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin",
> ucode_prefix);
> > +   r = amdgpu_ucode_request(adev, &adev->vcn.fw, fw_name);
> > +   if (r)
> > +   amdgpu_ucode_release(adev->vcn.fw);
> > +
> > +   return r;
> > +}
> > +
> >  int amdgpu_vcn_sw_init(struct amdgpu_device *adev)
> >  {
> > unsi

Re: [PATCH v5 10/45] drm/amd: Load VCN microcode during early_init

2023-01-04 Thread Alex Deucher
On Wed, Jan 4, 2023 at 11:42 AM Mario Limonciello
 wrote:
>
> Simplifies the code so that all VCN versions will get the firmware
> name from `amdgpu_ucode_ip_version_decode` and then use this filename
> to load microcode as part of the early_init process.
>
> Signed-off-by: Mario Limonciello 
> ---
>  drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c | 91 +
>  drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.h |  1 +
>  drivers/gpu/drm/amd/amdgpu/vcn_v1_0.c   |  5 +-
>  drivers/gpu/drm/amd/amdgpu/vcn_v2_0.c   |  5 +-
>  drivers/gpu/drm/amd/amdgpu/vcn_v2_5.c   |  5 +-
>  drivers/gpu/drm/amd/amdgpu/vcn_v3_0.c   |  5 +-
>  drivers/gpu/drm/amd/amdgpu/vcn_v4_0.c   |  5 +-
>  7 files changed, 50 insertions(+), 67 deletions(-)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c 
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
> index b5692f825589..55bbe4c8ff5b 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c
> @@ -36,25 +36,25 @@
>  #include "soc15d.h"
>
>  /* Firmware Names */
> -#define FIRMWARE_RAVEN "amdgpu/raven_vcn.bin"
> -#define FIRMWARE_PICASSO   "amdgpu/picasso_vcn.bin"
> -#define FIRMWARE_RAVEN2"amdgpu/raven2_vcn.bin"
> -#define FIRMWARE_ARCTURUS  "amdgpu/arcturus_vcn.bin"
> -#define FIRMWARE_RENOIR"amdgpu/renoir_vcn.bin"
> -#define FIRMWARE_GREEN_SARDINE "amdgpu/green_sardine_vcn.bin"
> -#define FIRMWARE_NAVI10"amdgpu/navi10_vcn.bin"
> -#define FIRMWARE_NAVI14"amdgpu/navi14_vcn.bin"
> -#define FIRMWARE_NAVI12"amdgpu/navi12_vcn.bin"
> -#define FIRMWARE_SIENNA_CICHLID"amdgpu/sienna_cichlid_vcn.bin"
> -#define FIRMWARE_NAVY_FLOUNDER "amdgpu/navy_flounder_vcn.bin"
> -#define FIRMWARE_VANGOGH   "amdgpu/vangogh_vcn.bin"
> -#define FIRMWARE_DIMGREY_CAVEFISH  "amdgpu/dimgrey_cavefish_vcn.bin"
> -#define FIRMWARE_ALDEBARAN "amdgpu/aldebaran_vcn.bin"
> -#define FIRMWARE_BEIGE_GOBY"amdgpu/beige_goby_vcn.bin"
> -#define FIRMWARE_YELLOW_CARP   "amdgpu/yellow_carp_vcn.bin"
> -#define FIRMWARE_VCN_3_1_2 "amdgpu/vcn_3_1_2.bin"
> -#define FIRMWARE_VCN4_0_0  "amdgpu/vcn_4_0_0.bin"
> -#define FIRMWARE_VCN4_0_2  "amdgpu/vcn_4_0_2.bin"
> +#define FIRMWARE_RAVEN "amdgpu/raven_vcn.bin"
> +#define FIRMWARE_PICASSO   "amdgpu/picasso_vcn.bin"
> +#define FIRMWARE_RAVEN2"amdgpu/raven2_vcn.bin"
> +#define FIRMWARE_ARCTURUS  "amdgpu/arcturus_vcn.bin"
> +#define FIRMWARE_RENOIR"amdgpu/renoir_vcn.bin"
> +#define FIRMWARE_GREEN_SARDINE "amdgpu/green_sardine_vcn.bin"
> +#define FIRMWARE_NAVI10"amdgpu/navi10_vcn.bin"
> +#define FIRMWARE_NAVI14"amdgpu/navi14_vcn.bin"
> +#define FIRMWARE_NAVI12"amdgpu/navi12_vcn.bin"
> +#define FIRMWARE_SIENNA_CICHLID"amdgpu/sienna_cichlid_vcn.bin"
> +#define FIRMWARE_NAVY_FLOUNDER "amdgpu/navy_flounder_vcn.bin"
> +#define FIRMWARE_VANGOGH   "amdgpu/vangogh_vcn.bin"
> +#define FIRMWARE_DIMGREY_CAVEFISH  "amdgpu/dimgrey_cavefish_vcn.bin"
> +#define FIRMWARE_ALDEBARAN "amdgpu/aldebaran_vcn.bin"
> +#define FIRMWARE_BEIGE_GOBY"amdgpu/beige_goby_vcn.bin"
> +#define FIRMWARE_YELLOW_CARP   "amdgpu/yellow_carp_vcn.bin"
> +#define FIRMWARE_VCN_3_1_2 "amdgpu/vcn_3_1_2.bin"
> +#define FIRMWARE_VCN4_0_0  "amdgpu/vcn_4_0_0.bin"
> +#define FIRMWARE_VCN4_0_2  "amdgpu/vcn_4_0_2.bin"
>  #define FIRMWARE_VCN4_0_4  "amdgpu/vcn_4_0_4.bin"

Is this just a whitespace change?

Alex

>
>  MODULE_FIRMWARE(FIRMWARE_RAVEN);
> @@ -80,10 +80,24 @@ MODULE_FIRMWARE(FIRMWARE_VCN4_0_4);
>
>  static void amdgpu_vcn_idle_work_handler(struct work_struct *work);
>
> +int amdgpu_vcn_early_init(struct amdgpu_device *adev)
> +{
> +   char ucode_prefix[30];
> +   char fw_name[40];
> +   int r;
> +
> +   amdgpu_ucode_ip_version_decode(adev, UVD_HWIP, ucode_prefix, 
> sizeof(ucode_prefix));
> +   snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", ucode_prefix);
> +   r = amdgpu_ucode_request(adev, &adev->vcn.fw, fw_name);
> +   if (r)
> +   amdgpu_ucode_release(adev->vcn.fw);
> +
> +   return r;
> +}
> +
>  int amdgpu_vcn_sw_init(struct amdgpu_device *adev)
>  {
> unsigned long bo_size;
> -   const char *fw_name;
> const struct common_firmware_header *hdr;
> unsigned char fw_check;
> unsigned int fw_shared_size, log_offset;
> @@ -99,46 +113,27 @@ int amdgpu_vcn_sw_init(struct amdgpu_device *adev)
> switch (adev->ip_versions[UVD_HWIP][0]) {
> case IP_VERSION(1, 0, 0):
> case IP_VERSION(1, 0, 1):
> -   if (adev->apu_flags & AMD_APU_IS_RAVEN2)
> -   fw_name = FIRMWARE_RAVEN2;
> -   else if (adev->apu_flags & AMD_APU_IS_PICASSO)
> -   fw_name = FIRMWARE_PICASSO;
> -   else
> -   fw_name = FIRMWARE_RAVEN;
> -   break;
>   

Re: [PATCH v5 05/45] drm/amd: Add a new helper for loading/validating microcode

2023-01-04 Thread Alex Deucher
On Wed, Jan 4, 2023 at 11:42 AM Mario Limonciello
 wrote:
>
> All microcode runs a basic validation after it's been loaded. Each
> IP block as part of init will run both.
>
> Introduce a wrapper for request_firmware and amdgpu_ucode_validate.
> This wrapper will also remap any error codes from request_firmware
> to -ENODEV.  This is so that early_init will fail if firmware couldn't
> be loaded instead of the IP block being disabled.
>
> Signed-off-by: Mario Limonciello 
> ---
> v4->v5:
>  * Rename symbols for amdgpu_ucode_request/amdgpu_ucode_release
>  * Make argument const
> ---
>  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 36 +++
>  drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h |  3 ++
>  2 files changed, 39 insertions(+)
>
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
> index eafcddce58d3..dc6af1fffdd9 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
> @@ -1312,3 +1312,39 @@ void amdgpu_ucode_ip_version_decode(struct 
> amdgpu_device *adev, int block_type,
>
> snprintf(ucode_prefix, len, "%s_%d_%d_%d", ip_name, maj, min, rev);
>  }
> +
> +/*
> + * amdgpu_ucode_request - Fetch and validate amdgpu microcode
> + *
> + * @adev: amdgpu device
> + * @fw: pointer to load firmware to
> + * @fw_name: firmware to load
> + *
> + * This is a helper that will use request_firmware and amdgpu_ucode_validate
> + * to load and run basic validation on firmware. If the load fails, remap
> + * the error code to -ENODEV, so that early_init functions will fail to load.
> + */
> +int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
> **fw,
> +const char *fw_name)
> +{
> +   int err = request_firmware(fw, fw_name, adev->dev);
> +
> +   if (err)
> +   return -ENODEV;
> +   err = amdgpu_ucode_validate(*fw);
> +   if (err)
> +   dev_dbg(adev->dev, "\"%s\" failed to validate\n", fw_name);
> +
> +   return err;
> +}
> +
> +/*
> + * amdgpu_ucode_release - Release firmware microcode
> + *
> + * @fw: pointer to firmware to release
> + */
> +void amdgpu_ucode_release(const struct firmware *fw)

This should be **fw if we want to set it to NULL.

Alex

> +{
> +   release_firmware(fw);
> +   fw = NULL;
> +}
> diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
> b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
> index 552e06929229..7fd2f04f7f98 100644
> --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
> +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
> @@ -544,6 +544,9 @@ void amdgpu_ucode_print_sdma_hdr(const struct 
> common_firmware_header *hdr);
>  void amdgpu_ucode_print_psp_hdr(const struct common_firmware_header *hdr);
>  void amdgpu_ucode_print_gpu_info_hdr(const struct common_firmware_header 
> *hdr);
>  int amdgpu_ucode_validate(const struct firmware *fw);
> +int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
> **fw,
> +const char *fw_name);
> +void amdgpu_ucode_release(const struct firmware *fw);
>  bool amdgpu_ucode_hdr_version(union amdgpu_firmware_header *hdr,
> uint16_t hdr_major, uint16_t hdr_minor);
>
> --
> 2.34.1
>


[PATCH v5 45/45] drm/amd: make amdgpu_ucode_validate static

2023-01-04 Thread Mario Limonciello
No consumers outside of amdgpu_ucode.c use amdgpu_ucode_validate
anymore, so make the function static.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c | 2 +-
 drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h | 1 -
 2 files changed, 1 insertion(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
index dc6af1fffdd9..b759a4300d7a 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.c
@@ -504,7 +504,7 @@ void amdgpu_ucode_print_gpu_info_hdr(const struct 
common_firmware_header *hdr)
}
 }
 
-int amdgpu_ucode_validate(const struct firmware *fw)
+static int amdgpu_ucode_validate(const struct firmware *fw)
 {
const struct common_firmware_header *hdr =
(const struct common_firmware_header *)fw->data;
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
index 7fd2f04f7f98..28fc2960edfe 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h
@@ -543,7 +543,6 @@ void amdgpu_ucode_print_rlc_hdr(const struct 
common_firmware_header *hdr);
 void amdgpu_ucode_print_sdma_hdr(const struct common_firmware_header *hdr);
 void amdgpu_ucode_print_psp_hdr(const struct common_firmware_header *hdr);
 void amdgpu_ucode_print_gpu_info_hdr(const struct common_firmware_header *hdr);
-int amdgpu_ucode_validate(const struct firmware *fw);
 int amdgpu_ucode_request(struct amdgpu_device *adev, const struct firmware 
**fw,
 const char *fw_name);
 void amdgpu_ucode_release(const struct firmware *fw);
-- 
2.34.1



[PATCH v5 43/45] drm/amd: Use `amdgpu_ucode_release` helper for powerplay

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_release` helper is replacing all calls to
release_firmware.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c 
b/drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c
index 8f2cc6310340..15f41189c911 100644
--- a/drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c
+++ b/drivers/gpu/drm/amd/pm/powerplay/amd_powerplay.c
@@ -111,8 +111,7 @@ static int pp_sw_fini(void *handle)
 
hwmgr_sw_fini(hwmgr);
 
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(adev->pm.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v5 40/45] drm/amd: Use `amdgpu_ucode_*` helpers for CGS

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c | 11 ++-
 1 file changed, 2 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c
index f1a050379190..151a313fc2a1 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_cgs.c
@@ -411,17 +411,10 @@ static int amdgpu_cgs_get_firmware_info(struct cgs_device 
*cgs_device,
return -EINVAL;
}
 
-   err = request_firmware(&adev->pm.fw, fw_name, 
adev->dev);
-   if (err) {
-   DRM_ERROR("Failed to request firmware\n");
-   return err;
-   }
-
-   err = amdgpu_ucode_validate(adev->pm.fw);
+   err = amdgpu_ucode_request(adev, &adev->pm.fw, fw_name);
if (err) {
DRM_ERROR("Failed to load firmware \"%s\"", 
fw_name);
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(adev->pm.fw);
return err;
}
 
-- 
2.34.1



[PATCH v5 37/45] drm/amd: Use `amdgpu_ucode_*` helpers for SDMA on CIK

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/cik_sdma.c | 16 ++--
 1 file changed, 6 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/cik_sdma.c 
b/drivers/gpu/drm/amd/amdgpu/cik_sdma.c
index cbca9866645c..25d7b80b0fcf 100644
--- a/drivers/gpu/drm/amd/amdgpu/cik_sdma.c
+++ b/drivers/gpu/drm/amd/amdgpu/cik_sdma.c
@@ -73,10 +73,9 @@ u32 amdgpu_cik_gpu_check_soft_reset(struct amdgpu_device 
*adev);
 static void cik_sdma_free_microcode(struct amdgpu_device *adev)
 {
int i;
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(adev->sdma.instance[i].fw);
 }
 
 /*
@@ -137,18 +136,15 @@ static int cik_sdma_init_microcode(struct amdgpu_device 
*adev)
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma.bin", chip_name);
else
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma1.bin", chip_name);
-   err = request_firmware(&adev->sdma.instance[i].fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->sdma.instance[i].fw, 
fw_name);
if (err)
goto out;
-   err = amdgpu_ucode_validate(adev->sdma.instance[i].fw);
}
 out:
if (err) {
pr_err("cik_sdma: Failed to load firmware \"%s\"\n", fw_name);
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(adev->sdma.instance[i].fw);
}
return err;
 }
-- 
2.34.1



[PATCH v5 42/45] drm/amd: Use `amdgpu_ucode_*` helpers for DMCU

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 11 ++-
 1 file changed, 2 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c 
b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
index 3908d715b90b..19c365283d91 100644
--- a/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
+++ b/drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c
@@ -1881,20 +1881,13 @@ static int load_dmcu_fw(struct amdgpu_device *adev)
return 0;
}
 
-   r = request_firmware_direct(&adev->dm.fw_dmcu, fw_name_dmcu, adev->dev);
-   if (r == -ENOENT) {
+   r = amdgpu_ucode_request(adev, &adev->dm.fw_dmcu, fw_name_dmcu);
+   if (r == -ENODEV) {
/* DMCU firmware is not necessary, so don't raise a fuss if 
it's missing */
DRM_DEBUG_KMS("dm: DMCU firmware not found\n");
adev->dm.fw_dmcu = NULL;
return 0;
}
-   if (r) {
-   dev_err(adev->dev, "amdgpu_dm: Can't load firmware \"%s\"\n",
-   fw_name_dmcu);
-   return r;
-   }
-
-   r = amdgpu_ucode_validate(adev->dm.fw_dmcu);
if (r) {
dev_err(adev->dev, "amdgpu_dm: Can't validate firmware 
\"%s\"\n",
fw_name_dmcu);
-- 
2.34.1



[PATCH v5 26/45] drm/amd: Use `amdgpu_ucode_*` helpers for SMU

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c | 16 
 drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c | 16 
 2 files changed, 8 insertions(+), 24 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
index d4756bd30830..2e03dffbe59c 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu11/smu_v11_0.c
@@ -109,10 +109,7 @@ int smu_v11_0_init_microcode(struct smu_context *smu)
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", ucode_prefix);
 
-   err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->pm.fw);
+   err = amdgpu_ucode_request(adev, &adev->pm.fw, fw_name);
if (err)
goto out;
 
@@ -130,12 +127,8 @@ int smu_v11_0_init_microcode(struct smu_context *smu)
}
 
 out:
-   if (err) {
-   DRM_ERROR("smu_v11_0: Failed to load firmware \"%s\"\n",
- fw_name);
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
-   }
+   if (err)
+   amdgpu_ucode_release(adev->pm.fw);
return err;
 }
 
@@ -143,8 +136,7 @@ void smu_v11_0_fini_microcode(struct smu_context *smu)
 {
struct amdgpu_device *adev = smu->adev;
 
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(adev->pm.fw);
adev->pm.fw_version = 0;
 }
 
diff --git a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c 
b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
index 506a49a4b425..990cf54b4bca 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0.c
@@ -103,10 +103,7 @@ int smu_v13_0_init_microcode(struct smu_context *smu)
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s.bin", ucode_prefix);
 
-   err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->pm.fw);
+   err = amdgpu_ucode_request(adev, &adev->pm.fw, fw_name);
if (err)
goto out;
 
@@ -124,12 +121,8 @@ int smu_v13_0_init_microcode(struct smu_context *smu)
}
 
 out:
-   if (err) {
-   DRM_ERROR("smu_v13_0: Failed to load firmware \"%s\"\n",
- fw_name);
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
-   }
+   if (err)
+   amdgpu_ucode_release(adev->pm.fw);
return err;
 }
 
@@ -137,8 +130,7 @@ void smu_v13_0_fini_microcode(struct smu_context *smu)
 {
struct amdgpu_device *adev = smu->adev;
 
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(adev->pm.fw);
adev->pm.fw_version = 0;
 }
 
-- 
2.34.1



[PATCH v5 44/45] drm/amd: Use `amdgpu_ucode_release` helper for si

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_release` helper is replacing all calls
to release_firmware.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c | 11 ++-
 1 file changed, 2 insertions(+), 9 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c 
b/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c
index 49c398ec0aaf..b4e5aac25ca7 100644
--- a/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c
+++ b/drivers/gpu/drm/amd/pm/legacy-dpm/si_dpm.c
@@ -7714,20 +7714,13 @@ static int si_dpm_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_smc.bin", chip_name);
-   err = request_firmware(&adev->pm.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->pm.fw);
-
-out:
+   err = amdgpu_ucode_request(adev, &adev->pm.fw, fw_name);
if (err) {
DRM_ERROR("si_smc: Failed to load firmware. err = %d\"%s\"\n",
  err, fw_name);
-   release_firmware(adev->pm.fw);
-   adev->pm.fw = NULL;
+   amdgpu_ucode_release(adev->pm.fw);
}
return err;
-
 }
 
 static int si_dpm_sw_init(void *handle)
-- 
2.34.1



[PATCH v5 30/45] drm/amd: Use `amdgpu_ucode_*` helpers for GFX7

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c | 68 +++
 1 file changed, 17 insertions(+), 51 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c
index 0f2976507e48..a16a44e5fb32 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v7_0.c
@@ -887,6 +887,16 @@ static void gfx_v7_0_get_csb_buffer(struct amdgpu_device 
*adev, volatile u32 *bu
 static void gfx_v7_0_init_pg(struct amdgpu_device *adev);
 static void gfx_v7_0_get_cu_info(struct amdgpu_device *adev);
 
+static void gfx_v7_0_free_microcode(struct amdgpu_device *adev)
+{
+   amdgpu_ucode_release(adev->gfx.pfp_fw);
+   amdgpu_ucode_release(adev->gfx.me_fw);
+   amdgpu_ucode_release(adev->gfx.ce_fw);
+   amdgpu_ucode_release(adev->gfx.mec_fw);
+   amdgpu_ucode_release(adev->gfx.mec2_fw);
+   amdgpu_ucode_release(adev->gfx.rlc_fw);
+}
+
 /*
  * Core functions
  */
@@ -927,88 +937,44 @@ static int gfx_v7_0_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.pfp_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
if (err)
goto out;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.me_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
if (err)
goto out;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce.bin", chip_name);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.ce_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, fw_name);
if (err)
goto out;
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mec.bin", chip_name);
-   err = request_firmware(&adev->gfx.mec_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.mec_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.mec_fw, fw_name);
if (err)
goto out;
 
if (adev->asic_type == CHIP_KAVERI) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mec2.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.mec2_fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.mec2_fw);
+   err = amdgpu_ucode_request(adev, &adev->gfx.mec2_fw, fw_name);
if (err)
goto out;
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_rlc.bin", chip_name);
-   err = request_firmware(&adev->gfx.rlc_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.rlc_fw, fw_name);
if (err)
goto out;
-   err = amdgpu_ucode_validate(adev->gfx.rlc_fw);
-
 out:
if (err) {
pr_err("gfx7: Failed to load firmware \"%s\"\n", fw_name);
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
-   release_firmware(adev->gfx.mec2_fw);
-   adev->gfx.mec2_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
+   gfx_v7_0_free_microcode(adev);
}
return err;
 }
 
-static void gfx_v7_0_free_microcode(struct amdgpu_device *adev)
-{
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
-   release_firmware(adev->gfx.mec2_fw);
-   adev->gfx.mec2_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
-}
-
 /**
  * gfx_v7_0_tiling_mode_table_init - init the hw tiling table
  *
-- 
2.34.1



[PATCH v5 41/45] drm/amd: Use `amdgpu_ucode_*` helpers for GPU info bin

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 14 +++---
 1 file changed, 3 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
index cdb681398a99..0d70eeb75731 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_device.c
@@ -1983,17 +1983,10 @@ static int amdgpu_device_parse_gpu_info_fw(struct 
amdgpu_device *adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_gpu_info.bin", chip_name);
-   err = request_firmware(&adev->firmware.gpu_info_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->firmware.gpu_info_fw, fw_name);
if (err) {
dev_err(adev->dev,
-   "Failed to load gpu_info firmware \"%s\"\n",
-   fw_name);
-   goto out;
-   }
-   err = amdgpu_ucode_validate(adev->firmware.gpu_info_fw);
-   if (err) {
-   dev_err(adev->dev,
-   "Failed to validate gpu_info firmware \"%s\"\n",
+   "Failed to get gpu_info firmware \"%s\"\n",
fw_name);
goto out;
}
@@ -4030,8 +4023,7 @@ void amdgpu_device_fini_sw(struct amdgpu_device *adev)
 
amdgpu_fence_driver_sw_fini(adev);
amdgpu_device_ip_fini(adev);
-   release_firmware(adev->firmware.gpu_info_fw);
-   adev->firmware.gpu_info_fw = NULL;
+   amdgpu_ucode_release(adev->firmware.gpu_info_fw);
adev->accel_working = false;
dma_fence_put(rcu_dereference_protected(adev->gang_submit, true));
 
-- 
2.34.1



[PATCH v5 32/45] drm/amd: Use `amdgpu_ucode_*` helpers for GMC6

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c | 14 +++---
 1 file changed, 3 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c 
b/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
index ec291d28edff..cc8f79a9d52a 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v6_0.c
@@ -131,19 +131,12 @@ static int gmc_v6_0_init_microcode(struct amdgpu_device 
*adev)
snprintf(fw_name, sizeof(fw_name), "amdgpu/si58_mc.bin");
else
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mc.bin", 
chip_name);
-   err = request_firmware(&adev->gmc.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-
-   err = amdgpu_ucode_validate(adev->gmc.fw);
-
-out:
+   err = amdgpu_ucode_request(adev, &adev->gmc.fw, fw_name);
if (err) {
dev_err(adev->dev,
   "si_mc: Failed to load firmware \"%s\"\n",
   fw_name);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(adev->gmc.fw);
}
return err;
 }
@@ -894,8 +887,7 @@ static int gmc_v6_0_sw_fini(void *handle)
amdgpu_vm_manager_fini(adev);
amdgpu_gart_table_vram_free(adev);
amdgpu_bo_fini(adev);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(adev->gmc.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v5 39/45] drm/amd: Use `amdgpu_ucode_*` helpers for VCE

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c | 14 +++---
 1 file changed, 3 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c
index 02cb3a12dd76..019763f7881b 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vce.c
@@ -158,19 +158,11 @@ int amdgpu_vce_sw_init(struct amdgpu_device *adev, 
unsigned long size)
return -EINVAL;
}
 
-   r = request_firmware(&adev->vce.fw, fw_name, adev->dev);
-   if (r) {
-   dev_err(adev->dev, "amdgpu_vce: Can't load firmware \"%s\"\n",
-   fw_name);
-   return r;
-   }
-
-   r = amdgpu_ucode_validate(adev->vce.fw);
+   r = amdgpu_ucode_request(adev, &adev->vce.fw, fw_name);
if (r) {
dev_err(adev->dev, "amdgpu_vce: Can't validate firmware 
\"%s\"\n",
fw_name);
-   release_firmware(adev->vce.fw);
-   adev->vce.fw = NULL;
+   amdgpu_ucode_release(adev->vce.fw);
return r;
}
 
@@ -226,7 +218,7 @@ int amdgpu_vce_sw_fini(struct amdgpu_device *adev)
for (i = 0; i < adev->vce.num_rings; i++)
amdgpu_ring_fini(&adev->vce.ring[i]);
 
-   release_firmware(adev->vce.fw);
+   amdgpu_ucode_release(adev->vce.fw);
mutex_destroy(&adev->vce.idle_mutex);
 
return 0;
-- 
2.34.1



[PATCH v5 38/45] drm/amd: Use `amdgpu_ucode_*` helpers for UVD

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c | 14 +++---
 1 file changed, 3 insertions(+), 11 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c
index 6eac649499d3..ce19e73b75bb 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c
@@ -260,19 +260,11 @@ int amdgpu_uvd_sw_init(struct amdgpu_device *adev)
return -EINVAL;
}
 
-   r = request_firmware(&adev->uvd.fw, fw_name, adev->dev);
-   if (r) {
-   dev_err(adev->dev, "amdgpu_uvd: Can't load firmware \"%s\"\n",
-   fw_name);
-   return r;
-   }
-
-   r = amdgpu_ucode_validate(adev->uvd.fw);
+   r = amdgpu_ucode_request(adev, &adev->uvd.fw, fw_name);
if (r) {
dev_err(adev->dev, "amdgpu_uvd: Can't validate firmware 
\"%s\"\n",
fw_name);
-   release_firmware(adev->uvd.fw);
-   adev->uvd.fw = NULL;
+   amdgpu_ucode_release(adev->uvd.fw);
return r;
}
 
@@ -394,7 +386,7 @@ int amdgpu_uvd_sw_fini(struct amdgpu_device *adev)
amdgpu_ring_fini(&adev->uvd.inst[j].ring_enc[i]);
}
amdgpu_bo_free_kernel(&adev->uvd.ib_bo, NULL, &addr);
-   release_firmware(adev->uvd.fw);
+   amdgpu_ucode_release(adev->uvd.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v5 28/45] drm/amd: Optimize SRIOV switch/case for PSP microcode load

2023-01-04 Thread Mario Limonciello
Now that IP version decoding is used, a number of case statements
can be combined.

Reviewed-by: Christian König 
Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c | 8 +---
 1 file changed, 1 insertion(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c 
b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
index 8a3a38ea7b46..15ffc5a6e4da 100644
--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
+++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c
@@ -132,14 +132,8 @@ static int psp_init_sriov_microcode(struct psp_context 
*psp)
 
switch (adev->ip_versions[MP0_HWIP][0]) {
case IP_VERSION(9, 0, 0):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
-   ret = psp_init_cap_microcode(psp, ucode_prefix);
-   break;
-   case IP_VERSION(11, 0, 9):
-   adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
-   ret = psp_init_cap_microcode(psp, ucode_prefix);
-   break;
case IP_VERSION(11, 0, 7):
+   case IP_VERSION(11, 0, 9):
adev->virt.autoload_ucode_id = AMDGPU_UCODE_ID_CP_MEC2;
ret = psp_init_cap_microcode(psp, ucode_prefix);
break;
-- 
2.34.1



[PATCH v5 31/45] drm/amd: Use `amdgpu_ucode_*` helpers for GFX8

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c | 94 ++-
 1 file changed, 33 insertions(+), 61 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c 
b/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c
index d47135606e3e..7197b342944c 100644
--- a/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gfx_v8_0.c
@@ -924,20 +924,14 @@ static int gfx_v8_0_ring_test_ib(struct amdgpu_ring 
*ring, long timeout)
 
 static void gfx_v8_0_free_microcode(struct amdgpu_device *adev)
 {
-   release_firmware(adev->gfx.pfp_fw);
-   adev->gfx.pfp_fw = NULL;
-   release_firmware(adev->gfx.me_fw);
-   adev->gfx.me_fw = NULL;
-   release_firmware(adev->gfx.ce_fw);
-   adev->gfx.ce_fw = NULL;
-   release_firmware(adev->gfx.rlc_fw);
-   adev->gfx.rlc_fw = NULL;
-   release_firmware(adev->gfx.mec_fw);
-   adev->gfx.mec_fw = NULL;
+   amdgpu_ucode_release(adev->gfx.pfp_fw);
+   amdgpu_ucode_release(adev->gfx.me_fw);
+   amdgpu_ucode_release(adev->gfx.ce_fw);
+   amdgpu_ucode_release(adev->gfx.rlc_fw);
+   amdgpu_ucode_release(adev->gfx.mec_fw);
if ((adev->asic_type != CHIP_STONEY) &&
(adev->asic_type != CHIP_TOPAZ))
-   release_firmware(adev->gfx.mec2_fw);
-   adev->gfx.mec2_fw = NULL;
+   amdgpu_ucode_release(adev->gfx.mec2_fw);
 
kfree(adev->gfx.rlc.register_list_format);
 }
@@ -989,18 +983,15 @@ static int gfx_v8_0_init_microcode(struct amdgpu_device 
*adev)
 
if (adev->asic_type >= CHIP_POLARIS10 && adev->asic_type <= 
CHIP_POLARIS12) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp_2.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
-   if (err == -ENOENT) {
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
+   if (err == -ENODEV) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, 
fw_name);
}
} else {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_pfp.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.pfp_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.pfp_fw, fw_name);
}
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.pfp_fw);
if (err)
goto out;
cp_hdr = (const struct gfx_firmware_header_v1_0 
*)adev->gfx.pfp_fw->data;
@@ -1009,18 +1000,15 @@ static int gfx_v8_0_init_microcode(struct amdgpu_device 
*adev)
 
if (adev->asic_type >= CHIP_POLARIS10 && adev->asic_type <= 
CHIP_POLARIS12) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me_2.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
-   if (err == -ENOENT) {
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
+   if (err == -ENODEV) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
}
} else {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_me.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.me_fw, fw_name, adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.me_fw, fw_name);
}
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gfx.me_fw);
if (err)
goto out;
cp_hdr = (const struct gfx_firmware_header_v1_0 *)adev->gfx.me_fw->data;
@@ -1030,18 +1018,15 @@ static int gfx_v8_0_init_microcode(struct amdgpu_device 
*adev)
 
if (adev->asic_type >= CHIP_POLARIS10 && adev->asic_type <= 
CHIP_POLARIS12) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce_2.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, adev->dev);
-   if (err == -ENOENT) {
+   err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, fw_name);
+   if (err == -ENODEV) {
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_ce.bin", 
chip_name);
-   err = request_firmware(&adev->gfx.ce_fw, fw_name, 
adev->dev);
+   err = amdgpu_ucode_request(adev, &adev->gfx.ce_fw, 
fw_name);
}
} else {
snprin

[PATCH v5 36/45] drm/amd: Use `amdgpu_ucode_*` helpers for SDMA3.0

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c | 18 ++
 1 file changed, 6 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c 
b/drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c
index 486d9b5c1b9e..337e348d5ae4 100644
--- a/drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/sdma_v3_0.c
@@ -250,10 +250,9 @@ static void sdma_v3_0_init_golden_registers(struct 
amdgpu_device *adev)
 static void sdma_v3_0_free_microcode(struct amdgpu_device *adev)
 {
int i;
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(adev->sdma.instance[i].fw);
 }
 
 /**
@@ -309,10 +308,7 @@ static int sdma_v3_0_init_microcode(struct amdgpu_device 
*adev)
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma.bin", chip_name);
else
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma1.bin", chip_name);
-   err = request_firmware(&adev->sdma.instance[i].fw, fw_name, 
adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->sdma.instance[i].fw);
+   err = amdgpu_ucode_request(adev, &adev->sdma.instance[i].fw, 
fw_name);
if (err)
goto out;
hdr = (const struct sdma_firmware_header_v1_0 
*)adev->sdma.instance[i].fw->data;
@@ -332,10 +328,8 @@ static int sdma_v3_0_init_microcode(struct amdgpu_device 
*adev)
 out:
if (err) {
pr_err("sdma_v3_0: Failed to load firmware \"%s\"\n", fw_name);
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(adev->sdma.instance[i].fw);
}
return err;
 }
-- 
2.34.1



[PATCH v5 35/45] drm/amd: Use `amdgpu_ucode_*` helpers for SDMA2.4

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c | 18 ++
 1 file changed, 6 insertions(+), 12 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c 
b/drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c
index c52d246a1d96..297695731efd 100644
--- a/drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c
+++ b/drivers/gpu/drm/amd/amdgpu/sdma_v2_4.c
@@ -113,10 +113,9 @@ static void sdma_v2_4_init_golden_registers(struct 
amdgpu_device *adev)
 static void sdma_v2_4_free_microcode(struct amdgpu_device *adev)
 {
int i;
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(adev->sdma.instance[i].fw);
 }
 
 /**
@@ -151,10 +150,7 @@ static int sdma_v2_4_init_microcode(struct amdgpu_device 
*adev)
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma.bin", chip_name);
else
snprintf(fw_name, sizeof(fw_name), 
"amdgpu/%s_sdma1.bin", chip_name);
-   err = request_firmware(&adev->sdma.instance[i].fw, fw_name, 
adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->sdma.instance[i].fw);
+   err = amdgpu_ucode_request(adev, &adev->sdma.instance[i].fw, 
fw_name);
if (err)
goto out;
hdr = (const struct sdma_firmware_header_v1_0 
*)adev->sdma.instance[i].fw->data;
@@ -176,10 +172,8 @@ static int sdma_v2_4_init_microcode(struct amdgpu_device 
*adev)
 out:
if (err) {
pr_err("sdma_v2_4: Failed to load firmware \"%s\"\n", fw_name);
-   for (i = 0; i < adev->sdma.num_instances; i++) {
-   release_firmware(adev->sdma.instance[i].fw);
-   adev->sdma.instance[i].fw = NULL;
-   }
+   for (i = 0; i < adev->sdma.num_instances; i++)
+   amdgpu_ucode_release(adev->sdma.instance[i].fw);
}
return err;
 }
-- 
2.34.1



[PATCH v5 34/45] drm/amd: Use `amdgpu_ucode_*` helpers for GMC8

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c | 13 +++--
 1 file changed, 3 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c 
b/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
index 382dde1ce74c..caea65de3e85 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v8_0.c
@@ -264,16 +264,10 @@ static int gmc_v8_0_init_microcode(struct amdgpu_device 
*adev)
}
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mc.bin", chip_name);
-   err = request_firmware(&adev->gmc.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gmc.fw);
-
-out:
+   err = amdgpu_ucode_request(adev, &adev->gmc.fw, fw_name);
if (err) {
pr_err("mc: Failed to load firmware \"%s\"\n", fw_name);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(adev->gmc.fw);
}
return err;
 }
@@ -1203,8 +1197,7 @@ static int gmc_v8_0_sw_fini(void *handle)
kfree(adev->gmc.vm_fault_info);
amdgpu_gart_table_vram_free(adev);
amdgpu_bo_fini(adev);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(adev->gmc.fw);
 
return 0;
 }
-- 
2.34.1



[PATCH v5 27/45] drm/amd: Load SMU microcode during early_init

2023-01-04 Thread Mario Limonciello
This will ensure that the microcode is available before the firmware
framebuffer has been destroyed.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c | 12 +---
 1 file changed, 5 insertions(+), 7 deletions(-)

diff --git a/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c 
b/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
index 2fa79f892a92..ec52830dde24 100644
--- a/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
+++ b/drivers/gpu/drm/amd/pm/swsmu/amdgpu_smu.c
@@ -623,6 +623,7 @@ static int smu_early_init(void *handle)
 {
struct amdgpu_device *adev = (struct amdgpu_device *)handle;
struct smu_context *smu;
+   int r;
 
smu = kzalloc(sizeof(struct smu_context), GFP_KERNEL);
if (!smu)
@@ -640,7 +641,10 @@ static int smu_early_init(void *handle)
adev->powerplay.pp_handle = smu;
adev->powerplay.pp_funcs = &swsmu_pm_funcs;
 
-   return smu_set_funcs(adev);
+   r = smu_set_funcs(adev);
+   if (r)
+   return r;
+   return smu_init_microcode(smu);
 }
 
 static int smu_set_default_dpm_table(struct smu_context *smu)
@@ -1067,12 +1071,6 @@ static int smu_sw_init(void *handle)
smu->smu_dpm.dpm_level = AMD_DPM_FORCED_LEVEL_AUTO;
smu->smu_dpm.requested_dpm_level = AMD_DPM_FORCED_LEVEL_AUTO;
 
-   ret = smu_init_microcode(smu);
-   if (ret) {
-   dev_err(adev->dev, "Failed to load smu firmware!\n");
-   return ret;
-   }
-
ret = smu_smc_table_sw_init(smu);
if (ret) {
dev_err(adev->dev, "Failed to sw init smc table!\n");
-- 
2.34.1



[PATCH v5 33/45] drm/amd: Use `amdgpu_ucode_*` helpers for GMC7

2023-01-04 Thread Mario Limonciello
The `amdgpu_ucode_request` helper will ensure that the return code for
missing firmware is -ENODEV so that early_init can fail.

The `amdgpu_ucode_release` helper is for symmetry on unloading.

Signed-off-by: Mario Limonciello 
---
 drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c | 13 +++--
 1 file changed, 3 insertions(+), 10 deletions(-)

diff --git a/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c 
b/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
index 979da6f510e8..934410701a15 100644
--- a/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
+++ b/drivers/gpu/drm/amd/amdgpu/gmc_v7_0.c
@@ -156,16 +156,10 @@ static int gmc_v7_0_init_microcode(struct amdgpu_device 
*adev)
 
snprintf(fw_name, sizeof(fw_name), "amdgpu/%s_mc.bin", chip_name);
 
-   err = request_firmware(&adev->gmc.fw, fw_name, adev->dev);
-   if (err)
-   goto out;
-   err = amdgpu_ucode_validate(adev->gmc.fw);
-
-out:
+   err = amdgpu_ucode_request(adev, &adev->gmc.fw, fw_name);
if (err) {
pr_err("cik_mc: Failed to load firmware \"%s\"\n", fw_name);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(adev->gmc.fw);
}
return err;
 }
@@ -1081,8 +1075,7 @@ static int gmc_v7_0_sw_fini(void *handle)
kfree(adev->gmc.vm_fault_info);
amdgpu_gart_table_vram_free(adev);
amdgpu_bo_fini(adev);
-   release_firmware(adev->gmc.fw);
-   adev->gmc.fw = NULL;
+   amdgpu_ucode_release(adev->gmc.fw);
 
return 0;
 }
-- 
2.34.1



  1   2   >