From: Jonathan Cameron <Jonathan.Cameron@huawei.com>
To: Zaid Alali <zaidal@os.amperecomputing.com>
Cc: <rafael@kernel.org>, <lenb@kernel.org>, <james.morse@arm.com>,
<tony.luck@intel.com>, <bp@alien8.de>, <robert.moore@intel.com>,
<dan.j.williams@intel.com>, <Benjamin.Cheatham@amd.com>,
<Avadhut.Naik@amd.com>, <viro@zeniv.linux.org.uk>,
<arnd@arndb.de>, <ira.weiny@intel.com>, <dave.jiang@intel.com>,
<sthanneeru.opensrc@micron.com>, <linux-acpi@vger.kernel.org>,
<linux-kernel@vger.kernel.org>, <acpica-devel@lists.linux.dev>
Subject: Re: [PATCH v3 8/9] ACPI: APEI: EINJ: Enable EINJv2 error injections
Date: Wed, 12 Feb 2025 17:04:14 +0000 [thread overview]
Message-ID: <20250212170414.000059c4@huawei.com> (raw)
In-Reply-To: <20250210183705.1114624-9-zaidal@os.amperecomputing.com>
On Mon, 10 Feb 2025 10:37:04 -0800
Zaid Alali <zaidal@os.amperecomputing.com> wrote:
> Enable the driver to inject EINJv2 type errors. The component
> array values are parsed from user_input and expected to contain
> hex values for component id and syndrome separated by space,
> and multiple components are separated by new line as follows:
>
> component_id1 component_syndrome1
> component_id2 component_syndrome2
> :
> component_id(n) component_syndrome(n)
>
> for example:
>
> $comp_arr="0x1 0x2
> >0x1 0x4
> >0x2 0x4"
> $cd /sys/kernel/debug/apei/einj/
> $echo "$comp_arr" > einjv2_component_array
>
> Signed-off-by: Zaid Alali <zaidal@os.amperecomputing.com>
> ---
> drivers/acpi/apei/einj-core.c | 103 +++++++++++++++++++++++++++++-----
> 1 file changed, 89 insertions(+), 14 deletions(-)
>
> diff --git a/drivers/acpi/apei/einj-core.c b/drivers/acpi/apei/einj-core.c
> index 40ebdbc4961f..46359019ca03 100644
> --- a/drivers/acpi/apei/einj-core.c
> +++ b/drivers/acpi/apei/einj-core.c
> @@ -87,6 +87,13 @@ enum {
> SETWA_FLAGS_APICID = 1,
> SETWA_FLAGS_MEM = 2,
> SETWA_FLAGS_PCIE_SBDF = 4,
> + SETWA_FLAGS_EINJV2 = 8,
> +};
> +
> +enum {
> + EINJV2_PROCESSOR_ERROR = 0x1,
> + EINJV2_MEMORY_ERROR = 0x2,
> + EINJV2_PCIE_ERROR = 0x4,
> };
>
> /*
> @@ -111,6 +118,7 @@ static char vendor_dev[64];
> static struct debugfs_blob_wrapper einjv2_component_arr;
> static u64 component_count;
> static void *user_input;
> +static int nr_components;
> static u32 available_error_type;
> static u32 available_error_type_v2;
>
> @@ -181,6 +189,8 @@ static DEFINE_MUTEX(einj_mutex);
> bool einj_initialized __ro_after_init;
>
> static void __iomem *einj_param;
> +static u32 v5param_size;
> +static bool is_V2;
>
> static void einj_exec_ctx_init(struct apei_exec_context *ctx)
> {
> @@ -288,11 +298,23 @@ static void *einj_get_parameter_address(void)
> struct set_error_type_with_address v5param;
> void __iomem *p;
>
> + v5param_size = sizeof(v5param);
> p = acpi_os_map_iomem(pa_v5, sizeof(v5param));
> if (p) {
> - memcpy_fromio(&v5param, p, sizeof(v5param));
> + int offset, len;
> +
> + memcpy_fromio(&v5param, p, v5param_size);
Here you clear the first part, but not the extra elements.
> acpi5 = 1;
> check_vendor_extension(pa_v5, &v5param);
> + if (available_error_type & ACPI65_EINJV2_SUPP) {
> + len = v5param.einjv2_struct.length;
> + offset = offsetof(struct einjv2_extension_struct, component_arr);
> + nr_components = (len - offset) / 32;
> + acpi_os_unmap_iomem(p, v5param_size);
> + v5param_size = sizeof(v5param) +
> + (nr_components * sizeof(struct syndrome_array));
struct_size()
> + p = acpi_os_map_iomem(pa_v5, v5param_size);
> + }
> return p;
> }
> }
> @@ -486,8 +508,8 @@ static int __einj_error_inject(u32 type, u32 flags, u64 param1, u64 param2,
> if (acpi5) {
> struct set_error_type_with_address *v5param;
>
> - v5param = kmalloc(sizeof(*v5param), GFP_KERNEL);
> - memcpy_fromio(v5param, einj_param, sizeof(*v5param));
> + v5param = kmalloc(v5param_size, GFP_KERNEL);
This patch is the point where kmalloc makes sense. I'd introduce it here
rather than in earlier patch.
> + memcpy_fromio(v5param, einj_param, v5param_size);
> v5param->type = type;
> if (type & ACPI5_VENDOR_BIT) {
> switch (vendor_flags) {
...
> /* Inject the specified hardware error */
> @@ -597,10 +663,15 @@ int einj_error_inject(u32 type, u32 flags, u64 param1, u64 param2, u64 param3,
> u64 base_addr, size;
>
> /* If user manually set "flags", make sure it is legal */
> - if (flags && (flags &
> - ~(SETWA_FLAGS_APICID|SETWA_FLAGS_MEM|SETWA_FLAGS_PCIE_SBDF)))
> + if (flags && (flags & ~(SETWA_FLAGS_APICID | SETWA_FLAGS_MEM |
> + SETWA_FLAGS_PCIE_SBDF | SETWA_FLAGS_EINJV2)))
> return -EINVAL;
>
> + /* check if type is a valid EINJv2 error type */
> + if (is_V2) {
> + if (!(type & available_error_type_v2))
> + return -EINVAL;
> + }
> /*
> * We need extra sanity checks for memory errors.
> * Other types leap directly to injection.
> @@ -750,7 +821,7 @@ int einj_validate_error_type(u64 type)
> if (tval & (tval - 1))
> return -EINVAL;
> if (!vendor)
> - if (!(type & available_error_type))
> + if (!(type & (available_error_type | available_error_type_v2)))
> return -EINVAL;
>
> return 0;
> @@ -763,12 +834,14 @@ static ssize_t error_type_set(struct file *file, const char __user *buf,
> u64 val;
>
> memset(einj_buf, 0, BUFF_SIZE);
> + is_V2 = false;
> if (copy_from_user(einj_buf, buf, count))
> return -EFAULT;
>
> if (strncmp(einj_buf, "V2_", 3) == 0) {
> if (!sscanf(einj_buf, "V2_%llx", &val))
> return -EINVAL;
> + is_V2 = true;
Given you have an if / else here. Set is_V2 = false
in the else rather that default and override in one leg of
the if / else.
> } else
> if (!sscanf(einj_buf, "%llx", &val))
> return -EINVAL;
> @@ -792,6 +865,9 @@ static int error_inject_set(void *data, u64 val)
> if (!error_type)
> return -EINVAL;
>
> + if (is_V2)
> + error_flags |= SETWA_FLAGS_EINJV2;
> +
> return einj_error_inject(error_type, error_flags, error_param1, error_param2,
> error_param3, error_param4);
> }
> @@ -944,11 +1020,10 @@ static void __exit einj_remove(struct platform_device *pdev)
> struct apei_exec_context ctx;
>
> if (einj_param) {
> - acpi_size size = (acpi5) ?
> - sizeof(struct set_error_type_with_address) :
> - sizeof(struct einj_parameter);
> -
> - acpi_os_unmap_iomem(einj_param, size);
Unless strong reason to change I'd keep to existing style and just
replace the true condition with v5param_size
> + if (acpi5)
> + acpi_os_unmap_iomem(einj_param, v5param_size);
> + else
> + acpi_os_unmap_iomem(einj_param, sizeof(struct einj_parameter));
> if (vendor_errors.size)
> acpi_os_unmap_memory(vendor_errors.data, vendor_errors.size);
> }
next prev parent reply other threads:[~2025-02-12 17:04 UTC|newest]
Thread overview: 16+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-02-10 18:36 [PATCH v3 0/9] Enable EINJv2 Support Zaid Alali
2025-02-10 18:36 ` [PATCH v3 1/9] ACPICA: Update values to hex to follow ACPI specs Zaid Alali
2025-02-10 18:36 ` [PATCH v3 2/9] ACPICA: Add EINJv2 get error type action Zaid Alali
2025-02-10 18:36 ` [PATCH v3 3/9] ACPI: APEI: EINJ: Fix kernel test robot sparse warning Zaid Alali
2025-02-12 16:35 ` Jonathan Cameron
2025-02-10 18:37 ` [PATCH v3 4/9] ACPI: APEI: EINJ: Remove redundant calls to einj_get_available_error_type Zaid Alali
2025-02-12 16:37 ` Jonathan Cameron
2025-02-10 18:37 ` [PATCH v3 5/9] ACPI: APEI: EINJ: Enable the discovery of EINJv2 capabilities Zaid Alali
2025-02-12 16:47 ` Jonathan Cameron
2025-02-10 18:37 ` [PATCH v3 6/9] ACPI: APEI: EINJ: Add einjv2 extension struct Zaid Alali
2025-02-12 16:49 ` Jonathan Cameron
2025-02-10 18:37 ` [PATCH v3 7/9] ACPI: APEI: EINJ: Add debugfs files for EINJv2 support Zaid Alali
2025-02-12 16:54 ` Jonathan Cameron
2025-02-10 18:37 ` [PATCH v3 8/9] ACPI: APEI: EINJ: Enable EINJv2 error injections Zaid Alali
2025-02-12 17:04 ` Jonathan Cameron [this message]
2025-02-10 18:37 ` [PATCH v3 9/9] ACPI: APEI: EINJ: Update the documentation for EINJv2 support Zaid Alali
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20250212170414.000059c4@huawei.com \
--to=jonathan.cameron@huawei.com \
--cc=Avadhut.Naik@amd.com \
--cc=Benjamin.Cheatham@amd.com \
--cc=acpica-devel@lists.linux.dev \
--cc=arnd@arndb.de \
--cc=bp@alien8.de \
--cc=dan.j.williams@intel.com \
--cc=dave.jiang@intel.com \
--cc=ira.weiny@intel.com \
--cc=james.morse@arm.com \
--cc=lenb@kernel.org \
--cc=linux-acpi@vger.kernel.org \
--cc=linux-kernel@vger.kernel.org \
--cc=rafael@kernel.org \
--cc=robert.moore@intel.com \
--cc=sthanneeru.opensrc@micron.com \
--cc=tony.luck@intel.com \
--cc=viro@zeniv.linux.org.uk \
--cc=zaidal@os.amperecomputing.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.