mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-25 21:24:08 +08:00
tty/serial fixes for 4.13-rc5
Here are two tty serial driver fixes for 4.13-rc5. One is a revert of a -rc1 patch that turned out to not be a good idea, and the other is a fix for the pl011 serial driver. Both have been in linux-next with no reported issues. Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> -----BEGIN PGP SIGNATURE----- iG0EABECAC0WIQT0tgzFv3jCIUoxPcsxR9QN2y37KQUCWY+1vw8cZ3JlZ0Brcm9h aC5jb20ACgkQMUfUDdst+ykreACeLI2spfagnOcnW264PGHxLMgj47EAn0JPSNIg 5FLEtVsgxMuc8kc4LkDb =58g+ -----END PGP SIGNATURE----- Merge tag 'tty-4.13-rc5' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty Pull tty/serial fixes from Greg KH: "Here are two tty serial driver fixes for 4.13-rc5. One is a revert of a -rc1 patch that turned out to not be a good idea, and the other is a fix for the pl011 serial driver. Both have been in linux-next with no reported issues" * tag 'tty-4.13-rc5' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/tty: Revert "serial: Delete dead code for CIR serial ports" tty: pl011: fix initialization order of QDF2400 E44
This commit is contained in:
commit
438630ef5b
@ -16,6 +16,16 @@
|
|||||||
#include <linux/kernel.h>
|
#include <linux/kernel.h>
|
||||||
#include <linux/serial_core.h>
|
#include <linux/serial_core.h>
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Erratum 44 for QDF2432v1 and QDF2400v1 SoCs describes the BUSY bit as
|
||||||
|
* occasionally getting stuck as 1. To avoid the potential for a hang, check
|
||||||
|
* TXFE == 0 instead of BUSY == 1. This may not be suitable for all UART
|
||||||
|
* implementations, so only do so if an affected platform is detected in
|
||||||
|
* parse_spcr().
|
||||||
|
*/
|
||||||
|
bool qdf2400_e44_present;
|
||||||
|
EXPORT_SYMBOL(qdf2400_e44_present);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Some Qualcomm Datacenter Technologies SoCs have a defective UART BUSY bit.
|
* Some Qualcomm Datacenter Technologies SoCs have a defective UART BUSY bit.
|
||||||
* Detect them by examining the OEM fields in the SPCR header, similiar to PCI
|
* Detect them by examining the OEM fields in the SPCR header, similiar to PCI
|
||||||
@ -147,8 +157,30 @@ int __init parse_spcr(bool earlycon)
|
|||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (qdf2400_erratum_44_present(&table->header))
|
/*
|
||||||
uart = "qdf2400_e44";
|
* If the E44 erratum is required, then we need to tell the pl011
|
||||||
|
* driver to implement the work-around.
|
||||||
|
*
|
||||||
|
* The global variable is used by the probe function when it
|
||||||
|
* creates the UARTs, whether or not they're used as a console.
|
||||||
|
*
|
||||||
|
* If the user specifies "traditional" earlycon, the qdf2400_e44
|
||||||
|
* console name matches the EARLYCON_DECLARE() statement, and
|
||||||
|
* SPCR is not used. Parameter "earlycon" is false.
|
||||||
|
*
|
||||||
|
* If the user specifies "SPCR" earlycon, then we need to update
|
||||||
|
* the console name so that it also says "qdf2400_e44". Parameter
|
||||||
|
* "earlycon" is true.
|
||||||
|
*
|
||||||
|
* For consistency, if we change the console name, then we do it
|
||||||
|
* for everyone, not just earlycon.
|
||||||
|
*/
|
||||||
|
if (qdf2400_erratum_44_present(&table->header)) {
|
||||||
|
qdf2400_e44_present = true;
|
||||||
|
if (earlycon)
|
||||||
|
uart = "qdf2400_e44";
|
||||||
|
}
|
||||||
|
|
||||||
if (xgene_8250_erratum_present(table))
|
if (xgene_8250_erratum_present(table))
|
||||||
iotype = "mmio32";
|
iotype = "mmio32";
|
||||||
|
|
||||||
|
@ -1043,13 +1043,24 @@ int serial8250_register_8250_port(struct uart_8250_port *up)
|
|||||||
if (up->dl_write)
|
if (up->dl_write)
|
||||||
uart->dl_write = up->dl_write;
|
uart->dl_write = up->dl_write;
|
||||||
|
|
||||||
if (serial8250_isa_config != NULL)
|
if (uart->port.type != PORT_8250_CIR) {
|
||||||
serial8250_isa_config(0, &uart->port,
|
if (serial8250_isa_config != NULL)
|
||||||
&uart->capabilities);
|
serial8250_isa_config(0, &uart->port,
|
||||||
|
&uart->capabilities);
|
||||||
|
|
||||||
ret = uart_add_one_port(&serial8250_reg, &uart->port);
|
ret = uart_add_one_port(&serial8250_reg,
|
||||||
if (ret == 0)
|
&uart->port);
|
||||||
ret = uart->port.line;
|
if (ret == 0)
|
||||||
|
ret = uart->port.line;
|
||||||
|
} else {
|
||||||
|
dev_info(uart->port.dev,
|
||||||
|
"skipping CIR port at 0x%lx / 0x%llx, IRQ %d\n",
|
||||||
|
uart->port.iobase,
|
||||||
|
(unsigned long long)uart->port.mapbase,
|
||||||
|
uart->port.irq);
|
||||||
|
|
||||||
|
ret = 0;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
mutex_unlock(&serial_mutex);
|
mutex_unlock(&serial_mutex);
|
||||||
|
|
||||||
|
@ -142,15 +142,7 @@ static struct vendor_data vendor_sbsa = {
|
|||||||
.fixed_options = true,
|
.fixed_options = true,
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
#ifdef CONFIG_ACPI_SPCR_TABLE
|
||||||
* Erratum 44 for QDF2432v1 and QDF2400v1 SoCs describes the BUSY bit as
|
|
||||||
* occasionally getting stuck as 1. To avoid the potential for a hang, check
|
|
||||||
* TXFE == 0 instead of BUSY == 1. This may not be suitable for all UART
|
|
||||||
* implementations, so only do so if an affected platform is detected in
|
|
||||||
* parse_spcr().
|
|
||||||
*/
|
|
||||||
static bool qdf2400_e44_present = false;
|
|
||||||
|
|
||||||
static struct vendor_data vendor_qdt_qdf2400_e44 = {
|
static struct vendor_data vendor_qdt_qdf2400_e44 = {
|
||||||
.reg_offset = pl011_std_offsets,
|
.reg_offset = pl011_std_offsets,
|
||||||
.fr_busy = UART011_FR_TXFE,
|
.fr_busy = UART011_FR_TXFE,
|
||||||
@ -165,6 +157,7 @@ static struct vendor_data vendor_qdt_qdf2400_e44 = {
|
|||||||
.always_enabled = true,
|
.always_enabled = true,
|
||||||
.fixed_options = true,
|
.fixed_options = true,
|
||||||
};
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
static u16 pl011_st_offsets[REG_ARRAY_SIZE] = {
|
static u16 pl011_st_offsets[REG_ARRAY_SIZE] = {
|
||||||
[REG_DR] = UART01x_DR,
|
[REG_DR] = UART01x_DR,
|
||||||
@ -2375,12 +2368,14 @@ static int __init pl011_console_match(struct console *co, char *name, int idx,
|
|||||||
resource_size_t addr;
|
resource_size_t addr;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
if (strcmp(name, "qdf2400_e44") == 0) {
|
/*
|
||||||
pr_info_once("UART: Working around QDF2400 SoC erratum 44");
|
* Systems affected by the Qualcomm Technologies QDF2400 E44 erratum
|
||||||
qdf2400_e44_present = true;
|
* have a distinct console name, so make sure we check for that.
|
||||||
} else if (strcmp(name, "pl011") != 0) {
|
* The actual implementation of the erratum occurs in the probe
|
||||||
|
* function.
|
||||||
|
*/
|
||||||
|
if ((strcmp(name, "qdf2400_e44") != 0) && (strcmp(name, "pl011") != 0))
|
||||||
return -ENODEV;
|
return -ENODEV;
|
||||||
}
|
|
||||||
|
|
||||||
if (uart_parse_earlycon(options, &iotype, &addr, &options))
|
if (uart_parse_earlycon(options, &iotype, &addr, &options))
|
||||||
return -ENODEV;
|
return -ENODEV;
|
||||||
@ -2734,11 +2729,17 @@ static int sbsa_uart_probe(struct platform_device *pdev)
|
|||||||
}
|
}
|
||||||
uap->port.irq = ret;
|
uap->port.irq = ret;
|
||||||
|
|
||||||
uap->reg_offset = vendor_sbsa.reg_offset;
|
#ifdef CONFIG_ACPI_SPCR_TABLE
|
||||||
uap->vendor = qdf2400_e44_present ?
|
if (qdf2400_e44_present) {
|
||||||
&vendor_qdt_qdf2400_e44 : &vendor_sbsa;
|
dev_info(&pdev->dev, "working around QDF2400 SoC erratum 44\n");
|
||||||
|
uap->vendor = &vendor_qdt_qdf2400_e44;
|
||||||
|
} else
|
||||||
|
#endif
|
||||||
|
uap->vendor = &vendor_sbsa;
|
||||||
|
|
||||||
|
uap->reg_offset = uap->vendor->reg_offset;
|
||||||
uap->fifosize = 32;
|
uap->fifosize = 32;
|
||||||
uap->port.iotype = vendor_sbsa.access_32b ? UPIO_MEM32 : UPIO_MEM;
|
uap->port.iotype = uap->vendor->access_32b ? UPIO_MEM32 : UPIO_MEM;
|
||||||
uap->port.ops = &sbsa_uart_pops;
|
uap->port.ops = &sbsa_uart_pops;
|
||||||
uap->fixed_baud = baudrate;
|
uap->fixed_baud = baudrate;
|
||||||
|
|
||||||
|
@ -1209,6 +1209,7 @@ static inline bool acpi_has_watchdog(void) { return false; }
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef CONFIG_ACPI_SPCR_TABLE
|
#ifdef CONFIG_ACPI_SPCR_TABLE
|
||||||
|
extern bool qdf2400_e44_present;
|
||||||
int parse_spcr(bool earlycon);
|
int parse_spcr(bool earlycon);
|
||||||
#else
|
#else
|
||||||
static inline int parse_spcr(bool earlycon) { return 0; }
|
static inline int parse_spcr(bool earlycon) { return 0; }
|
||||||
|
Loading…
Reference in New Issue
Block a user