diff options
author | Loc Ho <lho@apm.com> | 2017-07-04 00:33:09 +0300 |
---|---|---|
committer | Rafael J. Wysocki <rafael.j.wysocki@intel.com> | 2017-07-04 22:29:38 +0300 |
commit | 79a648328d2a604524a30523ca763fbeca0f70e3 (patch) | |
tree | 9d44cba925a86c9bc5d8b178e45dcc5291ddd1ba /drivers/acpi/spcr.c | |
parent | 2bece49394872d36bbc5767fd643deac05920c55 (diff) | |
download | linux-79a648328d2a604524a30523ca763fbeca0f70e3.tar.xz |
ACPI: SPCR: Workaround for APM X-Gene 8250 UART 32-alignment errata
APM X-Gene verion 1 and 2 have an 8250 UART with its register
aligned to 32-bit. In addition, the latest released BIOS
encodes the access field as 8-bit access instead 32-bit access.
This causes no console with ACPI boot as the console
will not match X-Gene UART port due to the lack of mmio32
option.
Signed-off-by: Loc Ho <lho@apm.com>
Acked-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Diffstat (limited to 'drivers/acpi/spcr.c')
-rw-r--r-- | drivers/acpi/spcr.c | 22 |
1 files changed, 22 insertions, 0 deletions
diff --git a/drivers/acpi/spcr.c b/drivers/acpi/spcr.c index 29050630f3da..4ac3e06b41d8 100644 --- a/drivers/acpi/spcr.c +++ b/drivers/acpi/spcr.c @@ -36,6 +36,26 @@ static bool qdf2400_erratum_44_present(struct acpi_table_header *h) return false; } +/* + * APM X-Gene v1 and v2 UART hardware is an 16550 like device but has its + * register aligned to 32-bit. In addition, the BIOS also encoded the + * access width to be 8 bits. This function detects this errata condition. + */ +static bool xgene_8250_erratum_present(struct acpi_table_spcr *tb) +{ + if (tb->interface_type != ACPI_DBG2_16550_COMPATIBLE) + return false; + + if (memcmp(tb->header.oem_id, "APMC0D", ACPI_OEM_ID_SIZE)) + return false; + + if (!memcmp(tb->header.oem_table_id, "XGENESPC", + ACPI_OEM_TABLE_ID_SIZE) && tb->header.oem_revision == 0) + return true; + + return false; +} + /** * parse_spcr() - parse ACPI SPCR table and add preferred console * @@ -129,6 +149,8 @@ int __init parse_spcr(bool earlycon) if (qdf2400_erratum_44_present(&table->header)) uart = "qdf2400_e44"; + if (xgene_8250_erratum_present(table)) + iotype = "mmio32"; snprintf(opts, sizeof(opts), "%s,%s,0x%llx,%d", uart, iotype, table->serial_port.address, baud_rate); |