From patchwork Mon Oct 15 14:03:52 2012 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Marek Szyprowski X-Patchwork-Id: 12235 Return-Path: X-Original-To: patchwork@peony.canonical.com Delivered-To: patchwork@peony.canonical.com Received: from fiordland.canonical.com (fiordland.canonical.com [91.189.94.145]) by peony.canonical.com (Postfix) with ESMTP id 698A6241A4 for ; Mon, 15 Oct 2012 14:05:21 +0000 (UTC) Received: from mail-ie0-f180.google.com (mail-ie0-f180.google.com [209.85.223.180]) by fiordland.canonical.com (Postfix) with ESMTP id E171AA18F2A for ; Mon, 15 Oct 2012 14:05:20 +0000 (UTC) Received: by mail-ie0-f180.google.com with SMTP id e10so7635209iej.11 for ; Mon, 15 Oct 2012 07:05:20 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20120113; h=x-forwarded-to:x-forwarded-for:delivered-to:received-spf:x-auditid :from:to:date:message-id:x-mailer:in-reply-to:references :x-brightmail-tracker:cc:subject:x-beenthere:x-mailman-version :precedence:list-id:list-unsubscribe:list-archive:list-post :list-help:list-subscribe:mime-version:content-type :content-transfer-encoding:sender:errors-to:x-gm-message-state; bh=QZb5+UPA7Mt4bMEQvwX93qo4jdJxI0JrdJ0cBpISwfg=; b=IW9xGGE3ngLkNTAZ8iOe4SCKtUgzy28hnjQUGKCVj+d5N4qllmPFOWhJrsMqNVMJJR j63iIK4QdzmLwepqcDX1ab8Nxm35GSDbMfyhcYhk8uynSE96cSjF+nxOiyS/3hNvPmNW dJTFjUNRfKMgWWd5rL8ipmMX6Y8IkiE0d1WQ8NZp9maWFKi0Yic2zlUIHIK14sbftV2W MniFiShYfX95Mw7L4uOuYaidIq58gcjz1JRUTQhymEb/slF+qsj0XAWya1o/1WTq4pMv sXz6e2/AVeb22A/42Nk251/CJbWv7nV/QYCItF5Pw36H6PwwmGmERy56BLFRHtgbhpmV AtEQ== Received: by 10.50.46.226 with SMTP id y2mr8579917igm.62.1350309920361; Mon, 15 Oct 2012 07:05:20 -0700 (PDT) X-Forwarded-To: linaro-patchwork@canonical.com X-Forwarded-For: patch@linaro.org linaro-patchwork@canonical.com Delivered-To: patches@linaro.org Received: by 10.50.67.148 with SMTP id n20csp578814igt; Mon, 15 Oct 2012 07:05:19 -0700 (PDT) Received: by 10.204.10.74 with SMTP id o10mr3246458bko.9.1350309918562; Mon, 15 Oct 2012 07:05:18 -0700 (PDT) Received: from mombin.canonical.com (mombin.canonical.com. [91.189.95.16]) by mx.google.com with ESMTP id iv7si24896275bkc.11.2012.10.15.07.05.15; Mon, 15 Oct 2012 07:05:18 -0700 (PDT) Received-SPF: neutral (google.com: 91.189.95.16 is neither permitted nor denied by best guess record for domain of linaro-mm-sig-bounces@lists.linaro.org) client-ip=91.189.95.16; Authentication-Results: mx.google.com; spf=neutral (google.com: 91.189.95.16 is neither permitted nor denied by best guess record for domain of linaro-mm-sig-bounces@lists.linaro.org) smtp.mail=linaro-mm-sig-bounces@lists.linaro.org Received: from localhost ([127.0.0.1] helo=mombin.canonical.com) by mombin.canonical.com with esmtp (Exim 4.71) (envelope-from ) id 1TNlIA-0001It-Lz; Mon, 15 Oct 2012 14:05:14 +0000 Received: from mailout4.samsung.com ([203.254.224.34]) by mombin.canonical.com with esmtp (Exim 4.71) (envelope-from ) id 1TNlI9-0001In-6a for linaro-mm-sig@lists.linaro.org; Mon, 15 Oct 2012 14:05:13 +0000 Received: from epcpsbgm1.samsung.com (epcpsbgm1 [203.254.230.26]) by mailout4.samsung.com (Oracle Communications Messaging Server 7u4-24.01(7.0.4.24.0) 64bit (built Nov 17 2011)) with ESMTP id <0MBX005C6TRGFXA0@mailout4.samsung.com> for linaro-mm-sig@lists.linaro.org; Mon, 15 Oct 2012 23:04:33 +0900 (KST) X-AuditID: cbfee61a-b7f976d000001eb9-a7-507c17f1a25c Received: from epmmp1.local.host ( [203.254.227.16]) by epcpsbgm1.samsung.com (EPCPMTA) with SMTP id A4.07.07865.1F71C705; Mon, 15 Oct 2012 23:04:33 +0900 (KST) Received: from localhost.localdomain ([106.116.147.30]) by mmp1.samsung.com (Oracle Communications Messaging Server 7u4-24.01 (7.0.4.24.0) 64bit (built Nov 17 2011)) with ESMTPA id <0MBX00JMCTQOCL70@mmp1.samsung.com> for linaro-mm-sig@lists.linaro.org; Mon, 15 Oct 2012 23:04:33 +0900 (KST) From: Marek Szyprowski To: linux-arm-kernel@lists.infradead.org, linaro-mm-sig@lists.linaro.org, linux-mm@kvack.org, linux-kernel@vger.kernel.org Date: Mon, 15 Oct 2012 16:03:52 +0200 Message-id: <1350309832-18461-3-git-send-email-m.szyprowski@samsung.com> X-Mailer: git-send-email 1.7.9.5 In-reply-to: <1350309832-18461-1-git-send-email-m.szyprowski@samsung.com> References: <1350309832-18461-1-git-send-email-m.szyprowski@samsung.com> X-Brightmail-Tracker: H4sIAAAAAAAAA+NgFrrHJMWRmVeSWpSXmKPExsVy+t9jAd2P4jUBBtfuS1l8ufKQyYHR4/a/ x8wBjFFcNimpOZllqUX6dglcGT9/fmYs+CBRMX+9XAPjNJEuRk4OCQETid+njrJC2GISF+6t Z+ti5OIQEljEKNH0eicLSEJIYBWTxJoGYxCbTcBQouttF1ARB4eIQI3EvBmMIPXMAq8ZJWbt 3AwWFxaIktj3NROknEVAVeLFnV8sIGFeAQ+JlxvBKiQEFCTmTLIBqeAU8JR4+nAuI8QiD4l5 jbuZJzDyLmBkWMUomlqQXFCclJ5rqFecmFtcmpeul5yfu4kR7OtnUjsYVzZYHGIU4GBU4uH9 6VUdIMSaWFZcmXuIUYKDWUmE99kjoBBvSmJlVWpRfnxRaU5q8SFGaQ4WJXHeZo+UACGB9MSS 1OzU1ILUIpgsEwenVAOjf3NJ5ByTP/p7vyhdKjSb+LF568egG57WR7d+8t/AuJgh+9J7y4t5 q91Fl25vM0vcZzjxUmqLo1j/v+2qjyU6lgbt2aOwff/nD+2d78QVjk0RTL3BL7ffsOdoyhIJ +/DMvfqRSzPMt5rLuqisimTxUG1ut777Y1/5Kq6/jDK7L+26LeDz9+FFJZbijERDLeai4kQA /E/1C/EBAAA= Cc: Russell King - ARM Linux , Arnd Bergmann , Inki Dae , Kyungmin Park Subject: [Linaro-mm-sig] [RFC 2/2] ARM: dma-mapping: add support for DMA_ATTR_FORCE_CONTIGUOUS attribute X-BeenThere: linaro-mm-sig@lists.linaro.org X-Mailman-Version: 2.1.13 Precedence: list List-Id: "Unified memory management interest group." List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Sender: linaro-mm-sig-bounces@lists.linaro.org Errors-To: linaro-mm-sig-bounces@lists.linaro.org X-Gm-Message-State: ALoCoQnlEXElUwu/X2raTQRyElifhCjcDagV/J6/dSLMdXpERbSPwdkYPKwUSyXKDi1FHrVP/unG This patch adds support for DMA_ATTR_FORCE_CONTIGUOUS attribute for dma_alloc_attrs() in IOMMU-aware implementation. For allocating physically contiguous buffers Contiguous Memory Allocator is used. Signed-off-by: Marek Szyprowski --- arch/arm/mm/dma-mapping.c | 41 +++++++++++++++++++++++++++++++++-------- 1 file changed, 33 insertions(+), 8 deletions(-) diff --git a/arch/arm/mm/dma-mapping.c b/arch/arm/mm/dma-mapping.c index 477a2d2..583a302 100644 --- a/arch/arm/mm/dma-mapping.c +++ b/arch/arm/mm/dma-mapping.c @@ -1036,7 +1036,8 @@ static inline void __free_iova(struct dma_iommu_mapping *mapping, spin_unlock_irqrestore(&mapping->lock, flags); } -static struct page **__iommu_alloc_buffer(struct device *dev, size_t size, gfp_t gfp) +static struct page **__iommu_alloc_buffer(struct device *dev, size_t size, + gfp_t gfp, struct dma_attrs *attrs) { struct page **pages; int count = size >> PAGE_SHIFT; @@ -1050,6 +1051,23 @@ static struct page **__iommu_alloc_buffer(struct device *dev, size_t size, gfp_t if (!pages) return NULL; + if (dma_get_attr(DMA_ATTR_FORCE_CONTIGUOUS, attrs)) + { + unsigned long order = get_order(size); + struct page *page; + + page = dma_alloc_from_contiguous(dev, count, order); + if (!page) + goto error; + + __dma_clear_buffer(page, size); + + for (i = 0; i < count; i++) + pages[i] = page + i; + + return pages; + } + while (count) { int j, order = __fls(count); @@ -1083,14 +1101,21 @@ error: return NULL; } -static int __iommu_free_buffer(struct device *dev, struct page **pages, size_t size) +static int __iommu_free_buffer(struct device *dev, struct page **pages, + size_t size, struct dma_attrs *attrs) { int count = size >> PAGE_SHIFT; int array_size = count * sizeof(struct page *); int i; - for (i = 0; i < count; i++) - if (pages[i]) - __free_pages(pages[i], 0); + + if (dma_get_attr(DMA_ATTR_FORCE_CONTIGUOUS, attrs)) { + dma_release_from_contiguous(dev, pages[0], count); + } else { + for (i = 0; i < count; i++) + if (pages[i]) + __free_pages(pages[i], 0); + } + if (array_size <= PAGE_SIZE) kfree(pages); else @@ -1252,7 +1277,7 @@ static void *arm_iommu_alloc_attrs(struct device *dev, size_t size, if (gfp & GFP_ATOMIC) return __iommu_alloc_atomic(dev, size, handle); - pages = __iommu_alloc_buffer(dev, size, gfp); + pages = __iommu_alloc_buffer(dev, size, gfp, attrs); if (!pages) return NULL; @@ -1273,7 +1298,7 @@ static void *arm_iommu_alloc_attrs(struct device *dev, size_t size, err_mapping: __iommu_remove_mapping(dev, *handle, size); err_buffer: - __iommu_free_buffer(dev, pages, size); + __iommu_free_buffer(dev, pages, size, attrs); return NULL; } @@ -1329,7 +1354,7 @@ void arm_iommu_free_attrs(struct device *dev, size_t size, void *cpu_addr, } __iommu_remove_mapping(dev, handle, size); - __iommu_free_buffer(dev, pages, size); + __iommu_free_buffer(dev, pages, size, attrs); } static int arm_iommu_get_sgtable(struct device *dev, struct sg_table *sgt,