diff options
Diffstat (limited to 'drivers/acpi')
-rw-r--r-- | drivers/acpi/osl.c | 25 |
1 files changed, 18 insertions, 7 deletions
diff --git a/drivers/acpi/osl.c b/drivers/acpi/osl.c index b0931818cf98..c90c76aa7f8b 100644 --- a/drivers/acpi/osl.c +++ b/drivers/acpi/osl.c @@ -636,17 +636,21 @@ EXPORT_SYMBOL(acpi_os_write_port); acpi_status acpi_os_read_memory(acpi_physical_address phys_addr, u32 * value, u32 width) { - u32 dummy; void __iomem *virt_addr; - int size = width / 8, unmap = 0; + unsigned int size = width / 8; + bool unmap = false; + u32 dummy; rcu_read_lock(); virt_addr = acpi_map_vaddr_lookup(phys_addr, size); - rcu_read_unlock(); if (!virt_addr) { + rcu_read_unlock(); virt_addr = acpi_os_ioremap(phys_addr, size); - unmap = 1; + if (!virt_addr) + return AE_BAD_ADDRESS; + unmap = true; } + if (!value) value = &dummy; @@ -666,6 +670,8 @@ acpi_os_read_memory(acpi_physical_address phys_addr, u32 * value, u32 width) if (unmap) iounmap(virt_addr); + else + rcu_read_unlock(); return AE_OK; } @@ -674,14 +680,17 @@ acpi_status acpi_os_write_memory(acpi_physical_address phys_addr, u32 value, u32 width) { void __iomem *virt_addr; - int size = width / 8, unmap = 0; + unsigned int size = width / 8; + bool unmap = false; rcu_read_lock(); virt_addr = acpi_map_vaddr_lookup(phys_addr, size); - rcu_read_unlock(); if (!virt_addr) { + rcu_read_unlock(); virt_addr = acpi_os_ioremap(phys_addr, size); - unmap = 1; + if (!virt_addr) + return AE_BAD_ADDRESS; + unmap = true; } switch (width) { @@ -700,6 +709,8 @@ acpi_os_write_memory(acpi_physical_address phys_addr, u32 value, u32 width) if (unmap) iounmap(virt_addr); + else + rcu_read_unlock(); return AE_OK; } |