From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-9.6 required=3.0 tests=DKIM_INVALID,DKIM_SIGNED, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_PATCH,MAILING_LIST_MULTI,SIGNED_OFF_BY, SPF_HELO_NONE,SPF_PASS,URIBL_BLOCKED,USER_AGENT_GIT autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 4D561C2BBC7 for ; Tue, 14 Apr 2020 13:14:44 +0000 (UTC) Received: from kanga.kvack.org (kanga.kvack.org [205.233.56.17]) by mail.kernel.org (Postfix) with ESMTP id E89CA2063A for ; Tue, 14 Apr 2020 13:14:43 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=fail reason="signature verification failed" (2048-bit key) header.d=infradead.org header.i=@infradead.org header.b="TknBV49y" DMARC-Filter: OpenDMARC Filter v1.3.2 mail.kernel.org E89CA2063A Authentication-Results: mail.kernel.org; dmarc=none (p=none dis=none) header.from=lst.de Authentication-Results: mail.kernel.org; spf=pass smtp.mailfrom=owner-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix) id 9B2CB8E000C; Tue, 14 Apr 2020 09:14:43 -0400 (EDT) Received: by kanga.kvack.org (Postfix, from userid 40) id 962E78E0001; Tue, 14 Apr 2020 09:14:43 -0400 (EDT) X-Delivered-To: int-list-linux-mm@kvack.org Received: by kanga.kvack.org (Postfix, from userid 63042) id 879728E000C; Tue, 14 Apr 2020 09:14:43 -0400 (EDT) X-Delivered-To: linux-mm@kvack.org Received: from forelay.hostedemail.com (smtprelay0001.hostedemail.com [216.40.44.1]) by kanga.kvack.org (Postfix) with ESMTP id 711D78E0001 for ; Tue, 14 Apr 2020 09:14:43 -0400 (EDT) Received: from smtpin19.hostedemail.com (10.5.19.251.rfc1918.com [10.5.19.251]) by forelay01.hostedemail.com (Postfix) with ESMTP id 2F261180AD802 for ; Tue, 14 Apr 2020 13:14:43 +0000 (UTC) X-FDA: 76706505246.19.swim85_c075388ba644 X-HE-Tag: swim85_c075388ba644 X-Filterd-Recvd-Size: 10063 Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) by imf34.hostedemail.com (Postfix) with ESMTP for ; Tue, 14 Apr 2020 13:14:42 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=infradead.org; s=bombadil.20170209; h=Content-Transfer-Encoding: MIME-Version:References:In-Reply-To:Message-Id:Date:Subject:Cc:To:From:Sender :Reply-To:Content-Type:Content-ID:Content-Description; bh=El3K7mGKX6B9o1n3n8/uSzRNv+M9pQhI906vP4nRJj0=; b=TknBV49y24E5J7xFzadKo5kjo5 H8QYGdmubIg2vBwe4mYro12NwuYp1KZTwMSErFsx1s9TwfxWwFDRWSyYmrajo1Y/8Dd7olymaZiKB OUeMc4IYdXC9zX9BTcv/N9q3I31wh3TlIc98iy/C6FIEx45kob0iaVmoDToA6yCmEag/F5zzdsuW3 ZFo+awA/3wTJWtGY2E0rKHXogHWWApzIqlcsjjb6Awp4NUqZi+Hx1hc/D0P1cAD7SDlvPd8K2icXI wl+6z7yHRJpbpDdPSvQSP4Id+GQVwc5XlDPmgap8nH2NdGYXZ9fDSfOeggdXxpsBX7IxfyPfaRIBb KZM3myUg==; Received: from [2001:4bb8:180:384b:c70:4a89:bc61:2] (helo=localhost) by bombadil.infradead.org with esmtpsa (Exim 4.92.3 #3 (Red Hat Linux)) id 1jOLOG-0006SH-MB; Tue, 14 Apr 2020 13:14:13 +0000 From: Christoph Hellwig To: Andrew Morton , "K. Y. Srinivasan" , Haiyang Zhang , Stephen Hemminger , Wei Liu , x86@kernel.org, David Airlie , Daniel Vetter , Laura Abbott , Sumit Semwal , Sakari Ailus , Minchan Kim , Nitin Gupta Cc: Robin Murphy , Christophe Leroy , Peter Zijlstra , linuxppc-dev@lists.ozlabs.org, linux-hyperv@vger.kernel.org, dri-devel@lists.freedesktop.org, linaro-mm-sig@lists.linaro.org, linux-arch@vger.kernel.org, linux-mm@kvack.org, iommu@lists.linux-foundation.org, linux-arm-kernel@lists.infradead.org, linux-s390@vger.kernel.org, bpf@vger.kernel.org, linux-kernel@vger.kernel.org Subject: [PATCH 06/29] powerpc: add an ioremap_phb helper Date: Tue, 14 Apr 2020 15:13:25 +0200 Message-Id: <20200414131348.444715-7-hch@lst.de> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20200414131348.444715-1-hch@lst.de> References: <20200414131348.444715-1-hch@lst.de> MIME-Version: 1.0 X-SRS-Rewrite: SMTP reverse-path rewritten from by bombadil.infradead.org. See http://www.infradead.org/rpr.html Content-Transfer-Encoding: quoted-printable X-Bogosity: Ham, tests=bogofilter, spamicity=0.000000, version=1.2.4 Sender: owner-linux-mm@kvack.org Precedence: bulk X-Loop: owner-majordomo@kvack.org List-ID: Factor code shared between pci_64 and electra_cf into a ioremap_pbh helper that follows the normal ioremap semantics, and returns a useful __iomem pointer. Note that it opencodes __ioremap_at as we know from the callers the slab is available. Switch pci_64 to also store the result as __iomem pointer, and unmap the result using iounmap instead of force casting and using vmalloc APIs. Signed-off-by: Christoph Hellwig Acked-by: Peter Zijlstra (Intel) --- arch/powerpc/include/asm/io.h | 2 + arch/powerpc/include/asm/pci-bridge.h | 2 +- arch/powerpc/kernel/pci_64.c | 53 ++++++++++++++++++--------- drivers/pcmcia/electra_cf.c | 45 ++++++++--------------- 4 files changed, 54 insertions(+), 48 deletions(-) diff --git a/arch/powerpc/include/asm/io.h b/arch/powerpc/include/asm/io.= h index 635969b5b58e..91320985d33f 100644 --- a/arch/powerpc/include/asm/io.h +++ b/arch/powerpc/include/asm/io.h @@ -719,6 +719,8 @@ void __iomem *ioremap_coherent(phys_addr_t address, u= nsigned long size); =20 extern void iounmap(volatile void __iomem *addr); =20 +void __iomem *ioremap_phb(phys_addr_t paddr, unsigned long size); + int early_ioremap_range(unsigned long ea, phys_addr_t pa, unsigned long size, pgprot_t prot); void __iomem *do_ioremap(phys_addr_t pa, phys_addr_t offset, unsigned lo= ng size, diff --git a/arch/powerpc/include/asm/pci-bridge.h b/arch/powerpc/include= /asm/pci-bridge.h index 69f4cb3b7c56..b92e81b256e5 100644 --- a/arch/powerpc/include/asm/pci-bridge.h +++ b/arch/powerpc/include/asm/pci-bridge.h @@ -66,7 +66,7 @@ struct pci_controller { =20 void __iomem *io_base_virt; #ifdef CONFIG_PPC64 - void *io_base_alloc; + void __iomem *io_base_alloc; #endif resource_size_t io_base_phys; resource_size_t pci_io_size; diff --git a/arch/powerpc/kernel/pci_64.c b/arch/powerpc/kernel/pci_64.c index f83d1f69b1dd..2a976314f169 100644 --- a/arch/powerpc/kernel/pci_64.c +++ b/arch/powerpc/kernel/pci_64.c @@ -109,23 +109,46 @@ int pcibios_unmap_io_space(struct pci_bus *bus) /* Get the host bridge */ hose =3D pci_bus_to_host(bus); =20 - /* Check if we have IOs allocated */ - if (hose->io_base_alloc =3D=3D NULL) - return 0; - pr_debug("IO unmapping for PHB %pOF\n", hose->dn); pr_debug(" alloc=3D0x%p\n", hose->io_base_alloc); =20 - /* This is a PHB, we fully unmap the IO area */ - vunmap(hose->io_base_alloc); - + iounmap(hose->io_base_alloc); return 0; } EXPORT_SYMBOL_GPL(pcibios_unmap_io_space); =20 -static int pcibios_map_phb_io_space(struct pci_controller *hose) +void __iomem *ioremap_phb(phys_addr_t paddr, unsigned long size) { struct vm_struct *area; + unsigned long addr; + + WARN_ON_ONCE(paddr & ~PAGE_MASK); + WARN_ON_ONCE(size & ~PAGE_MASK); + + /* + * Let's allocate some IO space for that guy. We don't pass VM_IOREMAP + * because we don't care about alignment tricks that the core does in + * that case. Maybe we should due to stupid card with incomplete + * address decoding but I'd rather not deal with those outside of the + * reserved 64K legacy region. + */ + area =3D __get_vm_area(size, 0, PHB_IO_BASE, PHB_IO_END); + if (!area) + return NULL; + + addr =3D (unsigned long)area->addr; + if (ioremap_page_range(addr, addr + size, paddr, + pgprot_noncached(PAGE_KERNEL))) { + unmap_kernel_range(addr, size); + return NULL; + } + + return (void __iomem *)addr; +} +EXPORT_SYMBOL_GPL(ioremap_phb); + +static int pcibios_map_phb_io_space(struct pci_controller *hose) +{ unsigned long phys_page; unsigned long size_page; unsigned long io_virt_offset; @@ -146,12 +169,11 @@ static int pcibios_map_phb_io_space(struct pci_cont= roller *hose) * with incomplete address decoding but I'd rather not deal with * those outside of the reserved 64K legacy region. */ - area =3D __get_vm_area(size_page, 0, PHB_IO_BASE, PHB_IO_END); - if (area =3D=3D NULL) + hose->io_base_alloc =3D ioremap_phb(phys_page, size_page); + if (!hose->io_base_alloc) return -ENOMEM; - hose->io_base_alloc =3D area->addr; - hose->io_base_virt =3D (void __iomem *)(area->addr + - hose->io_base_phys - phys_page); + hose->io_base_virt =3D hose->io_base_alloc + + hose->io_base_phys - phys_page; =20 pr_debug("IO mapping for PHB %pOF\n", hose->dn); pr_debug(" phys=3D0x%016llx, virt=3D0x%p (alloc=3D0x%p)\n", @@ -159,11 +181,6 @@ static int pcibios_map_phb_io_space(struct pci_contr= oller *hose) pr_debug(" size=3D0x%016llx (alloc=3D0x%016lx)\n", hose->pci_io_size, size_page); =20 - /* Establish the mapping */ - if (__ioremap_at(phys_page, area->addr, size_page, - pgprot_noncached(PAGE_KERNEL)) =3D=3D NULL) - return -ENOMEM; - /* Fixup hose IO resource */ io_virt_offset =3D pcibios_io_space_offset(hose); hose->io_resource.start +=3D io_virt_offset; diff --git a/drivers/pcmcia/electra_cf.c b/drivers/pcmcia/electra_cf.c index f2741c04289d..35158cfd9c1a 100644 --- a/drivers/pcmcia/electra_cf.c +++ b/drivers/pcmcia/electra_cf.c @@ -178,10 +178,9 @@ static int electra_cf_probe(struct platform_device *= ofdev) struct device_node *np =3D ofdev->dev.of_node; struct electra_cf_socket *cf; struct resource mem, io; - int status; + int status =3D -ENOMEM; const unsigned int *prop; int err; - struct vm_struct *area; =20 err =3D of_address_to_resource(np, 0, &mem); if (err) @@ -202,30 +201,19 @@ static int electra_cf_probe(struct platform_device = *ofdev) cf->mem_phys =3D mem.start; cf->mem_size =3D PAGE_ALIGN(resource_size(&mem)); cf->mem_base =3D ioremap(cf->mem_phys, cf->mem_size); + if (!cf->mem_base) + goto out_free_cf; cf->io_size =3D PAGE_ALIGN(resource_size(&io)); - - area =3D __get_vm_area(cf->io_size, 0, PHB_IO_BASE, PHB_IO_END); - if (area =3D=3D NULL) { - status =3D -ENOMEM; - goto fail1; - } - - cf->io_virt =3D (void __iomem *)(area->addr); + cf->io_virt =3D ioremap_phb(io.start, cf->io_size); + if (!cf->io_virt) + goto out_unmap_mem; =20 cf->gpio_base =3D ioremap(0xfc103000, 0x1000); + if (!cf->gpio_base) + goto out_unmap_virt; dev_set_drvdata(device, cf); =20 - if (!cf->mem_base || !cf->io_virt || !cf->gpio_base || - (__ioremap_at(io.start, cf->io_virt, cf->io_size, - pgprot_noncached(PAGE_KERNEL)) =3D=3D NULL)) { - dev_err(device, "can't ioremap ranges\n"); - status =3D -ENOMEM; - goto fail1; - } - - cf->io_base =3D (unsigned long)cf->io_virt - VMALLOC_END; - cf->iomem.start =3D (unsigned long)cf->mem_base; cf->iomem.end =3D (unsigned long)cf->mem_base + (mem.end - mem.start); cf->iomem.flags =3D IORESOURCE_MEM; @@ -305,14 +293,13 @@ static int electra_cf_probe(struct platform_device = *ofdev) if (cf->irq) free_irq(cf->irq, cf); =20 - if (cf->io_virt) - __iounmap_at(cf->io_virt, cf->io_size); - if (cf->mem_base) - iounmap(cf->mem_base); - if (cf->gpio_base) - iounmap(cf->gpio_base); - if (area) - device_init_wakeup(&ofdev->dev, 0); + iounmap(cf->gpio_base); +out_unmap_virt: + device_init_wakeup(&ofdev->dev, 0); + iounmap(cf->io_virt); +out_unmap_mem: + iounmap(cf->mem_base); +out_free_cf: kfree(cf); return status; =20 @@ -330,7 +317,7 @@ static int electra_cf_remove(struct platform_device *= ofdev) free_irq(cf->irq, cf); del_timer_sync(&cf->timer); =20 - __iounmap_at(cf->io_virt, cf->io_size); + iounmap(cf->io_virt); iounmap(cf->mem_base); iounmap(cf->gpio_base); release_mem_region(cf->mem_phys, cf->mem_size); --=20 2.25.1