فهرست منبع

msm: eva: Update WarpNCC-related UAPI

Update UAPI for future backward compatibility.
Add mechanism to dynamically specify WarpNCC
metadata buffer offset instead of using macro.
Add UMD-KMD shared definitions header file.

Change-Id: If8ea7046e692eef1a784d2744228846b6f752d0d
Signed-off-by: Sabharsh Sidhu <[email protected]>
Signed-off-by: George Shen <[email protected]>
Sabharsh Sidhu 2 سال پیش
والد
کامیت
28d5691237
4فایلهای تغییر یافته به همراه134 افزوده شده و 79 حذف شده
  1. 1 67
      include/uapi/eva/media/msm_eva_private.h
  2. 86 0
      msm/eva/eva_shared_def.h
  3. 1 0
      msm/eva/msm_cvp.h
  4. 46 12
      msm/eva/msm_cvp_buf.c

+ 1 - 67
include/uapi/eva/media/msm_eva_private.h

@@ -119,72 +119,6 @@ struct eva_kmd_client_data {
 	__u32 client_data1;
 	__u32 client_data2;
 };
-struct cvp_buf_type {
-	__s32 fd;
-	__u32 size;
-	__u32 offset;
-	__u32 flags;
-	__u32 reserved1;
-	__u32 reserved2;
-	__u32 fence_type;
-	__u32 input_handle;
-	__u32 output_handle;
-	__u32 debug_flags;
-	__u32 crc;
-};
-
-/**
- * Structures and macros for Out-of-Band (OOB) buffer
- * that may accompany HFI packet data
- */
-
-#define EVA_KMD_WNCC_MAX_LAYERS               4
-#define EVA_KMD_WNCC_MAX_ADDRESSES            4095
-#define EVA_KMD_WNCC_MAX_SRC_BUFS             2400
-#define EVA_KMD_WNCC_SRC_BUF_ID_OFFSET        1
-
-/**
- * Macro to get Meta Data Buffer Offset from the HFI Packet
- * The number 15 denotes the position of the first Meta Data Buffer with respect to other fields
- * If the WARPNCC HFI Frame Packet changes, this macro definition also has to be revised
- */
-
-#define EVA_KMD_WNCC_HFI_METADATA_BUFS_OFFSET (15 + sizeof(struct cvp_buf_type) / sizeof(__u32) * 5)
-
-struct eva_kmd_wncc_metadata {
-	__u64 loc_x_dec   : 12;
-	__u64 loc_x_frac  : 9;
-	__u64 loc_y_dec   : 12;
-	__u64 loc_y_frac  : 9;
-	__u64 iova_lsb    : 22; /* Populated in KMD */
-	__u64 iova_msb    : 10; /* Populated in KMD */
-	__u64 scale_idx   : 2;
-	__s64 aff_coeff_3 : 13;
-	__s64 aff_coeff_2 : 13;
-	__s64 aff_coeff_1 : 13;
-	__s64 aff_coeff_0 : 13;
-};
-
-struct eva_kmd_oob_wncc {
-	__u32 num_layers;
-	struct eva_kmd_wncc_layer {
-		__u32 num_addrs;
-		struct eva_kmd_wncc_addr {
-			__u32 buffer_id;
-			__u32 offset;
-		} addrs[EVA_KMD_WNCC_MAX_ADDRESSES];
-	} layers[EVA_KMD_WNCC_MAX_LAYERS];
-};
-
-#define EVA_KMD_OOB_INVALID 0
-#define EVA_KMD_OOB_WNCC    1
-
-struct eva_kmd_oob_buf {
-	__u32 oob_type;
-	union {
-		struct eva_kmd_oob_wncc wncc;
-	};
-};
 
 /**
  * Structures and macros for KMD arg data
@@ -194,7 +128,7 @@ struct eva_kmd_oob_buf {
 
 struct eva_kmd_hfi_packet {
 	__u32 pkt_data[MAX_HFI_PKT_SIZE];
-	struct eva_kmd_oob_buf *oob_buf;
+	void *oob_buf;
 };
 
 #define EVA_KMD_PROP_HFI_VERSION	1

+ 86 - 0
msm/eva/eva_shared_def.h

@@ -0,0 +1,86 @@
+/**
+ * SPDX-License-Identifier: GPL-2.0-only
+ *
+ * Copyright (c) 2018-2021, The Linux Foundation. All rights reserved.
+ * Copyright (c) 2023 Qualcomm Innovation Center, Inc. All rights reserved.
+ */
+
+/**
+ * This file contains definitions that are common to UMD and KMD
+ * but shall not be added to the UAPI to allow for better UAPI
+ * backward compatibility. Identical copies of this file must be
+ * used by both UMD and KMD for desired functioning.
+ */
+
+#ifndef _EVA_SHARED_DEF_H_
+#define _EVA_SHARED_DEF_H_
+
+/**
+ * Structure corresponding to HFI_CVP_BUFFER_TYPE
+ */
+
+struct cvp_buf_type {
+	__s32 fd;
+	__u32 size;
+	__u32 offset;
+	__u32 flags;
+	__u32 reserved1;
+	__u32 reserved2;
+	__u32 fence_type;
+	__u32 input_handle;
+	__u32 output_handle;
+	__u32 debug_flags;
+	__u32 crc;
+};
+
+/**
+ * Structures and macros for Warp-NCC Out-of-Band (OOB) buffer
+ */
+
+#define EVA_KMD_WNCC_MAX_LAYERS               4
+#define EVA_KMD_WNCC_MAX_ADDRESSES            4095
+#define EVA_KMD_WNCC_MAX_SRC_BUFS             2400
+#define EVA_KMD_WNCC_SRC_BUF_ID_OFFSET        1
+
+struct eva_kmd_wncc_metadata {
+	__u64 loc_x_dec : 12;
+	__u64 loc_x_frac : 9;
+	__u64 loc_y_dec : 12;
+	__u64 loc_y_frac : 9;
+	__u64 iova_lsb : 22; /* Populated in KMD */
+	__u64 iova_msb : 10; /* Populated in KMD */
+	__u64 scale_idx : 2;
+	__s64 aff_coeff_3 : 13;
+	__s64 aff_coeff_2 : 13;
+	__s64 aff_coeff_1 : 13;
+	__s64 aff_coeff_0 : 13;
+};
+
+struct eva_kmd_oob_wncc {
+	__u32 metadata_bufs_offset;
+	__u32 num_layers;
+	struct eva_kmd_wncc_layer {
+		__u32 num_addrs;
+		struct eva_kmd_wncc_addr {
+			__u32 buffer_id;
+			__u32 offset;
+		} addrs[EVA_KMD_WNCC_MAX_ADDRESSES];
+	} layers[EVA_KMD_WNCC_MAX_LAYERS];
+};
+
+/**
+ * Structure and macros for Out-of-Band (OOB) buffer
+ * that may accompany HFI packet data
+ */
+
+#define EVA_KMD_OOB_INVALID 0
+#define EVA_KMD_OOB_WNCC    1
+
+struct eva_kmd_oob_buf {
+	__u32 oob_type;
+	union {
+		struct eva_kmd_oob_wncc wncc;
+	};
+};
+
+#endif

+ 1 - 0
msm/eva/msm_cvp.h

@@ -11,6 +11,7 @@
 #include "msm_cvp_clocks.h"
 #include "msm_cvp_debug.h"
 #include "msm_cvp_dsp.h"
+#include "eva_shared_def.h"
 
 static inline bool is_buf_param_valid(u32 buf_num, u32 offset)
 {

+ 46 - 12
msm/eva/msm_cvp_buf.c

@@ -15,6 +15,7 @@
 #include "msm_cvp_debug.h"
 #include "msm_cvp_core.h"
 #include "msm_cvp_dsp.h"
+#include "eva_shared_def.h"
 
 #if (LINUX_VERSION_CODE < KERNEL_VERSION(5, 16, 0))
 #define eva_buf_map dma_buf_map
@@ -42,7 +43,8 @@
 
 static void _wncc_print_cvpwnccbufs_table(struct msm_cvp_inst* inst);
 static int _wncc_unmap_metadata_bufs(struct eva_kmd_hfi_packet* in_pkt,
-	unsigned int num_layers, struct eva_kmd_wncc_metadata** wncc_metadata);
+	unsigned int num_layers, unsigned int metadata_bufs_offset,
+	struct eva_kmd_wncc_metadata** wncc_metadata);
 
 void msm_cvp_print_inst_bufs(struct msm_cvp_inst *inst, bool log);
 
@@ -750,6 +752,7 @@ static int _wncc_copy_oob_from_user(struct eva_kmd_hfi_packet* in_pkt,
 {
 	int rc = 0;
 	u32 oob_type;
+	struct eva_kmd_oob_buf* oob_buf_u;
 	struct eva_kmd_oob_wncc* wncc_oob_u;
 	struct eva_kmd_oob_wncc* wncc_oob_k;
 	unsigned int i;
@@ -760,12 +763,13 @@ static int _wncc_copy_oob_from_user(struct eva_kmd_hfi_packet* in_pkt,
 		return -EINVAL;
 	}
 
-	if (!access_ok(in_pkt->oob_buf, sizeof(*in_pkt->oob_buf))) {
+	oob_buf_u = in_pkt->oob_buf;
+	if (!access_ok(oob_buf_u, sizeof(*oob_buf_u))) {
 		dprintk(CVP_ERR, "%s: invalid OOB buf pointer", __func__);
 		return -EINVAL;
 	}
 
-	rc = get_user(oob_type, &in_pkt->oob_buf->oob_type);
+	rc = get_user(oob_type, &oob_buf_u->oob_type);
 	if (rc)
 		return rc;
 	if (oob_type != EVA_KMD_OOB_WNCC) {
@@ -774,9 +778,20 @@ static int _wncc_copy_oob_from_user(struct eva_kmd_hfi_packet* in_pkt,
 		return -EINVAL;
 	}
 
-	wncc_oob_u = &in_pkt->oob_buf->wncc;
+	wncc_oob_u = &oob_buf_u->wncc;
 	wncc_oob_k = wncc_oob;
 
+	rc = get_user(wncc_oob_k->metadata_bufs_offset,
+		&wncc_oob_u->metadata_bufs_offset);
+	if (rc)
+		return rc;
+	if (wncc_oob_k->metadata_bufs_offset > ((sizeof(in_pkt->pkt_data)
+		- sizeof(struct cvp_buf_type)) / sizeof(__u32))) {
+		dprintk(CVP_ERR, "%s: invalid wncc metadata bufs offset",
+			__func__);
+		return -EINVAL;
+	}
+
 	rc = get_user(wncc_oob_k->num_layers, &wncc_oob_u->num_layers);
 	if (rc)
 		return rc;
@@ -817,7 +832,8 @@ static int _wncc_copy_oob_from_user(struct eva_kmd_hfi_packet* in_pkt,
 }
 
 static int _wncc_map_metadata_bufs(struct eva_kmd_hfi_packet* in_pkt,
-	unsigned int num_layers, struct eva_kmd_wncc_metadata** wncc_metadata)
+	unsigned int num_layers, unsigned int metadata_bufs_offset,
+	struct eva_kmd_wncc_metadata** wncc_metadata)
 {
 	int rc = 0, i;
 	struct cvp_buf_type* wncc_metadata_bufs;
@@ -829,9 +845,15 @@ static int _wncc_map_metadata_bufs(struct eva_kmd_hfi_packet* in_pkt,
 		dprintk(CVP_ERR, "%s: invalid params", __func__);
 		return -EINVAL;
 	}
+	if (metadata_bufs_offset > ((sizeof(in_pkt->pkt_data)
+		- sizeof(struct cvp_buf_type)) / sizeof(__u32))) {
+		dprintk(CVP_ERR, "%s: invalid wncc metadata bufs offset",
+			__func__);
+		return -EINVAL;
+	}
 
 	wncc_metadata_bufs = (struct cvp_buf_type*)
-		&in_pkt->pkt_data[EVA_KMD_WNCC_HFI_METADATA_BUFS_OFFSET];
+		&in_pkt->pkt_data[metadata_bufs_offset];
 	for (i = 0; i < num_layers; i++) {
 		dmabuf = dma_buf_get(wncc_metadata_bufs[i].fd);
 		if (IS_ERR(dmabuf)) {
@@ -872,13 +894,15 @@ static int _wncc_map_metadata_bufs(struct eva_kmd_hfi_packet* in_pkt,
 	}
 
 	if (rc)
-		_wncc_unmap_metadata_bufs(in_pkt, i, wncc_metadata);
+		_wncc_unmap_metadata_bufs(in_pkt, i, metadata_bufs_offset,
+			wncc_metadata);
 
 	return rc;
 }
 
 static int _wncc_unmap_metadata_bufs(struct eva_kmd_hfi_packet* in_pkt,
-	unsigned int num_layers, struct eva_kmd_wncc_metadata** wncc_metadata)
+	unsigned int num_layers, unsigned int metadata_bufs_offset,
+	struct eva_kmd_wncc_metadata** wncc_metadata)
 {
 	int rc = 0, i;
 	struct cvp_buf_type* wncc_metadata_bufs;
@@ -890,9 +914,15 @@ static int _wncc_unmap_metadata_bufs(struct eva_kmd_hfi_packet* in_pkt,
 		dprintk(CVP_ERR, "%s: invalid params", __func__);
 		return -EINVAL;
 	}
+	if (metadata_bufs_offset > ((sizeof(in_pkt->pkt_data)
+		- sizeof(struct cvp_buf_type)) / sizeof(__u32))) {
+		dprintk(CVP_ERR, "%s: invalid wncc metadata bufs offset",
+			__func__);
+		return -EINVAL;
+	}
 
 	wncc_metadata_bufs = (struct cvp_buf_type*)
-		&in_pkt->pkt_data[EVA_KMD_WNCC_HFI_METADATA_BUFS_OFFSET];
+		&in_pkt->pkt_data[metadata_bufs_offset];
 	for (i = 0; i < num_layers; i++) {
 		if (!wncc_metadata[i]) {
 			rc = -EINVAL;
@@ -944,8 +974,10 @@ static int msm_cvp_proc_oob_wncc(struct msm_cvp_inst* inst,
 
 	wncc_oob = (struct eva_kmd_oob_wncc*)kzalloc(
 		sizeof(struct eva_kmd_oob_wncc), GFP_KERNEL);
-	if (!wncc_oob)
+	if (!wncc_oob) {
+		dprintk(CVP_ERR, "%s: OOB buf allocation failed", __func__);
 		return -ENOMEM;
+	}
 	rc = _wncc_copy_oob_from_user(in_pkt, wncc_oob);
 	if (rc) {
 		dprintk(CVP_ERR, "%s: OOB buf copying failed", __func__);
@@ -953,7 +985,8 @@ static int msm_cvp_proc_oob_wncc(struct msm_cvp_inst* inst,
 	}
 
 	rc = _wncc_map_metadata_bufs(in_pkt,
-		wncc_oob->num_layers, wncc_metadata);
+		wncc_oob->num_layers, wncc_oob->metadata_bufs_offset,
+		wncc_metadata);
 	if (rc) {
 		dprintk(CVP_ERR, "%s: failed to map wncc metadata bufs",
 			__func__);
@@ -1022,7 +1055,8 @@ static int msm_cvp_proc_oob_wncc(struct msm_cvp_inst* inst,
 			wncc_oob->layers[0].num_addrs, wncc_metadata);
 
 	if (_wncc_unmap_metadata_bufs(in_pkt,
-		wncc_oob->num_layers, wncc_metadata)) {
+		wncc_oob->num_layers, wncc_oob->metadata_bufs_offset,
+		wncc_metadata)) {
 		dprintk(CVP_ERR, "%s: failed to unmap wncc metadata bufs",
 			__func__);
 	}