video: driver: packetize dynamic controls with buffer
packetize dynamic controls set via request api along with corresponding input buffer under the same hfi header and queue to FW. Change-Id: I8bf82f7ccb1ab16c42ce02189a208f5f7cb8dc70 Signed-off-by: Darshana Patil <quic_darshana@quicinc.com>
This commit is contained in:
@@ -144,6 +144,7 @@ struct msm_vidc_inst {
|
|||||||
struct list_head caps_list;
|
struct list_head caps_list;
|
||||||
struct list_head children_list;
|
struct list_head children_list;
|
||||||
struct list_head firmware_list;
|
struct list_head firmware_list;
|
||||||
|
struct list_head pending_pkts; /* list of struct hfi_pending_packet */
|
||||||
bool once_per_session_set;
|
bool once_per_session_set;
|
||||||
bool ipsc_properties_set;
|
bool ipsc_properties_set;
|
||||||
bool opsc_properties_set;
|
bool opsc_properties_set;
|
||||||
|
@@ -11,6 +11,8 @@
|
|||||||
struct msm_vidc_core;
|
struct msm_vidc_core;
|
||||||
struct msm_vidc_inst;
|
struct msm_vidc_inst;
|
||||||
|
|
||||||
|
#define MSM_MEM_POOL_PACKET_SIZE 1024
|
||||||
|
|
||||||
struct msm_memory_dmabuf {
|
struct msm_memory_dmabuf {
|
||||||
struct list_head list;
|
struct list_head list;
|
||||||
struct dma_buf *dmabuf;
|
struct dma_buf *dmabuf;
|
||||||
@@ -23,6 +25,7 @@ enum msm_memory_pool_type {
|
|||||||
MSM_MEM_POOL_ALLOC,
|
MSM_MEM_POOL_ALLOC,
|
||||||
MSM_MEM_POOL_TIMESTAMP,
|
MSM_MEM_POOL_TIMESTAMP,
|
||||||
MSM_MEM_POOL_DMABUF,
|
MSM_MEM_POOL_DMABUF,
|
||||||
|
MSM_MEM_POOL_PACKET,
|
||||||
MSM_MEM_POOL_MAX,
|
MSM_MEM_POOL_MAX,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@@ -28,6 +28,11 @@ struct vidc_buffer_addr_info {
|
|||||||
u32 response_required;
|
u32 response_required;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct hfi_pending_packet {
|
||||||
|
struct list_head list;
|
||||||
|
void *data;
|
||||||
|
};
|
||||||
|
|
||||||
int venus_hfi_session_property(struct msm_vidc_inst *inst,
|
int venus_hfi_session_property(struct msm_vidc_inst *inst,
|
||||||
u32 pkt_type, u32 flags, u32 port,
|
u32 pkt_type, u32 flags, u32 port,
|
||||||
u32 payload_type, void *payload, u32 payload_size);
|
u32 payload_type, void *payload, u32 payload_size);
|
||||||
|
@@ -945,6 +945,7 @@ void *msm_vidc_open(void *vidc_core, u32 session_type)
|
|||||||
INIT_LIST_HEAD(&inst->firmware_list);
|
INIT_LIST_HEAD(&inst->firmware_list);
|
||||||
INIT_LIST_HEAD(&inst->enc_input_crs);
|
INIT_LIST_HEAD(&inst->enc_input_crs);
|
||||||
INIT_LIST_HEAD(&inst->dmabuf_tracker);
|
INIT_LIST_HEAD(&inst->dmabuf_tracker);
|
||||||
|
INIT_LIST_HEAD(&inst->pending_pkts);
|
||||||
for (i = 0; i < MAX_SIGNAL; i++)
|
for (i = 0; i < MAX_SIGNAL; i++)
|
||||||
init_completion(&inst->completions[i]);
|
init_completion(&inst->completions[i]);
|
||||||
|
|
||||||
|
@@ -945,14 +945,6 @@ int msm_v4l2_op_s_ctrl(struct v4l2_ctrl *ctrl)
|
|||||||
kfree(curr_node);
|
kfree(curr_node);
|
||||||
}
|
}
|
||||||
|
|
||||||
/* dynamic controls with request will be set along with qbuf */
|
|
||||||
if (inst->request) {
|
|
||||||
i_vpr_l(inst,
|
|
||||||
"%s: request api enabled, dynamic ctrls to be set with qbuf\n",
|
|
||||||
__func__);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Dynamic set control ASAP */
|
/* Dynamic set control ASAP */
|
||||||
rc = msm_vidc_set_v4l2_properties(inst);
|
rc = msm_vidc_set_v4l2_properties(inst);
|
||||||
if (rc) {
|
if (rc) {
|
||||||
|
@@ -17,6 +17,7 @@
|
|||||||
#include "msm_vidc_dt.h"
|
#include "msm_vidc_dt.h"
|
||||||
#include "msm_vidc_core.h"
|
#include "msm_vidc_core.h"
|
||||||
#include "msm_vidc_events.h"
|
#include "msm_vidc_events.h"
|
||||||
|
#include "venus_hfi.h"
|
||||||
|
|
||||||
struct msm_vidc_buf_region_name {
|
struct msm_vidc_buf_region_name {
|
||||||
enum msm_vidc_buffer_region region;
|
enum msm_vidc_buffer_region region;
|
||||||
@@ -589,6 +590,8 @@ static struct msm_vidc_type_size_name buftype_size_name_arr[] = {
|
|||||||
{MSM_MEM_POOL_ALLOC, sizeof(struct msm_vidc_alloc), "MSM_MEM_POOL_ALLOC" },
|
{MSM_MEM_POOL_ALLOC, sizeof(struct msm_vidc_alloc), "MSM_MEM_POOL_ALLOC" },
|
||||||
{MSM_MEM_POOL_TIMESTAMP, sizeof(struct msm_vidc_timestamp), "MSM_MEM_POOL_TIMESTAMP" },
|
{MSM_MEM_POOL_TIMESTAMP, sizeof(struct msm_vidc_timestamp), "MSM_MEM_POOL_TIMESTAMP" },
|
||||||
{MSM_MEM_POOL_DMABUF, sizeof(struct msm_memory_dmabuf), "MSM_MEM_POOL_DMABUF" },
|
{MSM_MEM_POOL_DMABUF, sizeof(struct msm_memory_dmabuf), "MSM_MEM_POOL_DMABUF" },
|
||||||
|
{MSM_MEM_POOL_PACKET, sizeof(struct hfi_pending_packet) + MSM_MEM_POOL_PACKET_SIZE,
|
||||||
|
"MSM_MEM_POOL_PACKET"},
|
||||||
};
|
};
|
||||||
|
|
||||||
int msm_memory_pools_init(struct msm_vidc_inst *inst)
|
int msm_memory_pools_init(struct msm_vidc_inst *inst)
|
||||||
|
@@ -3047,6 +3047,43 @@ unlock:
|
|||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int venus_hfi_cache_packet(struct msm_vidc_inst *inst)
|
||||||
|
{
|
||||||
|
int rc = 0;
|
||||||
|
struct hfi_header *hdr;
|
||||||
|
struct hfi_pending_packet *packet;
|
||||||
|
|
||||||
|
if (!inst->packet) {
|
||||||
|
d_vpr_e("%s: invalid params\n", __func__);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
hdr = (struct hfi_header *)inst->packet;
|
||||||
|
if (hdr->size < sizeof(struct hfi_header)) {
|
||||||
|
d_vpr_e("%s: invalid hdr size %d\n", __func__, hdr->size);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
packet = msm_memory_pool_alloc(inst, MSM_MEM_POOL_PACKET);
|
||||||
|
if (!packet) {
|
||||||
|
i_vpr_e(inst, "%s: failed to allocate pending packet\n", __func__);
|
||||||
|
return -ENOMEM;
|
||||||
|
}
|
||||||
|
|
||||||
|
INIT_LIST_HEAD(&packet->list);
|
||||||
|
list_add_tail(&packet->list, &inst->pending_pkts);
|
||||||
|
packet->data = (u8 *)packet + sizeof(struct hfi_pending_packet);
|
||||||
|
|
||||||
|
if (hdr->size > MSM_MEM_POOL_PACKET_SIZE) {
|
||||||
|
i_vpr_e(inst, "%s: header size %d exceeds pool packet size %d\n",
|
||||||
|
__func__, hdr->size, MSM_MEM_POOL_PACKET_SIZE);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
memcpy(packet->data, inst->packet, hdr->size);
|
||||||
|
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
int venus_hfi_session_property(struct msm_vidc_inst *inst,
|
int venus_hfi_session_property(struct msm_vidc_inst *inst,
|
||||||
u32 pkt_type, u32 flags, u32 port, u32 payload_type,
|
u32 pkt_type, u32 flags, u32 port, u32 payload_type,
|
||||||
void *payload, u32 payload_size)
|
void *payload, u32 payload_size)
|
||||||
@@ -3081,6 +3118,12 @@ int venus_hfi_session_property(struct msm_vidc_inst *inst,
|
|||||||
if (rc)
|
if (rc)
|
||||||
goto unlock;
|
goto unlock;
|
||||||
|
|
||||||
|
/* skip sending packet to firmware */
|
||||||
|
if (inst->request) {
|
||||||
|
rc = venus_hfi_cache_packet(inst);
|
||||||
|
goto unlock;
|
||||||
|
}
|
||||||
|
|
||||||
rc = __iface_cmdq_write(inst->core, inst->packet);
|
rc = __iface_cmdq_write(inst->core, inst->packet);
|
||||||
if (rc)
|
if (rc)
|
||||||
goto unlock;
|
goto unlock;
|
||||||
@@ -3381,6 +3424,48 @@ unlock:
|
|||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int venus_hfi_add_pending_packets(struct msm_vidc_inst *inst)
|
||||||
|
{
|
||||||
|
int rc = 0;
|
||||||
|
int num_packets = 0;
|
||||||
|
struct hfi_pending_packet *pkt_info, *dummy;
|
||||||
|
struct hfi_header *hdr, *src_hdr;
|
||||||
|
struct hfi_packet *src_pkt;
|
||||||
|
|
||||||
|
if (!inst || !inst->packet) {
|
||||||
|
d_vpr_e("%s: invalid params\n", __func__);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
hdr = (struct hfi_header *)inst->packet;
|
||||||
|
if (hdr->size < sizeof(struct hfi_header)) {
|
||||||
|
i_vpr_e(inst, "%s: invalid hdr size %d\n",
|
||||||
|
__func__, hdr->size);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
|
||||||
|
list_for_each_entry_safe(pkt_info, dummy, &inst->pending_pkts, list) {
|
||||||
|
src_hdr = (struct hfi_header *)(pkt_info->data);
|
||||||
|
num_packets = src_hdr->num_packets;
|
||||||
|
src_pkt = (struct hfi_packet *)((u8 *)src_hdr + sizeof(struct hfi_header));
|
||||||
|
while (num_packets > 0) {
|
||||||
|
memcpy((u8 *)hdr + hdr->size, (void *)src_pkt, src_pkt->size);
|
||||||
|
hdr->num_packets++;
|
||||||
|
hdr->size += src_pkt->size;
|
||||||
|
num_packets--;
|
||||||
|
src_pkt = (struct hfi_packet *)((u8 *)src_pkt + src_pkt->size);
|
||||||
|
if ((u8 *)src_pkt < (u8 *)src_hdr ||
|
||||||
|
(u8 *)src_pkt > (u8 *)src_hdr + hdr->size) {
|
||||||
|
i_vpr_e(inst, "%s: invalid packet address\n", __func__);
|
||||||
|
return -EINVAL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
list_del(&pkt_info->list);
|
||||||
|
msm_memory_pool_free(inst, pkt_info);
|
||||||
|
}
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
int venus_hfi_queue_buffer(struct msm_vidc_inst *inst,
|
int venus_hfi_queue_buffer(struct msm_vidc_inst *inst,
|
||||||
struct msm_vidc_buffer *buffer, struct msm_vidc_buffer *metabuf)
|
struct msm_vidc_buffer *buffer, struct msm_vidc_buffer *metabuf)
|
||||||
{
|
{
|
||||||
@@ -3438,6 +3523,10 @@ int venus_hfi_queue_buffer(struct msm_vidc_inst *inst,
|
|||||||
goto unlock;
|
goto unlock;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
rc = venus_hfi_add_pending_packets(inst);
|
||||||
|
if (rc)
|
||||||
|
goto unlock;
|
||||||
|
|
||||||
rc = __iface_cmdq_write(inst->core, inst->packet);
|
rc = __iface_cmdq_write(inst->core, inst->packet);
|
||||||
if (rc)
|
if (rc)
|
||||||
goto unlock;
|
goto unlock;
|
||||||
|
Reference in New Issue
Block a user