aboutsummaryrefslogtreecommitdiffstats
path: root/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.14.71/0785-drm-amdgpu-hybrid-add-SSG-support.patch
diff options
context:
space:
mode:
Diffstat (limited to 'meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.14.71/0785-drm-amdgpu-hybrid-add-SSG-support.patch')
-rw-r--r--meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.14.71/0785-drm-amdgpu-hybrid-add-SSG-support.patch233
1 files changed, 233 insertions, 0 deletions
diff --git a/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.14.71/0785-drm-amdgpu-hybrid-add-SSG-support.patch b/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.14.71/0785-drm-amdgpu-hybrid-add-SSG-support.patch
new file mode 100644
index 00000000..f8f04cfb
--- /dev/null
+++ b/meta-amd-bsp/recipes-kernel/linux/linux-yocto-4.14.71/0785-drm-amdgpu-hybrid-add-SSG-support.patch
@@ -0,0 +1,233 @@
+From 5844c053f2f504b17a59b51d220a169a3fa2e846 Mon Sep 17 00:00:00 2001
+From: Qiang Yu <Qiang.Yu@amd.com>
+Date: Mon, 13 Feb 2017 16:01:52 +0800
+Subject: [PATCH 0785/4131] drm/amdgpu/hybrid: add SSG support
+
+Depend on DirectGMA and CONFIG_ZONE_DEVICE/PFN_MAP. User process
+can mmap a DirectGMA amdgpu_bo and use it as the buffer for file
+directio read/write which means disk can transfer data directly
+between visible VRAM and disk controller without pass the DRAM.
+
+This implementation is inspired by DAX-GUP:
+https://lwn.net/Articles/667148/
+
+Change-Id: I7205f3391d67677277b4b5cbcb26fd81b66e15fb
+Signed-off-by: Qiang Yu <Qiang.Yu@amd.com>
+Acked-by: Chunming Zhou <david1.zhou@amd.com>
+Signed-off-by: Kalyan Alle <kalyan.alle@amd.com>
+
+ Conflicts:
+ drivers/gpu/drm/ttm/ttm_bo_vm.c
+---
+ drivers/gpu/drm/amd/amdgpu/amdgpu.h | 18 +++++++
+ drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c | 4 ++
+ drivers/gpu/drm/amd/amdgpu/amdgpu_object.c | 3 ++
+ drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c | 79 ++++++++++++++++++++++++++++++
+ include/drm/ttm/ttm_bo_api.h | 1 +
+ 5 files changed, 105 insertions(+)
+
+diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu.h b/drivers/gpu/drm/amd/amdgpu/amdgpu.h
+index 9db84c8..80aca7d 100644
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu.h
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu.h
+@@ -35,6 +35,7 @@
+ #include <linux/rbtree.h>
+ #include <linux/hashtable.h>
+ #include <linux/dma-fence.h>
++#include <linux/version.h>
+
+ #include <drm/ttm/ttm_bo_api.h>
+ #include <drm/ttm/ttm_bo_driver.h>
+@@ -107,6 +108,7 @@ extern int amdgpu_sched_jobs;
+ extern int amdgpu_sched_hw_submission;
+ extern int amdgpu_no_evict;
+ extern int amdgpu_direct_gma_size;
++extern int amdgpu_ssg_enabled;
+ extern unsigned amdgpu_pcie_gen_cap;
+ extern unsigned amdgpu_pcie_lane_cap;
+ extern unsigned amdgpu_cg_mask;
+@@ -1417,6 +1419,19 @@ struct amdgpu_direct_gma {
+ atomic64_t gart_usage;
+ };
+
++#if defined(CONFIG_ZONE_DEVICE) && \
++ (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 5, 0) || defined(OS_NAME_RHEL_7_3) || defined(OS_NAME_SLE))
++#define CONFIG_ENABLE_SSG
++#endif
++
++struct amdgpu_ssg {
++ bool enabled;
++#ifdef CONFIG_ENABLE_SSG
++ struct percpu_ref ref;
++ struct completion cmp;
++#endif
++};
++
+ #define AMDGPU_RESET_MAGIC_NUM 64
+ struct amdgpu_device {
+ struct device *dev;
+@@ -1463,6 +1478,9 @@ struct amdgpu_device {
+ uint32_t bios_scratch_reg_offset;
+ uint32_t bios_scratch[AMDGPU_BIOS_NUM_SCRATCH];
+
++ /* SSG */
++ struct amdgpu_ssg ssg;
++
+ /* Register/doorbell mmio */
+ resource_size_t rmmio_base;
+ resource_size_t rmmio_size;
+diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
+index da98307..e190da1 100644
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c
+@@ -107,6 +107,7 @@ int amdgpu_sched_jobs = 32;
+ int amdgpu_sched_hw_submission = 2;
+ int amdgpu_no_evict = 0;
+ int amdgpu_direct_gma_size = 0;
++int amdgpu_ssg_enabled = 0;
+ unsigned amdgpu_pcie_gen_cap = 0;
+ unsigned amdgpu_pcie_lane_cap = 0;
+ unsigned amdgpu_cg_mask = 0xffffffff;
+@@ -225,6 +226,9 @@ module_param_named(no_evict, amdgpu_no_evict, int, 0444);
+ MODULE_PARM_DESC(direct_gma_size, "Direct GMA size in megabytes (max 96MB)");
+ module_param_named(direct_gma_size, amdgpu_direct_gma_size, int, 0444);
+
++MODULE_PARM_DESC(ssg, "SSG support (1 = enable, 0 = disable (default))");
++module_param_named(ssg, amdgpu_ssg_enabled, int, 0444);
++
+ MODULE_PARM_DESC(pcie_gen_cap, "PCIE Gen Caps (0: autodetect (default))");
+ module_param_named(pcie_gen_cap, amdgpu_pcie_gen_cap, uint, 0444);
+
+diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c
+index cb5fce1..8339fd4 100644
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_object.c
+@@ -433,6 +433,9 @@ int amdgpu_bo_create_restricted(struct amdgpu_device *adev,
+ else
+ amdgpu_cs_report_moved_bytes(adev, bytes_moved, 0);
+
++ if (domain & AMDGPU_GEM_DOMAIN_DGMA && adev->ssg.enabled)
++ bo->tbo.ssg_can_map = true;
++
+ if (kernel)
+ bo->tbo.priority = 1;
+
+diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c
+index c841795..e150097 100644
+--- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c
++++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c
+@@ -1327,6 +1327,83 @@ static void amdgpu_direct_gma_fini(struct amdgpu_device *adev)
+ adev->gart_pin_size -= (u64)amdgpu_direct_gma_size << 20;
+ }
+
++#ifdef CONFIG_ENABLE_SSG
++#include <linux/memremap.h>
++
++static struct amdgpu_ssg *to_amdgpu_ssg(struct percpu_ref *ref)
++{
++ return container_of(ref, struct amdgpu_ssg, ref);
++}
++
++static void amdgpu_ssg_percpu_release(struct percpu_ref *ref)
++{
++ struct amdgpu_ssg *ssg = to_amdgpu_ssg(ref);
++
++ complete(&ssg->cmp);
++}
++
++static int amdgpu_ssg_init(struct amdgpu_device *adev)
++{
++ struct resource res;
++ void *addr;
++ int rc;
++
++ adev->ssg.enabled = false;
++
++ if (!amdgpu_ssg_enabled)
++ return 0;
++
++ if (amdgpu_direct_gma_size == 0) {
++ DRM_INFO("SSG: not enabled due to DirectGMA is disabled\n");
++ return 0;
++ }
++
++ init_completion(&adev->ssg.cmp);
++
++ res.start = adev->mc.aper_base +
++ (amdgpu_bo_gpu_offset(adev->direct_gma.dgma_bo) -
++ adev->mc.vram_start);
++ res.end = res.start + amdgpu_bo_size(adev->direct_gma.dgma_bo);
++ res.name = "DirectGMA";
++
++ rc = percpu_ref_init(&adev->ssg.ref, amdgpu_ssg_percpu_release,
++ 0, GFP_KERNEL);
++ if (rc)
++ return rc;
++
++ addr = devm_memremap_pages(adev->dev, &res, &adev->ssg.ref, NULL);
++ if (IS_ERR(addr)) {
++ percpu_ref_exit(&adev->ssg.ref);
++ return PTR_ERR(addr);
++ }
++
++ adev->ssg.enabled = true;
++ DRM_INFO("SSG: remap %llx-%llx to %p\n", res.start, res.end, addr);
++ return 0;
++}
++
++static void amdgpu_ssg_fini(struct amdgpu_device *adev)
++{
++ if (!adev->ssg.enabled)
++ return;
++
++ percpu_ref_kill(&adev->ssg.ref);
++ wait_for_completion(&adev->ssg.cmp);
++ percpu_ref_exit(&adev->ssg.ref);
++}
++#else
++static int amdgpu_ssg_init(struct amdgpu_device *adev)
++{
++ adev->ssg.enabled = false;
++ return 0;
++}
++
++static void amdgpu_ssg_fini(struct amdgpu_device *adev)
++{
++
++}
++#endif
++
+ int amdgpu_ttm_init(struct amdgpu_device *adev)
+ {
+ uint64_t gtt_size;
+@@ -1388,6 +1465,7 @@ int amdgpu_ttm_init(struct amdgpu_device *adev)
+ (unsigned)(gtt_size / (1024 * 1024)));
+
+ amdgpu_direct_gma_init(adev);
++ amdgpu_ssg_init(adev);
+
+ adev->gds.mem.total_size = adev->gds.mem.total_size << AMDGPU_GDS_SHIFT;
+ adev->gds.mem.gfx_partition_size = adev->gds.mem.gfx_partition_size << AMDGPU_GDS_SHIFT;
+@@ -1451,6 +1529,7 @@ void amdgpu_ttm_fini(struct amdgpu_device *adev)
+ }
+ amdgpu_bo_unref(&adev->stolen_vga_memory);
+ }
++ amdgpu_ssg_fini(adev);
+ amdgpu_direct_gma_fini(adev);
+ ttm_bo_clean_mm(&adev->mman.bdev, TTM_PL_VRAM);
+ ttm_bo_clean_mm(&adev->mman.bdev, TTM_PL_TT);
+diff --git a/include/drm/ttm/ttm_bo_api.h b/include/drm/ttm/ttm_bo_api.h
+index fa07be1..a29c078 100644
+--- a/include/drm/ttm/ttm_bo_api.h
++++ b/include/drm/ttm/ttm_bo_api.h
+@@ -175,6 +175,7 @@ struct ttm_buffer_object {
+ void (*destroy) (struct ttm_buffer_object *);
+ unsigned long num_pages;
+ size_t acc_size;
++ bool ssg_can_map;
+
+ /**
+ * Members not needing protection.
+--
+2.7.4
+