linux-acpi.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Huang Ying <ying.huang@intel.com>
To: lenb@kernel.org
Cc: linux-kernel@vger.kernel.org, ying.huang@intel.com,
	andi@firstfloor.org, linux-acpi@vger.kernel.org,
	Andi Kleen <ak@linux.intel.com>
Subject: [PATCH -v5 14/14] ACPI, APEI, EINJ injection parameters support
Date: Tue, 18 May 2010 14:35:24 +0800	[thread overview]
Message-ID: <1274164524-6092-15-git-send-email-ying.huang@intel.com> (raw)
In-Reply-To: <1274164524-6092-1-git-send-email-ying.huang@intel.com>

Some hardware error injection needs parameters, for example, it is
useful to specify memory address and memory address mask for memory
errors.

Some BIOSes allow parameters to be specified via an unpublished
extension. This patch adds support to it. The parameters will be
ignored on machines without necessary BIOS support.

Signed-off-by: Huang Ying <ying.huang@intel.com>
Signed-off-by: Andi Kleen <ak@linux.intel.com>
---
 Documentation/acpi/apei/einj.txt |   10 +++++
 drivers/acpi/apei/einj.c         |   72 ++++++++++++++++++++++++++++++++++++---
 2 files changed, 77 insertions(+), 5 deletions(-)

--- a/Documentation/acpi/apei/einj.txt
+++ b/Documentation/acpi/apei/einj.txt
@@ -45,5 +45,15 @@ directory apei/einj. The following files
   injection. Before this, please specify all necessary error
   parameters.
 
+- param1
+  This file is used to set the first error parameter value. Effect of
+  parameter depends on error_type specified. For memory error, this is
+  physical memory address.
+
+- param2
+  This file is used to set the second error parameter value. Effect of
+  parameter depends on error_type specified. For memory error, this is
+  physical memory address mask.
+
 For more information about EINJ, please refer to ACPI specification
 version 4.0, section 17.5.
--- a/drivers/acpi/apei/einj.c
+++ b/drivers/acpi/apei/einj.c
@@ -7,7 +7,7 @@
  * For more information about EINJ, please refer to ACPI Specification
  * version 4.0, section 17.5.
  *
- * Copyright 2009 Intel Corp.
+ * Copyright 2009-2010 Intel Corp.
  *   Author: Huang Ying <ying.huang@intel.com>
  *
  * This program is free software; you can redistribute it and/or
@@ -42,6 +42,20 @@
 /* Firmware should respond within 1 miliseconds */
 #define FIRMWARE_TIMEOUT	(1 * NSEC_PER_MSEC)
 
+/*
+ * Some BIOSes allow parameters to the SET_ERROR_TYPE entries in the
+ * EINJ table through an unpublished extension. Use with caution as
+ * most will ignore the parameter and make their own choice of address
+ * for error injection.
+ */
+struct einj_parameter {
+	u64 type;
+	u64 reserved1;
+	u64 reserved2;
+	u64 param1;
+	u64 param2;
+};
+
 #define EINJ_OP_BUSY			0x1
 #define EINJ_STATUS_SUCCESS		0x0
 #define EINJ_STATUS_FAIL		0x1
@@ -85,6 +99,8 @@ static struct apei_exec_ins_type einj_in
  */
 static DEFINE_MUTEX(einj_mutex);
 
+static struct einj_parameter *einj_param;
+
 static void einj_exec_ctx_init(struct apei_exec_context *ctx)
 {
 	apei_exec_ctx_init(ctx, einj_ins_type, ARRAY_SIZE(einj_ins_type),
@@ -130,6 +146,26 @@ static int einj_timedout(u64 *t)
 	return 0;
 }
 
+static u64 einj_get_parameter_address(void)
+{
+	int i;
+	u64 paddr = 0;
+	struct acpi_whea_header *entry;
+
+	entry = EINJ_TAB_ENTRY(einj_tab);
+	for (i = 0; i < einj_tab->entries; i++) {
+		if (entry->action == ACPI_EINJ_SET_ERROR_TYPE &&
+		    entry->instruction == ACPI_EINJ_WRITE_REGISTER &&
+		    entry->register_region.space_id ==
+		    ACPI_ADR_SPACE_SYSTEM_MEMORY)
+			memcpy(&paddr, &entry->register_region.address,
+			       sizeof(paddr));
+		entry++;
+	}
+
+	return paddr;
+}
+
 /* do sanity check to trigger table */
 static int einj_check_trigger_header(struct acpi_einj_trigger *trigger_tab)
 {
@@ -233,7 +269,7 @@ out:
 	return rc;
 }
 
-static int __einj_error_inject(u32 type)
+static int __einj_error_inject(u32 type, u64 param1, u64 param2)
 {
 	struct apei_exec_context ctx;
 	u64 val, trigger_paddr, timeout = FIRMWARE_TIMEOUT;
@@ -248,6 +284,10 @@ static int __einj_error_inject(u32 type)
 	rc = apei_exec_run(&ctx, ACPI_EINJ_SET_ERROR_TYPE);
 	if (rc)
 		return rc;
+	if (einj_param) {
+		writeq(param1, &einj_param->param1);
+		writeq(param2, &einj_param->param2);
+	}
 	rc = apei_exec_run(&ctx, ACPI_EINJ_EXECUTE_OPERATION);
 	if (rc)
 		return rc;
@@ -281,18 +321,20 @@ static int __einj_error_inject(u32 type)
 }
 
 /* Inject the specified hardware error */
-static int einj_error_inject(u32 type)
+static int einj_error_inject(u32 type, u64 param1, u64 param2)
 {
 	int rc;
 
 	mutex_lock(&einj_mutex);
-	rc = __einj_error_inject(type);
+	rc = __einj_error_inject(type, param1, param2);
 	mutex_unlock(&einj_mutex);
 
 	return rc;
 }
 
 static u32 error_type;
+static u64 error_param1;
+static u64 error_param2;
 static struct dentry *einj_debug_dir;
 
 static int available_error_type_show(struct seq_file *m, void *v)
@@ -376,7 +418,7 @@ static int error_inject_set(void *data,
 	if (!error_type)
 		return -EINVAL;
 
-	return einj_error_inject(error_type);
+	return einj_error_inject(error_type, error_param1, error_param2);
 }
 
 DEFINE_SIMPLE_ATTRIBUTE(error_inject_fops, NULL,
@@ -399,6 +441,7 @@ static int einj_check_table(struct acpi_
 static int __init einj_init(void)
 {
 	int rc;
+	u64 param_paddr;
 	acpi_status status;
 	struct dentry *fentry;
 	struct apei_exec_context ctx;
@@ -436,6 +479,14 @@ static int __init einj_init(void)
 				     einj_debug_dir, NULL, &error_type_fops);
 	if (!fentry)
 		goto err_cleanup;
+	fentry = debugfs_create_x64("param1", S_IRUSR | S_IWUSR,
+				    einj_debug_dir, &error_param1);
+	if (!fentry)
+		goto err_cleanup;
+	fentry = debugfs_create_x64("param2", S_IRUSR | S_IWUSR,
+				    einj_debug_dir, &error_param2);
+	if (!fentry)
+		goto err_cleanup;
 	fentry = debugfs_create_file("error_inject", S_IWUSR,
 				     einj_debug_dir, NULL, &error_inject_fops);
 	if (!fentry)
@@ -452,11 +503,20 @@ static int __init einj_init(void)
 	rc = apei_exec_pre_map_gars(&ctx);
 	if (rc)
 		goto err_release;
+	param_paddr = einj_get_parameter_address();
+	if (param_paddr) {
+		einj_param = ioremap(param_paddr, sizeof(*einj_param));
+		rc = -ENOMEM;
+		if (!einj_param)
+			goto err_unmap;
+	}
 
 	pr_info(EINJ_PFX "Error INJection is initialized.\n");
 
 	return 0;
 
+err_unmap:
+	apei_exec_post_unmap_gars(&ctx);
 err_release:
 	apei_resources_release(&einj_resources);
 err_fini:
@@ -471,6 +531,8 @@ static void __exit einj_exit(void)
 {
 	struct apei_exec_context ctx;
 
+	if (einj_param)
+		iounmap(einj_param);
 	einj_exec_ctx_init(&ctx);
 	apei_exec_post_unmap_gars(&ctx);
 	apei_resources_release(&einj_resources);

  parent reply	other threads:[~2010-05-18  6:35 UTC|newest]

Thread overview: 21+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2010-05-18  6:35 [PATCH -v5 00/14] ACPI, APEI support Huang Ying
2010-05-18  6:35 ` [PATCH -v5 01/14] ACPI, IO memory pre-mapping and atomic accessing Huang Ying
2010-05-18  6:35 ` [PATCH -v5 02/14] ACPI, APEI, APEI supporting infrastructure Huang Ying
2010-05-18  6:35 ` [PATCH -v5 03/14] ACPI, APEI, HEST table parsing Huang Ying
2010-05-18  6:35 ` [PATCH -v5 04/14] ACPI, APEI, EINJ support Huang Ying
2010-05-18  6:35 ` [PATCH -v5 05/14] ACPI, APEI, Document for APEI Huang Ying
2010-05-18 21:51   ` Randy Dunlap
2010-05-19  3:06     ` Huang Ying
2010-05-20  2:39       ` Len Brown
2010-05-20  2:43         ` Huang Ying
2010-05-18  6:35 ` [PATCH -v5 06/14] ACPI, APEI, PCIE AER, use general HEST table parsing in AER firmware_first setup Huang Ying
2010-05-18  6:35 ` [PATCH -v5 07/14] ACPI Hardware Error Device (PNP0C33) support Huang Ying
2010-05-18  6:35 ` [PATCH -v5 08/14] Unified UUID/GUID definition Huang Ying
2010-05-18  6:35 ` [PATCH -v5 09/14] ACPI, APEI, UEFI Common Platform Error Record (CPER) header Huang Ying
2010-05-18  6:35 ` [PATCH -v5 10/14] ACPI, APEI, Generic Hardware Error Source memory error support Huang Ying
2010-05-18  6:35 ` [PATCH -v5 11/14] ACPI, APEI, Error Record Serialization Table (ERST) support Huang Ying
2010-05-18  6:35 ` [PATCH -v5 12/14] ACPI, APEI, Use ERST for persistent storage of MCE Huang Ying
2010-05-18  6:35 ` [PATCH -v5 13/14] Add x64 support to debugfs Huang Ying
2010-05-18  6:35 ` Huang Ying [this message]
2010-05-18  8:48 ` [PATCH -v5 00/14] ACPI, APEI support Andi Kleen
2010-05-20  2:44 ` Len Brown

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=1274164524-6092-15-git-send-email-ying.huang@intel.com \
    --to=ying.huang@intel.com \
    --cc=ak@linux.intel.com \
    --cc=andi@firstfloor.org \
    --cc=lenb@kernel.org \
    --cc=linux-acpi@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    /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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).