host1x-emu: kmd: Add support for ACPI

This change enable device probing for ACPI device.

Bug 5011544

Change-Id: Ibfc85be18b0d73e813f68c699e4baa3de9682b5d
Reviewed-on: https://git-master.nvidia.com/r/c/linux-nv-oot/+/3276952
Signed-off-by: Amit Sharma <amisharma@nvidia.com>
(cherry picked from commit bbfa4c3afd2dd3856b01be1b15c3023549dd079b)
Reviewed-on: https://git-master.nvidia.com/r/c/linux-nv-oot/+/3272347
Reviewed-by: Arvind M <am@nvidia.com>
Reviewed-by: Mitch Harwell <mharwell@nvidia.com>
Reviewed-by: Ayush Kumar <ayushk@nvidia.com>
Reviewed-by: Amitabh Dutta <amitabhd@nvidia.com>
Reviewed-by: Vishal Thoke <vthoke@nvidia.com>
GVS: buildbot_gerritrpt <buildbot_gerritrpt@nvidia.com>
This commit is contained in:
Arvind M
2025-01-03 11:36:46 +00:00
committed by Jon Hunter
parent 7f006193a3
commit 4bf26c4247
2 changed files with 98 additions and 43 deletions

View File

@@ -1,5 +1,7 @@
// SPDX-License-Identifier: GPL-2.0-only /*
// SPDX-FileCopyrightText: Copyright (c) 2024-2025 NVIDIA CORPORATION & AFFILIATES. All rights reserved. * SPDX-FileCopyrightText: Copyright (c) 2024-2025 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
* SPDX-License-Identifier: GPL-2.0-only
*/
#include <nvidia/conftest.h> #include <nvidia/conftest.h>
#include <linux/clk.h> #include <linux/clk.h>
#include <linux/delay.h> #include <linux/delay.h>
@@ -7,6 +9,7 @@
#include <linux/io.h> #include <linux/io.h>
#include <linux/list.h> #include <linux/list.h>
#include <linux/module.h> #include <linux/module.h>
#include <linux/acpi.h>
#include <linux/of.h> #include <linux/of.h>
#include <linux/of_platform.h> #include <linux/of_platform.h>
#include <linux/pm_runtime.h> #include <linux/pm_runtime.h>
@@ -36,6 +39,8 @@
#define HOST1X_SYNCPT_POOL_BASE(x) (x*2+0) #define HOST1X_SYNCPT_POOL_BASE(x) (x*2+0)
#define HOST1X_SYNCPT_POOL_SIZE(x) (x*2+1) #define HOST1X_SYNCPT_POOL_SIZE(x) (x*2+1)
struct platform_device *host1x_def_pdev;
static const struct host1x_info host1xEmu_info = { static const struct host1x_info host1xEmu_info = {
.nb_pts = 1024, .nb_pts = 1024,
.init = host1xEMU_init, .init = host1xEMU_init,
@@ -101,6 +106,20 @@ static const struct of_device_id host1x_of_match[] = {
}; };
MODULE_DEVICE_TABLE(of, host1x_of_match); MODULE_DEVICE_TABLE(of, host1x_of_match);
static void *acpi_data[] = {
(void*)&host1xEmu_info, /*0x0*/
NULL,
};
static struct acpi_device_id tegra_emu_syncpt_acpi_match[] = {
{
.id = "NVDA300A",
.driver_data = 0,
},
{ },
};
MODULE_DEVICE_TABLE(acpi, tegra_emu_syncpt_acpi_match);
void host1x_sync_writel(struct host1x *host1x, u32 v, u32 r) void host1x_sync_writel(struct host1x *host1x, u32 v, u32 r)
{ {
if (host1x->hv_syncpt_mem == true) { if (host1x->hv_syncpt_mem == true) {
@@ -219,11 +238,20 @@ static int host1x_get_syncpt_pools(struct host1x *host)
int ret; int ret;
int i; int i;
ret = of_property_count_strings(np, "nvidia,syncpoint-pool-names"); if (ACPI_HANDLE(host->dev)) {
if (ret < 0) { /*
/* No pools defined, only read only pool*/ * Set number of R/W pool as 1 for ACPI clients
dev_err(host->dev, "Host1x-EMU: Invalid nvidia,syncpoint-pool-names property: %d\n", ret); * TODO: Make this based on host->info which is set
ret = 0; * based on platform.
*/
ret = 1;
} else {
ret = of_property_count_strings(np, "nvidia,syncpoint-pool-names");
if (ret < 0) {
/* No pools defined, only read only pool*/
dev_err(host->dev, "Host1x-EMU: Invalid nvidia,syncpoint-pool-names property: %d\n", ret);
ret = 0;
}
} }
host->num_pools = ret; host->num_pools = ret;
@@ -258,22 +286,31 @@ static int host1x_get_syncpt_pools(struct host1x *host)
for (i = 0; i < host->num_pools; i++) { for (i = 0; i < host->num_pools; i++) {
struct host1x_syncpt_pool *pool = &host->pools[i]; struct host1x_syncpt_pool *pool = &host->pools[i];
ret = of_property_read_string_index(np, "nvidia,syncpoint-pool-names", i, &pool->name); if (ACPI_HANDLE(host->dev)) {
if (ret) { /*
dev_err(host->dev, "Host1x-EMU: Invalid nvidia,syncpoint-pool-names property: %d\n", ret); * TODO: Make this based on host->info which is set
return ret; * based on platform.
} */
pool->sp_base = 0;
ret = of_property_read_u32_index(np, "nvidia,syncpoint-pools", HOST1X_SYNCPT_POOL_BASE(i), &pool->sp_base); pool->sp_end = host->syncpt_count;
if (!ret) { } else {
ret = of_property_read_u32_index(np, "nvidia,syncpoint-pools", HOST1X_SYNCPT_POOL_SIZE(i), &pool->sp_end); ret = of_property_read_string_index(np, "nvidia,syncpoint-pool-names", i, &pool->name);
if (ret) { if (ret) {
dev_err(host->dev, "Host1x-EMU: Invalid nvidia,syncpoint-pools property: %d\n", ret); dev_err(host->dev, "Host1x-EMU: Invalid nvidia,syncpoint-pool-names property: %d\n", ret);
return ret;
}
ret = of_property_read_u32_index(np, "nvidia,syncpoint-pools", HOST1X_SYNCPT_POOL_BASE(i), &pool->sp_base);
if (!ret) {
ret = of_property_read_u32_index(np, "nvidia,syncpoint-pools", HOST1X_SYNCPT_POOL_SIZE(i), &pool->sp_end);
if (ret) {
dev_err(host->dev, "Host1x-EMU: Invalid nvidia,syncpoint-pools property: %d\n", ret);
return ret;
}
} else {
dev_err(host->dev, "Host1x-EMU: Error in read, invalid nvidia,syncpoint-pools property: %d\n", ret);
return ret; return ret;
} }
} else {
dev_err(host->dev, "Host1x-EMU: Error in read, invalid nvidia,syncpoint-pools property: %d\n", ret);
return ret;
} }
pool->sp_end = pool->sp_base + pool->sp_end; pool->sp_end = pool->sp_base + pool->sp_end;
@@ -290,10 +327,23 @@ static int host1x_probe(struct platform_device *pdev)
struct host1x *host; struct host1x *host;
host = devm_kzalloc(&pdev->dev, sizeof(*host), GFP_KERNEL); host = devm_kzalloc(&pdev->dev, sizeof(*host), GFP_KERNEL);
if (!host) if (!host) {
return -ENOMEM; return -ENOMEM;
}
if (ACPI_HANDLE(&pdev->dev)) {
const struct acpi_device_id *match;
match = acpi_match_device(tegra_emu_syncpt_acpi_match, &pdev->dev);
if (match == NULL) {
return -ENODEV;
}
host1x_def_pdev = pdev;
host->info = (struct host1x_info *)acpi_data[match->driver_data];
}else {
host->info = of_device_get_match_data(&pdev->dev);
}
host->info = of_device_get_match_data(&pdev->dev);
if (host->info == NULL) { if (host->info == NULL) {
dev_err(&pdev->dev, "Host1x-EMU: platform match data not found\n"); dev_err(&pdev->dev, "Host1x-EMU: platform match data not found\n");
return -EINVAL; return -EINVAL;
@@ -345,10 +395,12 @@ static int host1x_probe(struct platform_device *pdev)
host1x_debug_init(host); host1x_debug_init(host);
#endif #endif
err = devm_of_platform_populate(&pdev->dev); if (host->dev->of_node) {
if (err < 0) { err = devm_of_platform_populate(&pdev->dev);
pr_info("Host1x-EMU: Failed to populate device from DT\n"); if (err < 0) {
goto deinit_debugfs; pr_info("Host1x-EMU: Failed to populate device from DT\n");
goto deinit_debugfs;
}
} }
/* Start pool polling thread*/ /* Start pool polling thread*/
@@ -423,6 +475,7 @@ static struct platform_driver tegra_host1x_driver = {
.driver = { .driver = {
.name = "tegra-host1x-emu", .name = "tegra-host1x-emu",
.of_match_table = host1x_of_match, .of_match_table = host1x_of_match,
.acpi_match_table = ACPI_PTR(tegra_emu_syncpt_acpi_match),
.pm = &host1x_pm_ops, .pm = &host1x_pm_ops,
}, },
.probe = host1x_probe, .probe = host1x_probe,

View File

@@ -1,5 +1,5 @@
/* /*
* SPDX-FileCopyrightText: Copyright (c) 2024 NVIDIA CORPORATION & AFFILIATES. All rights reserved. * SPDX-FileCopyrightText: Copyright (c) 2024-2025 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
* SPDX-License-Identifier: GPL-2.0-only * SPDX-License-Identifier: GPL-2.0-only
*/ */
#include <nvidia/conftest.h> #include <nvidia/conftest.h>
@@ -10,24 +10,20 @@
#include <linux/interrupt.h> #include <linux/interrupt.h>
#include <linux/iommu.h> #include <linux/iommu.h>
#include <linux/module.h> #include <linux/module.h>
#include <linux/acpi.h>
#include <linux/of_platform.h> #include <linux/of_platform.h>
#include <linux/pm_runtime.h> #include <linux/pm_runtime.h>
#include <linux/reset.h> #include <linux/reset.h>
#include <linux/scatterlist.h> #include <linux/scatterlist.h>
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/version.h> #include <linux/version.h>
#ifdef CONFIG_TEGRA_HOST1X_EMU_DBG_SYMBL
#include <linux/host1x-emu.h>
#include <linux/nvhost-emu.h> #include <linux/nvhost-emu.h>
#else #include <linux/host1x-emu.h>
#include <linux/host1x-next.h>
#include <linux/nvhost.h>
#include <linux/nvhost_t194.h>
#endif
#include "dev.h" #include "dev.h"
#define NVHOST_NUM_CDEV 1 #define NVHOST_NUM_CDEV 1
extern struct platform_device *host1x_def_pdev;
struct nvhost_syncpt_interface { struct nvhost_syncpt_interface {
dma_addr_t base; dma_addr_t base;
@@ -127,16 +123,22 @@ HOST1X_EMU_EXPORT_SYMBOL(host1x_writel);
HOST1X_EMU_EXPORT_DECL(struct platform_device*, nvhost_get_default_device(void)) HOST1X_EMU_EXPORT_DECL(struct platform_device*, nvhost_get_default_device(void))
{ {
struct device_node *np; struct device_node *np;
struct platform_device *host1x_pdev; struct platform_device *host1x_pdev;
np = of_find_matching_node(NULL, host1x_match); np = of_find_matching_node(NULL, host1x_match);
if (!np) if (np) {
return NULL; host1x_pdev = of_find_device_by_node(np);
if (!host1x_pdev)
host1x_pdev = of_find_device_by_node(np); return NULL;
if (!host1x_pdev) } else {
return NULL; if ((host1x_def_pdev != NULL) &&
(ACPI_HANDLE(&host1x_def_pdev->dev))) {
host1x_pdev = host1x_def_pdev;
}
else
return NULL;
}
return host1x_pdev; return host1x_pdev;
} }