Received: by 10.213.65.68 with SMTP id h4csp451830imn; Sun, 25 Mar 2018 04:04:04 -0700 (PDT) X-Google-Smtp-Source: AG47ELvY56WpIbTbLr49vKujQC7ZdaVFjz121IRlBRw199y1iJSkccANopaROlsh7xEI9hFxvaXM X-Received: by 10.99.124.2 with SMTP id x2mr26007779pgc.262.1521975844183; Sun, 25 Mar 2018 04:04:04 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1521975844; cv=none; d=google.com; s=arc-20160816; b=ugLTObmAcNI0KOACZU+5MxxPW9otvLptouljNZ8dMp1tdQFRXyJp9V4wFss0Sjo1PR S4cLoVX9/vYb2wXYoRsDolzNMtMkAgenakDbnrrOIRurTxiR7R9hWrx91cdvI0I3Z9s1 NfZxFWLYtPBn76bpAkoSVakm3Vsk+wCbrqakL3iqr5tdlVoQQlTGIfEq9g/MsuNHUmCa j0f17zuFKVY0Pxr9FthXhvOH6bAfgRr/LxaLyeTFByfR9KAlGmoY+bxCHghtJcvk5i5s 020OwqgkE37U2JIjGgU+2s8jA0/RYnNZeu08s/R+ji5y4byYS7u5R8DhbQnUlEcaV3Y7 oB2g== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:sender:content-transfer-encoding:mime-version :references:in-reply-to:message-id:date:subject:to:from :dkim-signature:arc-authentication-results; bh=qODRP+4h6+joeezcX+VYrgYl07SgO/lRo+EWm5Gb3IE=; b=HS45/3kUNwqBcBvQciGWHTsdOiywFzUUFbM+ne8+mSw4zJumxrAPJR16Vs5RbwTQnU IDKvfN8d93hb91IahIc0/pSeXSn7Miwe3CnYBeBHgYc83bRxmL68plrXC5sGBs6RtovN fT5cVaz0CEwIeRy3tJ5zd0aNy9VdDz2swh+rq0K+AdhMq2dA7fvgfcU/Urfxyratpx5/ FPdWKefAM3A8ESyj4RrDoE3Ra4TsPq3BIiWmh7DhywKN1fiUOTEEBXizeyU8vfCe80/Z JKEv/5dPD0hs2pl5bk3MDokCeNlqLIwPRqpdCtEI+ZeUmBPdICIM0CSU5CQAq6Cjl+DH NuKg== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@gmail.com header.s=20161025 header.b=s2ze/4Nu; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id o3-v6si12195957pll.280.2018.03.25.04.03.50; Sun, 25 Mar 2018 04:04:04 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; dkim=pass header.i=@gmail.com header.s=20161025 header.b=s2ze/4Nu; spf=pass (google.com: best guess record for domain of linux-kernel-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753337AbeCYLBX (ORCPT + 99 others); Sun, 25 Mar 2018 07:01:23 -0400 Received: from mail-wm0-f65.google.com ([74.125.82.65]:34301 "EHLO mail-wm0-f65.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752628AbeCYLAJ (ORCPT ); Sun, 25 Mar 2018 07:00:09 -0400 Received: by mail-wm0-f65.google.com with SMTP id a20so12758696wmd.1; Sun, 25 Mar 2018 04:00:08 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=qODRP+4h6+joeezcX+VYrgYl07SgO/lRo+EWm5Gb3IE=; b=s2ze/4Nu0U2aK46P4saVyjwJV53IP65mwXJhN+6NcNcvh87bJ+YuYCitOmmwryGPrc kyY+BxRzWhSVgqH4lqVRf22lDiZOIDZ3y3FyE4+VgQRB+0rW5pKVehqKyhxSr/NwtuaE O5qMUhYgv1uF9Y/4Py9O3fQTCQLvHNlANlWcbouqQJqpwGHhsxZndYLW+3RRzPTC6Axw I8mE09MTznpS+h5Ry86x95MqVO85Tkf7gsQKCpxzhFdw6dq/GX9he03bLw2D3qRZJGYj QHgtRHVfzhk1Za3ZRUGOLPC1Sa/h3v2OruVD46p71zf5ooBi5tnVGKJuX/mpJ/TCzNp+ Uggw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=qODRP+4h6+joeezcX+VYrgYl07SgO/lRo+EWm5Gb3IE=; b=bOOEG9NDicSyknnSdMpQfZUxax2aNUGmGm/VpQEvQYSvt/UTtuLPcf1BDZ9lcncmgT bmzJ5aLsvQEjDtuENhupjD2mYXD/KS8sYa2oXwNYfKNchZtBxB5LxiHNymm4fQezkvPp GmyARh338YJlfFR6QU873hWAhZRY88UzDJZrDzQwA4Aqq1ACM9kjW0X/kQm0B1V+XYcm SIPLW/T58A6xQ+fH5w+M+u2T8AUsxB3Q2ply8PhjjM8M7Wq8r4CeaoKCD30g2W6IA73c chia2v6FNBNZx0K5+8hhk22fedarkZnB/vJecpUvyvqH5kAlesFzkMEQhVSG1PQrZqEz 4ulA== X-Gm-Message-State: AElRT7HXrcrKPbKhpMQOt6m7QfXEQXn0xNC+n/njPitK4a7saTqrj0Z7 5Ni0e8pazmlleOwOgekfIJU= X-Received: by 10.28.48.149 with SMTP id w143mr13722619wmw.88.1521975608142; Sun, 25 Mar 2018 04:00:08 -0700 (PDT) Received: from baker.fritz.box ([2a02:908:1257:4460:80f2:8bcd:4355:2edc]) by smtp.gmail.com with ESMTPSA id z3sm20492230wme.3.2018.03.25.04.00.07 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Sun, 25 Mar 2018 04:00:07 -0700 (PDT) From: "=?UTF-8?q?Christian=20K=C3=B6nig?=" X-Google-Original-From: =?UTF-8?q?Christian=20K=C3=B6nig?= To: linaro-mm-sig@lists.linaro.org, linux-media@vger.kernel.org, dri-devel@lists.freedesktop.org, amd-gfx@lists.freedesktop.org, linux-kernel@vger.kernel.org Subject: [PATCH 8/8] drm/amdgpu: add support for exporting VRAM using DMA-buf Date: Sun, 25 Mar 2018 13:00:00 +0200 Message-Id: <20180325110000.2238-8-christian.koenig@amd.com> X-Mailer: git-send-email 2.14.1 In-Reply-To: <20180325110000.2238-1-christian.koenig@amd.com> References: <20180325110000.2238-1-christian.koenig@amd.com> MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Sender: linux-kernel-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org We should be able to do this now after checking all the prerequisites. Signed-off-by: Christian König --- drivers/gpu/drm/amd/amdgpu/amdgpu_prime.c | 44 +++++++++++--- drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.h | 9 +++ drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c | 91 ++++++++++++++++++++++++++++ 3 files changed, 135 insertions(+), 9 deletions(-) diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_prime.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_prime.c index 133596df0775..86d983a0678b 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_prime.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_prime.c @@ -197,23 +197,44 @@ amdgpu_gem_map_dma_buf(struct dma_buf_attachment *attach, } else { /* move buffer into GTT */ struct ttm_operation_ctx ctx = { false, false }; + unsigned domains = AMDGPU_GEM_DOMAIN_GTT; - amdgpu_ttm_placement_from_domain(bo, AMDGPU_GEM_DOMAIN_GTT); + if (bo->preferred_domains & AMDGPU_GEM_DOMAIN_VRAM && + attach->peer2peer) { + bo->flags |= AMDGPU_GEM_CREATE_CPU_ACCESS_REQUIRED; + domains |= AMDGPU_GEM_DOMAIN_VRAM; + } + amdgpu_ttm_placement_from_domain(bo, domains); r = ttm_bo_validate(&bo->tbo, &bo->placement, &ctx); if (r) goto error_unreserve; } - sgt = drm_prime_pages_to_sg(bo->tbo.ttm->pages, bo->tbo.num_pages); - if (IS_ERR(sgt)) { - r = PTR_ERR(sgt); + switch (bo->tbo.mem.mem_type) { + case TTM_PL_TT: + sgt = drm_prime_pages_to_sg(bo->tbo.ttm->pages, + bo->tbo.num_pages); + if (IS_ERR(sgt)) { + r = PTR_ERR(sgt); + goto error_unreserve; + } + + if (!dma_map_sg_attrs(attach->dev, sgt->sgl, sgt->nents, dir, + DMA_ATTR_SKIP_CPU_SYNC)) + goto error_free; + break; + + case TTM_PL_VRAM: + r = amdgpu_vram_mgr_alloc_sgt(adev, &bo->tbo.mem, attach->dev, + dir, &sgt); + if (r) + goto error_unreserve; + break; + default: + r = -EINVAL; goto error_unreserve; } - if (!dma_map_sg_attrs(attach->dev, sgt->sgl, sgt->nents, dir, - DMA_ATTR_SKIP_CPU_SYNC)) - goto error_free; - if (attach->dev->driver != adev->dev->driver) bo->prime_shared_count++; @@ -254,10 +275,15 @@ static void amdgpu_gem_unmap_dma_buf(struct dma_buf_attachment *attach, if (!attach->invalidate) amdgpu_bo_unreserve(bo); - if (sgt) { + if (!sgt) + return; + + if (sgt->sgl->page_link) { dma_unmap_sg(attach->dev, sgt->sgl, sgt->nents, dir); sg_free_table(sgt); kfree(sgt); + } else { + amdgpu_vram_mgr_free_sgt(adev, attach->dev, dir, sgt); } } diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.h b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.h index 6ea7de863041..b483900abed2 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.h +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.h @@ -73,6 +73,15 @@ bool amdgpu_gtt_mgr_has_gart_addr(struct ttm_mem_reg *mem); uint64_t amdgpu_gtt_mgr_usage(struct ttm_mem_type_manager *man); int amdgpu_gtt_mgr_recover(struct ttm_mem_type_manager *man); +int amdgpu_vram_mgr_alloc_sgt(struct amdgpu_device *adev, + struct ttm_mem_reg *mem, + struct device *dev, + enum dma_data_direction dir, + struct sg_table **sgt); +void amdgpu_vram_mgr_free_sgt(struct amdgpu_device *adev, + struct device *dev, + enum dma_data_direction dir, + struct sg_table *sgt); uint64_t amdgpu_vram_mgr_usage(struct ttm_mem_type_manager *man); uint64_t amdgpu_vram_mgr_vis_usage(struct ttm_mem_type_manager *man); diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c index 9aca653bec07..eb8f75525a81 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_vram_mgr.c @@ -233,6 +233,97 @@ static void amdgpu_vram_mgr_del(struct ttm_mem_type_manager *man, mem->mm_node = NULL; } +/** + * amdgpu_vram_mgr_alloc_sgt - allocate and fill a sg table + * + * @adev: amdgpu device pointer + * @mem: TTM memory object + * @dev: the other device + * @dir: dma direction + * @sgt: resulting sg table + * + * Allocate and fill a sg table from a VRAM allocation. + */ +int amdgpu_vram_mgr_alloc_sgt(struct amdgpu_device *adev, + struct ttm_mem_reg *mem, + struct device *dev, + enum dma_data_direction dir, + struct sg_table **sgt) +{ + struct drm_mm_node *node = mem->mm_node; + struct scatterlist *sg; + int num_entries; + int i, r; + + *sgt = kmalloc(sizeof(*sgt), GFP_KERNEL); + if (!*sgt) + return -ENOMEM; + + num_entries = DIV_ROUND_UP(mem->num_pages, node->size); + r = sg_alloc_table(*sgt, num_entries, GFP_KERNEL); + if (r) + goto error_free; + + for_each_sg((*sgt)->sgl, sg, num_entries, i) + sg->length = 0; + + for_each_sg((*sgt)->sgl, sg, num_entries, i) { + phys_addr_t phys = (node->start << PAGE_SHIFT) + + adev->gmc.aper_base; + size_t size = node->size << PAGE_SHIFT; + dma_addr_t addr; + + ++node; + addr = dma_map_resource(dev, phys, size, dir, + DMA_ATTR_SKIP_CPU_SYNC); + r = dma_mapping_error(dev, addr); + if (r) + goto error_unmap; + + sg_set_dma_addr(sg, addr, size, 0); + } + return 0; + +error_unmap: + for_each_sg((*sgt)->sgl, sg, num_entries, i) { + if (!sg->length) + continue; + + dma_unmap_resource(dev, sg->dma_address, + sg->length, dir, + DMA_ATTR_SKIP_CPU_SYNC); + } + sg_free_table(*sgt); + +error_free: + kfree(*sgt); + return r; +} + +/** + * amdgpu_vram_mgr_alloc_sgt - allocate and fill a sg table + * + * @adev: amdgpu device pointer + * @sgt: sg table to free + * + * Free a previously allocate sg table. + */ +void amdgpu_vram_mgr_free_sgt(struct amdgpu_device *adev, + struct device *dev, + enum dma_data_direction dir, + struct sg_table *sgt) +{ + struct scatterlist *sg; + int i; + + for_each_sg(sgt->sgl, sg, sgt->nents, i) + dma_unmap_resource(dev, sg->dma_address, + sg->length, dir, + DMA_ATTR_SKIP_CPU_SYNC); + sg_free_table(sgt); + kfree(sgt); +} + /** * amdgpu_vram_mgr_usage - how many bytes are used in this domain * -- 2.14.1