[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [XEN v4 04/11] xen/drivers: ns16550: Use paddr_t for io_base/io_size
io_base and io_size represent physical addresses. So they should use paddr_t (instead of u64). However in future, paddr_t may be defined as u32. So when typecasting values from u64 to paddr_t, one should always check for any possible truncation. If any truncation is discovered, Xen needs to return an appropriate an error message for this. Also moved the definition of PARSE_ERR_RET before its first usage. Signed-off-by: Ayan Kumar Halder <ayan.kumar.halder@xxxxxxx> --- Changes from - v1 - NA v2 - 1. Extracted the patch from "[XEN v2 05/11] xen/arm: Use paddr_t instead of u64 for address/size" into a separate patch of its own. v3 - 1. Reduced the scope of pci_uart_io_base and uart_io_base definitions. 2. Instead of crashing, invoke PARSE_ERR_RET(). 3. Moved PARSE_ERR_RET() so that it is defined before its first use. xen/drivers/char/ns16550.c | 41 ++++++++++++++++++++++++++------------ 1 file changed, 28 insertions(+), 13 deletions(-) diff --git a/xen/drivers/char/ns16550.c b/xen/drivers/char/ns16550.c index 092f6b9c4b..2e8a9cfb24 100644 --- a/xen/drivers/char/ns16550.c +++ b/xen/drivers/char/ns16550.c @@ -42,8 +42,8 @@ static struct ns16550 { int baud, clock_hz, data_bits, parity, stop_bits, fifo_size, irq; - u64 io_base; /* I/O port or memory-mapped I/O address. */ - u64 io_size; + paddr_t io_base; /* I/O port or memory-mapped I/O address. */ + paddr_t io_size; int reg_shift; /* Bits to shift register offset by */ int reg_width; /* Size of access to use, the registers * themselves are still bytes */ @@ -1163,10 +1163,16 @@ static const struct ns16550_config __initconst uart_config[] = }, }; +#define PARSE_ERR_RET(_f, _a...) \ + do { \ + printk( "ERROR: " _f "\n" , ## _a ); \ + return false; \ + } while ( 0 ) + static int __init pci_uart_config(struct ns16550 *uart, bool_t skip_amt, unsigned int idx) { - u64 orig_base = uart->io_base; + paddr_t orig_base = uart->io_base; unsigned int b, d, f, nextf, i; /* NB. Start at bus 1 to avoid AMT: a plug-in card cannot be on bus 0. */ @@ -1235,6 +1241,8 @@ pci_uart_config(struct ns16550 *uart, bool_t skip_amt, unsigned int idx) /* MMIO based */ if ( param->mmio && !(bar & PCI_BASE_ADDRESS_SPACE_IO) ) { + uint64_t pci_uart_io_base; + pci_conf_write32(PCI_SBDF(0, b, d, f), PCI_BASE_ADDRESS_0 + bar_idx*4, ~0u); len = pci_conf_read32(PCI_SBDF(0, b, d, f), @@ -1259,8 +1267,14 @@ pci_uart_config(struct ns16550 *uart, bool_t skip_amt, unsigned int idx) else size = len & PCI_BASE_ADDRESS_MEM_MASK; - uart->io_base = ((u64)bar_64 << 32) | - (bar & PCI_BASE_ADDRESS_MEM_MASK); + pci_uart_io_base = ((u64)bar_64 << 32) | + (bar & PCI_BASE_ADDRESS_MEM_MASK); + + /* Truncation detected while converting to paddr_t */ + if ( (pci_uart_io_base >> (PADDR_BITS - 1)) > 1 ) + PARSE_ERR_RET("Truncation detected for io_base address"); + + uart->io_base = pci_uart_io_base; } /* IO based */ else if ( !param->mmio && (bar & PCI_BASE_ADDRESS_SPACE_IO) ) @@ -1456,13 +1470,6 @@ static enum __init serial_param_type get_token(char *token, char **value) return; \ } while ( 0 ) -#define PARSE_ERR_RET(_f, _a...) \ - do { \ - printk( "ERROR: " _f "\n" , ## _a ); \ - return false; \ - } while ( 0 ) - - static bool __init parse_positional(struct ns16550 *uart, char **str) { int baud; @@ -1532,7 +1539,15 @@ static bool __init parse_positional(struct ns16550 *uart, char **str) else #endif { - uart->io_base = simple_strtoull(conf, &conf, 0); + uint64_t uart_io_base; + + uart_io_base = simple_strtoull(conf, &conf, 0); + + /* Truncation detected while converting to paddr_t */ + if ( (uart_io_base >> (PADDR_BITS - 1)) > 1 ) + PARSE_ERR_RET("Truncation detected for uart_io_base address"); + + uart->io_base = uart_io_base; } } -- 2.17.1
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |