From nobody Tue Nov 26 06:34:34 2024 Received: from NAM04-BN8-obe.outbound.protection.outlook.com (mail-bn8nam04on2072.outbound.protection.outlook.com [40.107.100.72]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 912CF1E573D for ; Mon, 21 Oct 2024 16:20:04 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=fail smtp.client-ip=40.107.100.72 ARC-Seal: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729527607; cv=fail; b=e5GgRWlWLbPGU0JWVkp0DhueKYTScbp/PbilI9v6zZxPAO8tRxLvPynAM3RUZykGzfkt1rX8wXesVl9tOPQ7HZjQu0eaXQ9fX9tZfqOZ2NfvV3Vmuuzs+oqmH/VkDCalixaLuDxWKqwwKD/FSUqMTuSbCG8qoqKxasSTg0SKHa0= ARC-Message-Signature: i=2; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729527607; c=relaxed/simple; bh=4E9exIvCjpQJyKU1kevOIzkkfRNS4ykr6lNg3yoxKNM=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=iPV8i+yB48ifwp77mGdQaIAcMK2fTF9zx0k8cLIc4woaYq/U6YUoW4441o3iNexaFNw6LqkpEv8MS3wuWAafb4z/q0Rpqhy2Fx/ZuBBMUgU9FiMpsYiO4LKLbX8KwS0t/Sc/w8JavAS9pBfJYxILLQ+c5bpBXFwjhmV41xLZgpA= ARC-Authentication-Results: i=2; smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=amd.com; spf=fail smtp.mailfrom=amd.com; dkim=pass (1024-bit key) header.d=amd.com header.i=@amd.com header.b=k6Ny7jxC; arc=fail smtp.client-ip=40.107.100.72 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=quarantine dis=none) header.from=amd.com Authentication-Results: smtp.subspace.kernel.org; spf=fail smtp.mailfrom=amd.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (1024-bit key) header.d=amd.com header.i=@amd.com header.b="k6Ny7jxC" ARC-Seal: i=1; a=rsa-sha256; s=arcselector10001; d=microsoft.com; cv=none; b=VsxNLz71tDpQa9ANzhWhq6mZS2lv1Niro84YLoQMYDpHnKsKpNAKS4kIYuBBLmNlCLQ+PnMPQWqcpMhmlrZsT6QYF8kmyacyF9IW6IP4T39L5bzHJ/EQQau2xTaISG4noAi0T8RGPG8fXeU+Na3pmvGTJEl7xo2GRKTahBvHmeXuMXsjuxUdBh7k1VEWikTC0QYVX295CEe6sSU2oB2c4yypjSbV0sPdLFba1o6sgfswm3KAPONAN2TtDJ9eTSLcqU92zzJycU6whQVJaEYnJJbekxvavp/ls438XZepmbgwc+O8qVZe9/CCIR9fqTWRGrEGUkCdch2KsgAiDrRbfA== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector10001; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=TZgpfBeE0K9ztuEZon+pFPnij5/Rr5cJ3hI+Pf/j9E4=; b=JEZz36FqCS3tgZBlj8WTL7CSMaCob3uZT5Ak5/bj+QyaRdzXQMnhZcGWtcBOil56zuU6skVQGgSiKpe762gLLf+UuT6QlY8ezGasm6WnqG102EP9cKKpCo861NHZ6e5Fuk3Q9dt6B2UcdiTOuMt1YXxTNXdR4iNDMzg5V+eKow7HrDjT2+4B+LrK/7F5E1OsA//PLTaFr7Rw4iW/rCzRJoC491hsXTkhujY3CfUhpbvbNpx3+4rzb5xOlXLIqVyPzYMj+6GqX+u8D6VGTqXIHI2jy7ZJT+9pp9gnuOgpbnndMT6i09sKj7Dp8CqNNG5g/czsrKRHfRhPzJHNc37e9Q== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass (sender ip is 165.204.84.17) smtp.rcpttodomain=kernel.org smtp.mailfrom=amd.com; dmarc=pass (p=quarantine sp=quarantine pct=100) action=none header.from=amd.com; dkim=none (message not signed); arc=none (0) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=amd.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=TZgpfBeE0K9ztuEZon+pFPnij5/Rr5cJ3hI+Pf/j9E4=; b=k6Ny7jxCvZUnRbcZ64I4Z/CIXOeldJbA/d9OcCBVbsvXhb/AWMHt2pQnomHdHGc/FRNM660Bq4DCn097CVpp6i0e9IVpMqMBANSjDAZ1MueiOanIcTiVAZfxMq1n4ROPCXFqJkEefN3W646jzIzRlhISqPuZLXZdOxmXMssgXJM= Received: from MW4PR03CA0169.namprd03.prod.outlook.com (2603:10b6:303:8d::24) by SJ2PR12MB8782.namprd12.prod.outlook.com (2603:10b6:a03:4d0::21) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.8069.27; Mon, 21 Oct 2024 16:20:00 +0000 Received: from SJ1PEPF00001CDE.namprd05.prod.outlook.com (2603:10b6:303:8d:cafe::5e) by MW4PR03CA0169.outlook.office365.com (2603:10b6:303:8d::24) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.8069.28 via Frontend Transport; Mon, 21 Oct 2024 16:19:59 +0000 X-MS-Exchange-Authentication-Results: spf=pass (sender IP is 165.204.84.17) smtp.mailfrom=amd.com; dkim=none (message not signed) header.d=none;dmarc=pass action=none header.from=amd.com; Received-SPF: Pass (protection.outlook.com: domain of amd.com designates 165.204.84.17 as permitted sender) receiver=protection.outlook.com; client-ip=165.204.84.17; helo=SATLEXMB04.amd.com; pr=C Received: from SATLEXMB04.amd.com (165.204.84.17) by SJ1PEPF00001CDE.mail.protection.outlook.com (10.167.242.6) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.20.8093.14 via Frontend Transport; Mon, 21 Oct 2024 16:19:59 +0000 Received: from SATLEXMB05.amd.com (10.181.40.146) by SATLEXMB04.amd.com (10.181.40.145) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2507.39; Mon, 21 Oct 2024 11:19:58 -0500 Received: from SATLEXMB03.amd.com (10.181.40.144) by SATLEXMB05.amd.com (10.181.40.146) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2507.39; Mon, 21 Oct 2024 11:19:58 -0500 Received: from xsjlizhih51.xilinx.com (10.180.168.240) by SATLEXMB03.amd.com (10.181.40.144) with Microsoft SMTP Server id 15.1.2507.39 via Frontend Transport; Mon, 21 Oct 2024 11:19:57 -0500 From: Lizhi Hou To: , CC: Lizhi Hou , , , , , , Jeffrey Hugo Subject: [PATCH V5 10/10] accel/amdxdna: Add query functions Date: Mon, 21 Oct 2024 09:19:31 -0700 Message-ID: <20241021161931.3701754-11-lizhi.hou@amd.com> X-Mailer: git-send-email 2.34.1 In-Reply-To: <20241021161931.3701754-1-lizhi.hou@amd.com> References: <20241021161931.3701754-1-lizhi.hou@amd.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Received-SPF: None (SATLEXMB05.amd.com: lizhi.hou@amd.com does not designate permitted sender hosts) X-EOPAttributedMessage: 0 X-MS-PublicTrafficType: Email X-MS-TrafficTypeDiagnostic: SJ1PEPF00001CDE:EE_|SJ2PR12MB8782:EE_ X-MS-Office365-Filtering-Correlation-Id: 944190a2-0cd6-4019-8966-08dcf1ec35bb X-MS-Exchange-SenderADCheck: 1 X-MS-Exchange-AntiSpam-Relay: 0 X-Microsoft-Antispam: BCL:0;ARA:13230040|36860700013|376014|82310400026|1800799024; X-Microsoft-Antispam-Message-Info: =?us-ascii?Q?sOd2N3OcaQ/CoZ5/u2vHhorMfe7LttcLsZpdpilTnAkb8Szq61A48lhOieyi?= =?us-ascii?Q?7CWoWoMOuFIHmEjpxKnTm3Gp2s2udWBlD7jV94woxPFTobkgmprC9QirPPqU?= =?us-ascii?Q?YW6JWNMS/nSiJ8VjVDzyAgUGcqsD1nNgtQT1j1TD3XyKOCAYpPU4rzHiCthl?= =?us-ascii?Q?CgeChqbFQMLTCdqAFTzrqRHnzn1sD/If871Y+VCY6VDkCnqGDkE0wRQkXEDI?= =?us-ascii?Q?sUN/dWpWmmg7xg26t2yZ2OhVhYzQMWyAHzyuU93lJ01Zl8rhBXrmQsM4WdMr?= =?us-ascii?Q?Lwa2gkf7uiQMgP9lryepYVeRJw+mgWFfGrWsoIc6dOBBBai0ZlzN3eWFI33D?= =?us-ascii?Q?JOn5AlbbzpKqBL4ElB9Qawsd2ruwADCobW+zxNlFBaFbDMEj2q2q9gBn9gKv?= =?us-ascii?Q?GD4mJOPD0+Q88x+MZPZiBGqkbGqzQDI72zUHifJKN7OYRBIK1HvJUW67eCSZ?= =?us-ascii?Q?PNvkNWw90XFl9FMI//fKFjbH6LADI/wE2sYfVFoctLLcAfENhL9nN1qQq9O0?= =?us-ascii?Q?9Sb6Ji/OQM7GI0l5yzfMJX43kZgpSo+9wBf+tPDnGvZbKG6f+ws0CcHnLVBG?= =?us-ascii?Q?DVNeScvsr2Gck3emPnzStOHoB1d2VbnQR3BWkXX6tcjHMh5fY5GoPgPVsR9S?= =?us-ascii?Q?4JkVzrp6m3AbPW+qJDuhbmn49H0pWbuSuq56mbUbmtWXnCgjQ4SvOYispqPc?= =?us-ascii?Q?tS3NPeq/v12DM8gCLVMCPBUHW5UoKJpgBwMF3w4N8YFqdgh94dE4gzDYPjFq?= =?us-ascii?Q?lo8JOCYtfna0cqY4YJe5+POu6RpN0WYQAbkZ9DrHFfeVDq3a+8kxCxTluLbg?= =?us-ascii?Q?rAXEqLm9XTUcN8DsvrRRsiJVyM7ZeHorOXxuJkQNSaOhZQ5wk1++SYHmRE3i?= =?us-ascii?Q?WkGpT2PtgNYL8iTWEC1J9TlAfME4if/iZM2spaj1+HzzHx3WlHl46PqZaFjR?= =?us-ascii?Q?pFmlw+C5vgAxLpM/XeP0AY2g077AYoMbXduZgN58Jck48QeDfevt1bIC38Of?= =?us-ascii?Q?AnKhZwLnJ1SXnQrjg8es25NXPn07uYwp/Tu5IAqUK7PM3JaE1RPLUih3bbFK?= =?us-ascii?Q?0bmJ2eh1Olu2Q4Qaq0gISzkgTTlyROVF/bPBkS2GNfBMaw85owdGya3l1V0u?= =?us-ascii?Q?AbA9WVZ2dY0Caab2jxC9WJEB2OYR5of5ZUyN690atFmQrvpOSuCcfuyi04dB?= =?us-ascii?Q?G2kvimlFzQqV8asYIRJZRhpigiH5OUizBnVLdn5pDHMg2dO6nu088r4smIV4?= =?us-ascii?Q?u5BJUXD7s0qHqRd3VlvQ/V2Thp91dGijyg2rj+0tZqlPbrMOBMH4qjql9wuS?= =?us-ascii?Q?SYOx1Ztd87+oChKkSeRn9KQ8OkgHptfTY6PTv9ONW6m82aYkuOcxJLPZBOon?= =?us-ascii?Q?1INedZZuVuEPb/JpNVnVyxo0hLk0MKMVJkocGBlCDhzQ+LHSEw=3D=3D?= X-Forefront-Antispam-Report: CIP:165.204.84.17;CTRY:US;LANG:en;SCL:1;SRV:;IPV:CAL;SFV:NSPM;H:SATLEXMB04.amd.com;PTR:InfoDomainNonexistent;CAT:NONE;SFS:(13230040)(36860700013)(376014)(82310400026)(1800799024);DIR:OUT;SFP:1101; X-OriginatorOrg: amd.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 21 Oct 2024 16:19:59.4420 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 944190a2-0cd6-4019-8966-08dcf1ec35bb X-MS-Exchange-CrossTenant-Id: 3dd8961f-e488-4e60-8e11-a82d994e183d X-MS-Exchange-CrossTenant-OriginalAttributedTenantConnectingIp: TenantId=3dd8961f-e488-4e60-8e11-a82d994e183d;Ip=[165.204.84.17];Helo=[SATLEXMB04.amd.com] X-MS-Exchange-CrossTenant-AuthSource: SJ1PEPF00001CDE.namprd05.prod.outlook.com X-MS-Exchange-CrossTenant-AuthAs: Anonymous X-MS-Exchange-CrossTenant-FromEntityHeader: HybridOnPrem X-MS-Exchange-Transport-CrossTenantHeadersStamped: SJ2PR12MB8782 Content-Type: text/plain; charset="utf-8" Add GET_INFO ioctl to retrieve hardware information, including AIE, clock, hardware context etc. Co-developed-by: Min Ma Signed-off-by: Min Ma Reviewed-by: Jeffrey Hugo Signed-off-by: Lizhi Hou --- drivers/accel/amdxdna/aie2_message.c | 65 +++++++ drivers/accel/amdxdna/aie2_pci.c | 222 ++++++++++++++++++++++++ drivers/accel/amdxdna/aie2_pci.h | 1 + drivers/accel/amdxdna/amdxdna_pci_drv.c | 19 ++ drivers/accel/amdxdna/amdxdna_pci_drv.h | 3 + include/uapi/drm/amdxdna_accel.h | 166 ++++++++++++++++++ 6 files changed, 476 insertions(+) diff --git a/drivers/accel/amdxdna/aie2_message.c b/drivers/accel/amdxdna/a= ie2_message.c index 6e65b611b691..11686f3c4464 100644 --- a/drivers/accel/amdxdna/aie2_message.c +++ b/drivers/accel/amdxdna/aie2_message.c @@ -307,6 +307,71 @@ int aie2_map_host_buf(struct amdxdna_dev_hdl *ndev, u3= 2 context_id, u64 addr, u6 return 0; } =20 +int aie2_query_status(struct amdxdna_dev_hdl *ndev, char __user *buf, + u32 size, u32 *cols_filled) +{ + DECLARE_AIE2_MSG(aie_column_info, MSG_OP_QUERY_COL_STATUS); + struct amdxdna_dev *xdna =3D ndev->xdna; + struct amdxdna_client *client; + struct amdxdna_hwctx *hwctx; + dma_addr_t dma_addr; + u32 aie_bitmap =3D 0; + u8 *buff_addr; + int next =3D 0; + int ret, idx; + + buff_addr =3D dma_alloc_noncoherent(xdna->ddev.dev, size, &dma_addr, + DMA_FROM_DEVICE, GFP_KERNEL); + if (!buff_addr) + return -ENOMEM; + + /* Go through each hardware context and mark the AIE columns that are act= ive */ + list_for_each_entry(client, &xdna->client_list, node) { + idx =3D srcu_read_lock(&client->hwctx_srcu); + idr_for_each_entry_continue(&client->hwctx_idr, hwctx, next) + aie_bitmap |=3D amdxdna_hwctx_col_map(hwctx); + srcu_read_unlock(&client->hwctx_srcu, idx); + } + + *cols_filled =3D 0; + req.dump_buff_addr =3D dma_addr; + req.dump_buff_size =3D size; + req.num_cols =3D hweight32(aie_bitmap); + req.aie_bitmap =3D aie_bitmap; + + drm_clflush_virt_range(buff_addr, size); /* device can access */ + ret =3D aie2_send_mgmt_msg_wait(ndev, &msg); + if (ret) { + XDNA_ERR(xdna, "Error during NPU query, status %d", ret); + goto fail; + } + + if (resp.status !=3D AIE2_STATUS_SUCCESS) { + XDNA_ERR(xdna, "Query NPU status failed, status 0x%x", resp.status); + ret =3D -EINVAL; + goto fail; + } + XDNA_DBG(xdna, "Query NPU status completed"); + + if (size < resp.size) { + ret =3D -EINVAL; + XDNA_ERR(xdna, "Bad buffer size. Available: %u. Needs: %u", size, resp.s= ize); + goto fail; + } + + if (copy_to_user(buf, buff_addr, resp.size)) { + ret =3D -EFAULT; + XDNA_ERR(xdna, "Failed to copy NPU status to user space"); + goto fail; + } + + *cols_filled =3D aie_bitmap; + +fail: + dma_free_noncoherent(xdna->ddev.dev, size, buff_addr, dma_addr, DMA_FROM_= DEVICE); + return ret; +} + int aie2_register_asyn_event_msg(struct amdxdna_dev_hdl *ndev, dma_addr_t = addr, u32 size, void *handle, int (*cb)(void*, const u32 *, size_t)) { diff --git a/drivers/accel/amdxdna/aie2_pci.c b/drivers/accel/amdxdna/aie2_= pci.c index ff872f2389f7..385a5939944d 100644 --- a/drivers/accel/amdxdna/aie2_pci.c +++ b/drivers/accel/amdxdna/aie2_pci.c @@ -5,6 +5,7 @@ =20 #include #include +#include #include #include #include @@ -528,11 +529,232 @@ static void aie2_fini(struct amdxdna_dev *xdna) pci_free_irq_vectors(pdev); } =20 +static int aie2_get_aie_status(struct amdxdna_client *client, + struct amdxdna_drm_get_info *args) +{ + struct amdxdna_drm_query_aie_status status; + struct amdxdna_dev *xdna =3D client->xdna; + struct amdxdna_dev_hdl *ndev; + int ret; + + ndev =3D xdna->dev_handle; + if (copy_from_user(&status, u64_to_user_ptr(args->buffer), sizeof(status)= )) { + XDNA_ERR(xdna, "Failed to copy AIE request into kernel"); + return -EFAULT; + } + + if (ndev->metadata.cols * ndev->metadata.size < status.buffer_size) { + XDNA_ERR(xdna, "Invalid buffer size. Given Size: %u. Need Size: %u.", + status.buffer_size, ndev->metadata.cols * ndev->metadata.size); + return -EINVAL; + } + + ret =3D aie2_query_status(ndev, u64_to_user_ptr(status.buffer), + status.buffer_size, &status.cols_filled); + if (ret) { + XDNA_ERR(xdna, "Failed to get AIE status info. Ret: %d", ret); + return ret; + } + + if (copy_to_user(u64_to_user_ptr(args->buffer), &status, sizeof(status)))= { + XDNA_ERR(xdna, "Failed to copy AIE request info to user space"); + return -EFAULT; + } + + return 0; +} + +static int aie2_get_aie_metadata(struct amdxdna_client *client, + struct amdxdna_drm_get_info *args) +{ + struct amdxdna_drm_query_aie_metadata *meta; + struct amdxdna_dev *xdna =3D client->xdna; + struct amdxdna_dev_hdl *ndev; + int ret =3D 0; + + ndev =3D xdna->dev_handle; + meta =3D kzalloc(sizeof(*meta), GFP_KERNEL); + if (!meta) + return -ENOMEM; + + meta->col_size =3D ndev->metadata.size; + meta->cols =3D ndev->metadata.cols; + meta->rows =3D ndev->metadata.rows; + + meta->version.major =3D ndev->metadata.version.major; + meta->version.minor =3D ndev->metadata.version.minor; + + meta->core.row_count =3D ndev->metadata.core.row_count; + meta->core.row_start =3D ndev->metadata.core.row_start; + meta->core.dma_channel_count =3D ndev->metadata.core.dma_channel_count; + meta->core.lock_count =3D ndev->metadata.core.lock_count; + meta->core.event_reg_count =3D ndev->metadata.core.event_reg_count; + + meta->mem.row_count =3D ndev->metadata.mem.row_count; + meta->mem.row_start =3D ndev->metadata.mem.row_start; + meta->mem.dma_channel_count =3D ndev->metadata.mem.dma_channel_count; + meta->mem.lock_count =3D ndev->metadata.mem.lock_count; + meta->mem.event_reg_count =3D ndev->metadata.mem.event_reg_count; + + meta->shim.row_count =3D ndev->metadata.shim.row_count; + meta->shim.row_start =3D ndev->metadata.shim.row_start; + meta->shim.dma_channel_count =3D ndev->metadata.shim.dma_channel_count; + meta->shim.lock_count =3D ndev->metadata.shim.lock_count; + meta->shim.event_reg_count =3D ndev->metadata.shim.event_reg_count; + + if (copy_to_user(u64_to_user_ptr(args->buffer), meta, sizeof(*meta))) + ret =3D -EFAULT; + + kfree(meta); + return ret; +} + +static int aie2_get_aie_version(struct amdxdna_client *client, + struct amdxdna_drm_get_info *args) +{ + struct amdxdna_drm_query_aie_version version; + struct amdxdna_dev *xdna =3D client->xdna; + struct amdxdna_dev_hdl *ndev; + + ndev =3D xdna->dev_handle; + version.major =3D ndev->version.major; + version.minor =3D ndev->version.minor; + + if (copy_to_user(u64_to_user_ptr(args->buffer), &version, sizeof(version)= )) + return -EFAULT; + + return 0; +} + +static int aie2_get_clock_metadata(struct amdxdna_client *client, + struct amdxdna_drm_get_info *args) +{ + struct amdxdna_drm_query_clock_metadata *clock; + struct amdxdna_dev *xdna =3D client->xdna; + struct amdxdna_dev_hdl *ndev; + int ret =3D 0; + + ndev =3D xdna->dev_handle; + clock =3D kzalloc(sizeof(*clock), GFP_KERNEL); + if (!clock) + return -ENOMEM; + + memcpy(clock->mp_npu_clock.name, ndev->mp_npu_clock.name, + sizeof(clock->mp_npu_clock.name)); + clock->mp_npu_clock.freq_mhz =3D ndev->mp_npu_clock.freq_mhz; + memcpy(clock->h_clock.name, ndev->h_clock.name, sizeof(clock->h_clock.nam= e)); + clock->h_clock.freq_mhz =3D ndev->h_clock.freq_mhz; + + if (copy_to_user(u64_to_user_ptr(args->buffer), clock, sizeof(*clock))) + ret =3D -EFAULT; + + kfree(clock); + return ret; +} + +static int aie2_get_hwctx_status(struct amdxdna_client *client, + struct amdxdna_drm_get_info *args) +{ + struct amdxdna_drm_query_hwctx __user *buf; + struct amdxdna_dev *xdna =3D client->xdna; + struct amdxdna_drm_query_hwctx *tmp; + struct amdxdna_client *tmp_client; + struct amdxdna_hwctx *hwctx; + bool overflow =3D false; + u32 req_bytes =3D 0; + u32 hw_i =3D 0; + int ret =3D 0; + int next; + int idx; + + drm_WARN_ON(&xdna->ddev, !mutex_is_locked(&xdna->dev_lock)); + + tmp =3D kzalloc(sizeof(*tmp), GFP_KERNEL); + if (!tmp) + return -ENOMEM; + + buf =3D u64_to_user_ptr(args->buffer); + list_for_each_entry(tmp_client, &xdna->client_list, node) { + idx =3D srcu_read_lock(&tmp_client->hwctx_srcu); + next =3D 0; + idr_for_each_entry_continue(&tmp_client->hwctx_idr, hwctx, next) { + req_bytes +=3D sizeof(*tmp); + if (args->buffer_size < req_bytes) { + /* Continue iterating to get the required size */ + overflow =3D true; + continue; + } + + memset(tmp, 0, sizeof(*tmp)); + tmp->pid =3D tmp_client->pid; + tmp->context_id =3D hwctx->id; + tmp->start_col =3D hwctx->start_col; + tmp->num_col =3D hwctx->num_col; + tmp->command_submissions =3D hwctx->priv->seq; + tmp->command_completions =3D hwctx->priv->completed; + + if (copy_to_user(&buf[hw_i], tmp, sizeof(*tmp))) { + ret =3D -EFAULT; + srcu_read_unlock(&tmp_client->hwctx_srcu, idx); + goto out; + } + hw_i++; + } + srcu_read_unlock(&tmp_client->hwctx_srcu, idx); + } + + if (overflow) { + XDNA_ERR(xdna, "Invalid buffer size. Given: %u Need: %u.", + args->buffer_size, req_bytes); + ret =3D -EINVAL; + } + +out: + kfree(tmp); + args->buffer_size =3D req_bytes; + return ret; +} + +static int aie2_get_info(struct amdxdna_client *client, struct amdxdna_drm= _get_info *args) +{ + struct amdxdna_dev *xdna =3D client->xdna; + int ret, idx; + + if (!drm_dev_enter(&xdna->ddev, &idx)) + return -ENODEV; + + switch (args->param) { + case DRM_AMDXDNA_QUERY_AIE_STATUS: + ret =3D aie2_get_aie_status(client, args); + break; + case DRM_AMDXDNA_QUERY_AIE_METADATA: + ret =3D aie2_get_aie_metadata(client, args); + break; + case DRM_AMDXDNA_QUERY_AIE_VERSION: + ret =3D aie2_get_aie_version(client, args); + break; + case DRM_AMDXDNA_QUERY_CLOCK_METADATA: + ret =3D aie2_get_clock_metadata(client, args); + break; + case DRM_AMDXDNA_QUERY_HW_CONTEXTS: + ret =3D aie2_get_hwctx_status(client, args); + break; + default: + XDNA_ERR(xdna, "Not supported request parameter %u", args->param); + ret =3D -EOPNOTSUPP; + } + XDNA_DBG(xdna, "Got param %d", args->param); + + drm_dev_exit(idx); + return ret; +} + const struct amdxdna_dev_ops aie2_ops =3D { .init =3D aie2_init, .fini =3D aie2_fini, .resume =3D aie2_hw_start, .suspend =3D aie2_hw_stop, + .get_aie_info =3D aie2_get_info, .hwctx_init =3D aie2_hwctx_init, .hwctx_fini =3D aie2_hwctx_fini, .hwctx_config =3D aie2_hwctx_config, diff --git a/drivers/accel/amdxdna/aie2_pci.h b/drivers/accel/amdxdna/aie2_= pci.h index 9634a7588650..734499bfb9f7 100644 --- a/drivers/accel/amdxdna/aie2_pci.h +++ b/drivers/accel/amdxdna/aie2_pci.h @@ -225,6 +225,7 @@ int aie2_query_firmware_version(struct amdxdna_dev_hdl = *ndev, int aie2_create_context(struct amdxdna_dev_hdl *ndev, struct amdxdna_hwctx= *hwctx); int aie2_destroy_context(struct amdxdna_dev_hdl *ndev, struct amdxdna_hwct= x *hwctx); int aie2_map_host_buf(struct amdxdna_dev_hdl *ndev, u32 context_id, u64 ad= dr, u64 size); +int aie2_query_status(struct amdxdna_dev_hdl *ndev, char *buf, u32 size, u= 32 *cols_filled); int aie2_register_asyn_event_msg(struct amdxdna_dev_hdl *ndev, dma_addr_t = addr, u32 size, void *handle, int (*cb)(void*, const u32 *, size_t)); int aie2_config_cu(struct amdxdna_hwctx *hwctx); diff --git a/drivers/accel/amdxdna/amdxdna_pci_drv.c b/drivers/accel/amdxdn= a/amdxdna_pci_drv.c index 030fac1075b2..49f0de12200a 100644 --- a/drivers/accel/amdxdna/amdxdna_pci_drv.c +++ b/drivers/accel/amdxdna/amdxdna_pci_drv.c @@ -143,6 +143,23 @@ static int amdxdna_flush(struct file *f, fl_owner_t id) return 0; } =20 +static int amdxdna_drm_get_info_ioctl(struct drm_device *dev, void *data, = struct drm_file *filp) +{ + struct amdxdna_client *client =3D filp->driver_priv; + struct amdxdna_dev *xdna =3D to_xdna_dev(dev); + struct amdxdna_drm_get_info *args =3D data; + int ret; + + if (!xdna->dev_info->ops->get_aie_info) + return -EOPNOTSUPP; + + XDNA_DBG(xdna, "Request parameter %u", args->param); + mutex_lock(&xdna->dev_lock); + ret =3D xdna->dev_info->ops->get_aie_info(client, args); + mutex_unlock(&xdna->dev_lock); + return ret; +} + static const struct drm_ioctl_desc amdxdna_drm_ioctls[] =3D { /* Context */ DRM_IOCTL_DEF_DRV(AMDXDNA_CREATE_HWCTX, amdxdna_drm_create_hwctx_ioctl, 0= ), @@ -155,6 +172,8 @@ static const struct drm_ioctl_desc amdxdna_drm_ioctls[]= =3D { /* Exectuion */ DRM_IOCTL_DEF_DRV(AMDXDNA_EXEC_CMD, amdxdna_drm_submit_cmd_ioctl, 0), DRM_IOCTL_DEF_DRV(AMDXDNA_WAIT_CMD, amdxdna_drm_wait_cmd_ioctl, 0), + /* AIE hardware */ + DRM_IOCTL_DEF_DRV(AMDXDNA_GET_INFO, amdxdna_drm_get_info_ioctl, 0), }; =20 static const struct file_operations amdxdna_fops =3D { diff --git a/drivers/accel/amdxdna/amdxdna_pci_drv.h b/drivers/accel/amdxdn= a/amdxdna_pci_drv.h index 01b516743a00..0e1f566f8ca8 100644 --- a/drivers/accel/amdxdna/amdxdna_pci_drv.h +++ b/drivers/accel/amdxdna/amdxdna_pci_drv.h @@ -17,7 +17,9 @@ =20 extern const struct drm_driver amdxdna_drm_drv; =20 +struct amdxdna_client; struct amdxdna_dev; +struct amdxdna_drm_get_info; struct amdxdna_gem_obj; struct amdxdna_hwctx; struct amdxdna_sched_job; @@ -38,6 +40,7 @@ struct amdxdna_dev_ops { void (*hwctx_resume)(struct amdxdna_hwctx *hwctx); int (*cmd_submit)(struct amdxdna_hwctx *hwctx, struct amdxdna_sched_job *= job, u64 *seq); int (*cmd_wait)(struct amdxdna_hwctx *hwctx, u64 seq, u32 timeout); + int (*get_aie_info)(struct amdxdna_client *client, struct amdxdna_drm_get= _info *args); }; =20 /* diff --git a/include/uapi/drm/amdxdna_accel.h b/include/uapi/drm/amdxdna_ac= cel.h index 08f3ec7146ab..a7e23c6de3da 100644 --- a/include/uapi/drm/amdxdna_accel.h +++ b/include/uapi/drm/amdxdna_accel.h @@ -32,6 +32,7 @@ enum amdxdna_drm_ioctl_id { DRM_AMDXDNA_SYNC_BO, DRM_AMDXDNA_EXEC_CMD, DRM_AMDXDNA_WAIT_CMD, + DRM_AMDXDNA_GET_INFO, }; =20 /** @@ -252,6 +253,167 @@ struct amdxdna_drm_wait_cmd { __u64 seq; }; =20 +/** + * struct amdxdna_drm_query_aie_status - Query the status of the AIE hardw= are + * @buffer: The user space buffer that will return the AIE status. + * @buffer_size: The size of the user space buffer. + * @cols_filled: A bitmap of AIE columns whose data has been returned in t= he buffer. + */ +struct amdxdna_drm_query_aie_status { + __u64 buffer; /* out */ + __u32 buffer_size; /* in */ + __u32 cols_filled; /* out */ +}; + +/** + * struct amdxdna_drm_query_aie_version - Query the version of the AIE har= dware + * @major: The major version number. + * @minor: The minor version number. + */ +struct amdxdna_drm_query_aie_version { + __u32 major; /* out */ + __u32 minor; /* out */ +}; + +/** + * struct amdxdna_drm_query_aie_tile_metadata - Query the metadata of AIE = tile (core, mem, shim) + * @row_count: The number of rows. + * @row_start: The starting row number. + * @dma_channel_count: The number of dma channels. + * @lock_count: The number of locks. + * @event_reg_count: The number of events. + * @pad: Structure padding. + */ +struct amdxdna_drm_query_aie_tile_metadata { + __u16 row_count; + __u16 row_start; + __u16 dma_channel_count; + __u16 lock_count; + __u16 event_reg_count; + __u16 pad[3]; +}; + +/** + * struct amdxdna_drm_query_aie_metadata - Query the metadata of the AIE h= ardware + * @col_size: The size of a column in bytes. + * @cols: The total number of columns. + * @rows: The total number of rows. + * @version: The version of the AIE hardware. + * @core: The metadata for all core tiles. + * @mem: The metadata for all mem tiles. + * @shim: The metadata for all shim tiles. + */ +struct amdxdna_drm_query_aie_metadata { + __u32 col_size; + __u16 cols; + __u16 rows; + struct amdxdna_drm_query_aie_version version; + struct amdxdna_drm_query_aie_tile_metadata core; + struct amdxdna_drm_query_aie_tile_metadata mem; + struct amdxdna_drm_query_aie_tile_metadata shim; +}; + +/** + * struct amdxdna_drm_query_clock - Metadata for a clock + * @name: The clock name. + * @freq_mhz: The clock frequency. + * @pad: Structure padding. + */ +struct amdxdna_drm_query_clock { + __u8 name[16]; + __u32 freq_mhz; + __u32 pad; +}; + +/** + * struct amdxdna_drm_query_clock_metadata - Query metadata for clocks + * @mp_npu_clock: The metadata for MP-NPU clock. + * @h_clock: The metadata for H clock. + */ +struct amdxdna_drm_query_clock_metadata { + struct amdxdna_drm_query_clock mp_npu_clock; + struct amdxdna_drm_query_clock h_clock; +}; + +enum amdxdna_sensor_type { + AMDXDNA_SENSOR_TYPE_POWER +}; + +/** + * struct amdxdna_drm_query_sensor - The data for single sensor. + * @label: The name for a sensor. + * @input: The current value of the sensor. + * @max: The maximum value possible for the sensor. + * @average: The average value of the sensor. + * @highest: The highest recorded sensor value for this driver load for th= e sensor. + * @status: The sensor status. + * @units: The sensor units. + * @unitm: Translates value member variables into the correct unit via (po= w(10, unitm) * value). + * @type: The sensor type from enum amdxdna_sensor_type. + * @pad: Structure padding. + */ +struct amdxdna_drm_query_sensor { + __u8 label[64]; + __u32 input; + __u32 max; + __u32 average; + __u32 highest; + __u8 status[64]; + __u8 units[16]; + __s8 unitm; + __u8 type; + __u8 pad[6]; +}; + +/** + * struct amdxdna_drm_query_hwctx - The data for single context. + * @context_id: The ID for this context. + * @start_col: The starting column for the partition assigned to this cont= ext. + * @num_col: The number of columns in the partition assigned to this conte= xt. + * @pad: Structure padding. + * @pid: The Process ID of the process that created this context. + * @command_submissions: The number of commands submitted to this context. + * @command_completions: The number of commands completed by this context. + * @migrations: The number of times this context has been moved to a diffe= rent partition. + * @preemptions: The number of times this context has been preempted by an= other context in the + * same partition. + * @errors: The errors for this context. + */ +struct amdxdna_drm_query_hwctx { + __u32 context_id; + __u32 start_col; + __u32 num_col; + __u32 pad; + __s64 pid; + __u64 command_submissions; + __u64 command_completions; + __u64 migrations; + __u64 preemptions; + __u64 errors; +}; + +enum amdxdna_drm_get_param { + DRM_AMDXDNA_QUERY_AIE_STATUS, + DRM_AMDXDNA_QUERY_AIE_METADATA, + DRM_AMDXDNA_QUERY_AIE_VERSION, + DRM_AMDXDNA_QUERY_CLOCK_METADATA, + DRM_AMDXDNA_QUERY_SENSORS, + DRM_AMDXDNA_QUERY_HW_CONTEXTS, + DRM_AMDXDNA_NUM_GET_PARAM, +}; + +/** + * struct amdxdna_drm_get_info - Get some information from the AIE hardwar= e. + * @param: Value in enum amdxdna_drm_get_param. Specifies the structure pa= ssed in the buffer. + * @buffer_size: Size of the input buffer. Size needed/written by the kern= el. + * @buffer: A structure specified by the param struct member. + */ +struct amdxdna_drm_get_info { + __u32 param; /* in */ + __u32 buffer_size; /* in/out */ + __u64 buffer; /* in/out */ +}; + #define DRM_IOCTL_AMDXDNA_CREATE_HWCTX \ DRM_IOWR(DRM_COMMAND_BASE + DRM_AMDXDNA_CREATE_HWCTX, \ struct amdxdna_drm_create_hwctx) @@ -284,6 +446,10 @@ struct amdxdna_drm_wait_cmd { DRM_IOWR(DRM_COMMAND_BASE + DRM_AMDXDNA_WAIT_CMD, \ struct amdxdna_drm_wait_cmd) =20 +#define DRM_IOCTL_AMDXDNA_GET_INFO \ + DRM_IOWR(DRM_COMMAND_BASE + DRM_AMDXDNA_GET_INFO, \ + struct amdxdna_drm_get_info) + #if defined(__cplusplus) } /* extern c end */ #endif --=20 2.34.1