From patchwork Wed Jul 17 18:33:50 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Rob Herring X-Patchwork-Id: 169157 Delivered-To: patch@linaro.org Received: by 2002:a92:4782:0:0:0:0:0 with SMTP id e2csp1320513ilk; Wed, 17 Jul 2019 11:34:08 -0700 (PDT) X-Google-Smtp-Source: APXvYqzsSznVsJUCow9tLve43woW/fqyka6qc60CCg2fw9uSUU5oC9tFAY6EnH/JaWc8ay1Wr0dp X-Received: by 2002:a17:902:f204:: with SMTP id gn4mr45406973plb.3.1563388447984; Wed, 17 Jul 2019 11:34:07 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1563388447; cv=none; d=google.com; s=arc-20160816; b=Sgup7389KNGbq8qDKb8QZIehq7jwPaHqQeoSBvST0tK27hEzdhwjI3bB2VupruB15e KNcjeZQNjMt5VFFA5+3ixRTfoLHzgwPKmNu278YlkGEBIuyytIwMhHU5rjIiCsgvnLHH iRremtRilog0Dzwf61tslIyWbjpW593sFg64+/tk/+tTDX3Aqc5tqtRLX3s6P1sjEmxR kAmNsNBqu9puFZMTYPuLLokUf+Flytd6uH49m9UIXOTwpTmgIiMC/PYMSfMi8HaE2NFr l0gV88tiltus9HYIVeO4yHFyoyWdCmFVYrn5B+ms3A7rH5qsrz+nOfieY+c0PhyoUVSg UgyA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=sender:errors-to:content-transfer-encoding:cc:list-subscribe :list-help:list-post:list-archive:list-unsubscribe:list-id :precedence:mime-version:references:in-reply-to:message-id:date :subject:to:from:delivered-to; bh=akAaRoduiC1tUVIlXUnSs8ViPT/GFOs+bv8AnEm/zCU=; b=m/6iZO/I+m7E1FhRGEB+/y1V0vTEly2inLaJ3XLneBFydIwa12dj/TKIDsHGswXf7c Rxoe8QyPm5KBuHQLES+EHi+dZUQaytFcIt/to1bq/cLyPaUoY4RpzJQEFj/jhAwSs7wh ue0JjFXNh2R3OdTdMkyxSZddHwpd0R0WWtU/fLUs1jbsOI4kMP9jNTa9D1tEJHfoS3lJ 6IIciuuGxXRxlCHxXn8UfwoKWWymYNp5X3CyKfEv0jY+vd1L0OhyZ4rkFEFBA8Y+1gR9 xxTWGkzSmxaQsW3nUHTGjQjbIsoVHd4dORBCxcmDoOIhuSJilgoMzrfQujTPULVlVg4e 71JA== ARC-Authentication-Results: i=1; mx.google.com; spf=pass (google.com: best guess record for domain of dri-devel-bounces@lists.freedesktop.org designates 131.252.210.177 as permitted sender) smtp.mailfrom=dri-devel-bounces@lists.freedesktop.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=kernel.org Return-Path: Received: from gabe.freedesktop.org (gabe.freedesktop.org. [131.252.210.177]) by mx.google.com with ESMTPS id r14si28362143pgi.513.2019.07.17.11.34.07 (version=TLS1_2 cipher=ECDHE-RSA-CHACHA20-POLY1305 bits=256/256); Wed, 17 Jul 2019 11:34:07 -0700 (PDT) Received-SPF: pass (google.com: best guess record for domain of dri-devel-bounces@lists.freedesktop.org designates 131.252.210.177 as permitted sender) client-ip=131.252.210.177; Authentication-Results: mx.google.com; spf=pass (google.com: best guess record for domain of dri-devel-bounces@lists.freedesktop.org designates 131.252.210.177 as permitted sender) smtp.mailfrom=dri-devel-bounces@lists.freedesktop.org; dmarc=fail (p=NONE sp=NONE dis=NONE) header.from=kernel.org Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 7240F6E29D; Wed, 17 Jul 2019 18:34:06 +0000 (UTC) X-Original-To: dri-devel@lists.freedesktop.org Delivered-To: dri-devel@lists.freedesktop.org Received: from mail-io1-f65.google.com (mail-io1-f65.google.com [209.85.166.65]) by gabe.freedesktop.org (Postfix) with ESMTPS id 645DD6E299 for ; Wed, 17 Jul 2019 18:33:58 +0000 (UTC) Received: by mail-io1-f65.google.com with SMTP id k8so47417094iot.1 for ; Wed, 17 Jul 2019 11:33:58 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=jq4eSH6hla4aQ1CV+O0m+YbLlUpIZd8dCqrEOeNad44=; b=DHJC8+OoFdTkyahsjPjX89+LrGm6S7ovR1oys84HlQcDNNAjY0rrGk7KNheNYG7Jg4 xRZXCyPCRmd61YkFbH4NI/G3p0pZfImRTZ8n3sTjx6bExo8nK/HVz8ybkPBVn41xrE44 K3FP/n0lV/DGbatlezkf2HYqNJ4g0662GJ+EqPS9SvfUnbO0xEEWrdCl/SP84wtIEnU0 kffrdlJJG8jBhqRAYQNdC/CQIkG5A3zSWtwPt6CcK02NwrDfJqPRm21lxSSG+29sOeK4 6PNKeZjGqvJ4ETbwaE1eazcPrztpNYuee49DraNHFwWnzarPwm12UFy9FzRn1ucvobJA PaDg== X-Gm-Message-State: APjAAAUmhtO09ipXrJ3+sZ7LWKBQWebJytqnGdc3V4s/Bqxm2qSjKmyc /ZYdW/FgAPSEMWSTCWdvHOtPP4A= X-Received: by 2002:a02:ce37:: with SMTP id v23mr42123968jar.2.1563388437454; Wed, 17 Jul 2019 11:33:57 -0700 (PDT) Received: from xps15.herring.priv ([64.188.179.255]) by smtp.googlemail.com with ESMTPSA id v10sm22109472iob.43.2019.07.17.11.33.56 (version=TLS1_3 cipher=AEAD-AES256-GCM-SHA384 bits=256/256); Wed, 17 Jul 2019 11:33:56 -0700 (PDT) From: Rob Herring To: dri-devel@lists.freedesktop.org Subject: [PATCH 3/5] drm/panfrost: Add a no execute flag for BO allocations Date: Wed, 17 Jul 2019 12:33:50 -0600 Message-Id: <20190717183352.22519-3-robh@kernel.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20190717183352.22519-1-robh@kernel.org> References: <20190717183352.22519-1-robh@kernel.org> MIME-Version: 1.0 X-BeenThere: dri-devel@lists.freedesktop.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: Direct Rendering Infrastructure - Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Boris Brezillon , Robin Murphy , Alyssa Rosenzweig , Tomeu Vizoso , Steven Price Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" Executable buffers have an alignment restriction that they can't cross 16MB boundary as the GPU program counter is 24-bits. This restriction is currently not handled and we just get lucky. As current userspace assumes all BOs are executable, that has to remain the default. So add a new PANFROST_BO_NOEXEC flag to allow userspace to indicate which BOs are not executable. There is also a restriction that executable buffers cannot start or end on a 4GB boundary. This is mostly avoided as there is only 4GB of space currently and the beginning is already blocked out for NULL ptr detection. Add support to handle this restriction fully regardless of the current constraints. For existing userspace, all created BOs remain executable, but the GPU VA alignment will be increased to the size of the BO. This shouldn't matter as there is plenty of GPU VA space. Cc: Tomeu Vizoso Cc: Boris Brezillon Cc: Robin Murphy Cc: Steven Price Cc: Alyssa Rosenzweig Signed-off-by: Rob Herring --- drivers/gpu/drm/panfrost/panfrost_drv.c | 20 +++++++++++++++++++- drivers/gpu/drm/panfrost/panfrost_gem.c | 18 ++++++++++++++++-- drivers/gpu/drm/panfrost/panfrost_gem.h | 3 ++- drivers/gpu/drm/panfrost/panfrost_mmu.c | 3 +++ include/uapi/drm/panfrost_drm.h | 2 ++ 5 files changed, 42 insertions(+), 4 deletions(-) diff --git a/drivers/gpu/drm/panfrost/panfrost_drv.c b/drivers/gpu/drm/panfrost/panfrost_drv.c index d354b92964d5..b91e991bc6a3 100644 --- a/drivers/gpu/drm/panfrost/panfrost_drv.c +++ b/drivers/gpu/drm/panfrost/panfrost_drv.c @@ -49,7 +49,8 @@ static int panfrost_ioctl_create_bo(struct drm_device *dev, void *data, struct panfrost_gem_object *bo; struct drm_panfrost_create_bo *args = data; - if (!args->size || args->flags || args->pad) + if (!args->size || args->pad || + (args->flags & ~PANFROST_BO_NOEXEC)) return -EINVAL; bo = panfrost_gem_create_with_handle(file, dev, args->size, args->flags, @@ -367,6 +368,22 @@ static struct drm_driver panfrost_drm_driver = { .gem_prime_mmap = drm_gem_prime_mmap, }; +#define PFN_4G_MASK ((SZ_4G - 1) >> PAGE_SHIFT) + +static void panfrost_drm_mm_color_adjust(const struct drm_mm_node *node, + unsigned long color, + u64 *start, u64 *end) +{ + /* Executable buffers can't start or end on a 4GB boundary */ + if (!color) { + if ((*start & PFN_4G_MASK) == 0) + (*start)++; + + if ((*end & PFN_4G_MASK) == 0) + (*end)--; + } +} + static int panfrost_probe(struct platform_device *pdev) { struct panfrost_device *pfdev; @@ -394,6 +411,7 @@ static int panfrost_probe(struct platform_device *pdev) /* 4G enough for now. can be 48-bit */ drm_mm_init(&pfdev->mm, SZ_32M >> PAGE_SHIFT, (SZ_4G - SZ_32M) >> PAGE_SHIFT); + pfdev->mm.color_adjust = panfrost_drm_mm_color_adjust; pm_runtime_use_autosuspend(pfdev->dev); pm_runtime_set_autosuspend_delay(pfdev->dev, 50); /* ~3 frames */ diff --git a/drivers/gpu/drm/panfrost/panfrost_gem.c b/drivers/gpu/drm/panfrost/panfrost_gem.c index df70dcf3cb2f..37ffec8391da 100644 --- a/drivers/gpu/drm/panfrost/panfrost_gem.c +++ b/drivers/gpu/drm/panfrost/panfrost_gem.c @@ -66,11 +66,23 @@ static int panfrost_gem_map(struct panfrost_device *pfdev, struct panfrost_gem_o { int ret; size_t size = bo->base.base.size; - u64 align = size >= SZ_2M ? SZ_2M >> PAGE_SHIFT : 0; + u64 align; + + /* + * Executable buffers cannot cross a 16MB boundary as the program + * counter is 24-bits. We assume executable buffers will be less than + * 16MB and aligning executable buffers to their size will avoid + * crossing a 16MB boundary. + */ + if (!bo->noexec) + align = size >> PAGE_SHIFT; + else + align = size >= SZ_2M ? SZ_2M >> PAGE_SHIFT : 0; spin_lock(&pfdev->mm_lock); ret = drm_mm_insert_node_generic(&pfdev->mm, &bo->node, - size >> PAGE_SHIFT, align, 0, 0); + size >> PAGE_SHIFT, align, + bo->noexec, 0); spin_unlock(&pfdev->mm_lock); if (ret) return ret; @@ -96,6 +108,7 @@ panfrost_gem_create_with_handle(struct drm_file *file_priv, return ERR_CAST(shmem); bo = to_panfrost_bo(&shmem->base); + bo->noexec = !!(flags & PANFROST_BO_NOEXEC); ret = panfrost_gem_map(pfdev, bo); if (ret) @@ -123,6 +136,7 @@ panfrost_gem_prime_import_sg_table(struct drm_device *dev, return ERR_CAST(obj); pobj = to_panfrost_bo(obj); + pobj->noexec = true; ret = panfrost_gem_map(pfdev, pobj); if (ret) diff --git a/drivers/gpu/drm/panfrost/panfrost_gem.h b/drivers/gpu/drm/panfrost/panfrost_gem.h index ce065270720b..132f02399b7b 100644 --- a/drivers/gpu/drm/panfrost/panfrost_gem.h +++ b/drivers/gpu/drm/panfrost/panfrost_gem.h @@ -11,7 +11,8 @@ struct panfrost_gem_object { struct drm_gem_shmem_object base; struct drm_mm_node node; - bool is_mapped; + bool is_mapped :1; + bool noexec :1; }; static inline diff --git a/drivers/gpu/drm/panfrost/panfrost_mmu.c b/drivers/gpu/drm/panfrost/panfrost_mmu.c index 5383b837f04b..d18484a07bfa 100644 --- a/drivers/gpu/drm/panfrost/panfrost_mmu.c +++ b/drivers/gpu/drm/panfrost/panfrost_mmu.c @@ -212,6 +212,9 @@ int panfrost_mmu_map(struct panfrost_gem_object *bo) if (WARN_ON(bo->is_mapped)) return 0; + if (bo->noexec) + prot |= IOMMU_NOEXEC; + sgt = drm_gem_shmem_get_pages_sgt(obj); if (WARN_ON(IS_ERR(sgt))) return PTR_ERR(sgt); diff --git a/include/uapi/drm/panfrost_drm.h b/include/uapi/drm/panfrost_drm.h index b5d370638846..17fb5d200f7a 100644 --- a/include/uapi/drm/panfrost_drm.h +++ b/include/uapi/drm/panfrost_drm.h @@ -82,6 +82,8 @@ struct drm_panfrost_wait_bo { __s64 timeout_ns; /* absolute */ }; +#define PANFROST_BO_NOEXEC 1 + /** * struct drm_panfrost_create_bo - ioctl argument for creating Panfrost BOs. *