media: iris: Add V4L2 streaming support for encoder video device

Add support for V4L2 streaming operations on the encoder video device.
During stream-on, configure mandatory properties on the respective
planes and notify the firmware to initiate an encode session.

Tested-by: Vikash Garodia <quic_vgarodia@quicinc.com> # X1E80100
Reviewed-by: Vikash Garodia <quic_vgarodia@quicinc.com>
Tested-by: Neil Armstrong <neil.armstrong@linaro.org> # on SM8550-HDK
Tested-by: Neil Armstrong <neil.armstrong@linaro.org> # on SM8650-HDK
Signed-off-by: Dikshita Agarwal <quic_dikshita@quicinc.com>
Tested-by: Bryan O'Donoghue <bryan.odonoghue@linaro.org> # x1e80100-crd
[bod: add sm8750 enc/dec declarations during merge process]
Signed-off-by: Bryan O'Donoghue <bod@kernel.org>
Signed-off-by: Hans Verkuil <hverkuil+cisco@kernel.org>
This commit is contained in:
Dikshita Agarwal 2025-08-25 12:30:46 +05:30 committed by Hans Verkuil
parent 6bdfa3f947
commit 92e007ca5a
17 changed files with 790 additions and 410 deletions

View File

@ -1,5 +1,5 @@
qcom-iris-objs += \ qcom-iris-objs += iris_buffer.o \
iris_buffer.o \ iris_common.o \
iris_core.o \ iris_core.o \
iris_ctrls.o \ iris_ctrls.o \
iris_firmware.o \ iris_firmware.o \

View File

@ -0,0 +1,196 @@
// SPDX-License-Identifier: GPL-2.0-only
/*
* Copyright (c) 2022-2025 Qualcomm Innovation Center, Inc. All rights reserved.
*/
#include <media/v4l2-mem2mem.h>
#include "iris_common.h"
#include "iris_ctrls.h"
#include "iris_instance.h"
#include "iris_power.h"
int iris_process_streamon_input(struct iris_inst *inst)
{
const struct iris_hfi_command_ops *hfi_ops = inst->core->hfi_ops;
enum iris_inst_sub_state set_sub_state = 0;
int ret;
iris_scale_power(inst);
ret = hfi_ops->session_start(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
if (inst->sub_state & IRIS_INST_SUB_INPUT_PAUSE) {
ret = iris_inst_change_sub_state(inst, IRIS_INST_SUB_INPUT_PAUSE, 0);
if (ret)
return ret;
}
if (inst->domain == DECODER &&
(inst->sub_state & IRIS_INST_SUB_DRC ||
inst->sub_state & IRIS_INST_SUB_DRAIN ||
inst->sub_state & IRIS_INST_SUB_FIRST_IPSC)) {
if (!(inst->sub_state & IRIS_INST_SUB_INPUT_PAUSE)) {
if (hfi_ops->session_pause) {
ret = hfi_ops->session_pause(inst,
V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
}
set_sub_state = IRIS_INST_SUB_INPUT_PAUSE;
}
}
ret = iris_inst_state_change_streamon(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
inst->last_buffer_dequeued = false;
return iris_inst_change_sub_state(inst, 0, set_sub_state);
}
int iris_process_streamon_output(struct iris_inst *inst)
{
const struct iris_hfi_command_ops *hfi_ops = inst->core->hfi_ops;
bool drain_active = false, drc_active = false;
enum iris_inst_sub_state clear_sub_state = 0;
int ret = 0;
iris_scale_power(inst);
drain_active = inst->sub_state & IRIS_INST_SUB_DRAIN &&
inst->sub_state & IRIS_INST_SUB_DRAIN_LAST;
drc_active = inst->sub_state & IRIS_INST_SUB_DRC &&
inst->sub_state & IRIS_INST_SUB_DRC_LAST;
if (drc_active)
clear_sub_state = IRIS_INST_SUB_DRC | IRIS_INST_SUB_DRC_LAST;
else if (drain_active)
clear_sub_state = IRIS_INST_SUB_DRAIN | IRIS_INST_SUB_DRAIN_LAST;
if (inst->domain == DECODER && inst->sub_state & IRIS_INST_SUB_INPUT_PAUSE) {
ret = iris_alloc_and_queue_input_int_bufs(inst);
if (ret)
return ret;
ret = iris_set_stage(inst, STAGE);
if (ret)
return ret;
ret = iris_set_pipe(inst, PIPE);
if (ret)
return ret;
}
if (inst->state == IRIS_INST_INPUT_STREAMING &&
inst->sub_state & IRIS_INST_SUB_INPUT_PAUSE) {
if (!drain_active)
ret = hfi_ops->session_resume_drc(inst,
V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
else if (hfi_ops->session_resume_drain)
ret = hfi_ops->session_resume_drain(inst,
V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
clear_sub_state |= IRIS_INST_SUB_INPUT_PAUSE;
}
if (inst->sub_state & IRIS_INST_SUB_FIRST_IPSC)
clear_sub_state |= IRIS_INST_SUB_FIRST_IPSC;
ret = hfi_ops->session_start(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
if (ret)
return ret;
if (inst->sub_state & IRIS_INST_SUB_OUTPUT_PAUSE)
clear_sub_state |= IRIS_INST_SUB_OUTPUT_PAUSE;
ret = iris_inst_state_change_streamon(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
if (ret)
return ret;
inst->last_buffer_dequeued = false;
return iris_inst_change_sub_state(inst, clear_sub_state, 0);
}
static void iris_flush_deferred_buffers(struct iris_inst *inst,
enum iris_buffer_type type)
{
struct v4l2_m2m_ctx *m2m_ctx = inst->m2m_ctx;
struct v4l2_m2m_buffer *buffer, *n;
struct iris_buffer *buf;
if (type == BUF_INPUT) {
v4l2_m2m_for_each_src_buf_safe(m2m_ctx, buffer, n) {
buf = to_iris_buffer(&buffer->vb);
if (buf->attr & BUF_ATTR_DEFERRED) {
if (!(buf->attr & BUF_ATTR_BUFFER_DONE)) {
buf->attr |= BUF_ATTR_BUFFER_DONE;
buf->data_size = 0;
iris_vb2_buffer_done(inst, buf);
}
}
}
} else {
v4l2_m2m_for_each_dst_buf_safe(m2m_ctx, buffer, n) {
buf = to_iris_buffer(&buffer->vb);
if (buf->attr & BUF_ATTR_DEFERRED) {
if (!(buf->attr & BUF_ATTR_BUFFER_DONE)) {
buf->attr |= BUF_ATTR_BUFFER_DONE;
buf->data_size = 0;
iris_vb2_buffer_done(inst, buf);
}
}
}
}
}
static void iris_kill_session(struct iris_inst *inst)
{
const struct iris_hfi_command_ops *hfi_ops = inst->core->hfi_ops;
if (!inst->session_id)
return;
hfi_ops->session_close(inst);
iris_inst_change_state(inst, IRIS_INST_ERROR);
}
int iris_session_streamoff(struct iris_inst *inst, u32 plane)
{
const struct iris_hfi_command_ops *hfi_ops = inst->core->hfi_ops;
enum iris_buffer_type buffer_type;
int ret;
switch (plane) {
case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
buffer_type = BUF_INPUT;
break;
case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
buffer_type = BUF_OUTPUT;
break;
default:
return -EINVAL;
}
ret = hfi_ops->session_stop(inst, plane);
if (ret)
goto error;
ret = iris_inst_state_change_streamoff(inst, plane);
if (ret)
goto error;
iris_flush_deferred_buffers(inst, buffer_type);
return 0;
error:
iris_kill_session(inst);
iris_flush_deferred_buffers(inst, buffer_type);
return ret;
}

View File

@ -0,0 +1,16 @@
/* SPDX-License-Identifier: GPL-2.0-only */
/*
* Copyright (c) 2022-2025 Qualcomm Innovation Center, Inc. All rights reserved.
*/
#ifndef __IRIS_COMMON_H__
#define __IRIS_COMMON_H__
struct iris_inst;
struct iris_buffer;
int iris_process_streamon_input(struct iris_inst *inst);
int iris_process_streamon_output(struct iris_inst *inst);
int iris_session_streamoff(struct iris_inst *inst, u32 plane);
#endif

View File

@ -102,7 +102,7 @@ enum hfi_matrix_coefficients {
struct iris_hfi_prop_type_handle { struct iris_hfi_prop_type_handle {
u32 type; u32 type;
int (*handle)(struct iris_inst *inst); int (*handle)(struct iris_inst *inst, u32 plane);
}; };
struct iris_hfi_command_ops { struct iris_hfi_command_ops {

View File

@ -189,38 +189,65 @@ static int iris_hfi_gen1_session_stop(struct iris_inst *inst, u32 plane)
u32 flush_type = 0; u32 flush_type = 0;
int ret = 0; int ret = 0;
if (inst->state == IRIS_INST_STREAMING) { if (inst->domain == DECODER) {
if (V4L2_TYPE_IS_OUTPUT(plane)) if (inst->state == IRIS_INST_STREAMING) {
flush_type = HFI_FLUSH_ALL; if (V4L2_TYPE_IS_OUTPUT(plane))
else if (V4L2_TYPE_IS_CAPTURE(plane)) flush_type = HFI_FLUSH_ALL;
flush_type = HFI_FLUSH_OUTPUT; else if (V4L2_TYPE_IS_CAPTURE(plane))
flush_type = HFI_FLUSH_OUTPUT;
reinit_completion(&inst->flush_completion); reinit_completion(&inst->flush_completion);
flush_pkt.shdr.hdr.size = sizeof(struct hfi_session_flush_pkt); flush_pkt.shdr.hdr.size = sizeof(struct hfi_session_flush_pkt);
flush_pkt.shdr.hdr.pkt_type = HFI_CMD_SESSION_FLUSH; flush_pkt.shdr.hdr.pkt_type = HFI_CMD_SESSION_FLUSH;
flush_pkt.shdr.session_id = inst->session_id; flush_pkt.shdr.session_id = inst->session_id;
flush_pkt.flush_type = flush_type; flush_pkt.flush_type = flush_type;
ret = iris_hfi_queue_cmd_write(core, &flush_pkt, flush_pkt.shdr.hdr.size); ret = iris_hfi_queue_cmd_write(core, &flush_pkt, flush_pkt.shdr.hdr.size);
if (!ret) { if (!ret) {
inst->flush_responses_pending++; inst->flush_responses_pending++;
ret = iris_wait_for_session_response(inst, true); ret = iris_wait_for_session_response(inst, true);
}
} else if (inst->sub_state & IRIS_INST_SUB_LOAD_RESOURCES) {
reinit_completion(&inst->completion);
iris_hfi_gen1_packet_session_cmd(inst, &pkt, HFI_CMD_SESSION_STOP);
ret = iris_hfi_queue_cmd_write(core, &pkt, pkt.shdr.hdr.size);
if (!ret)
ret = iris_wait_for_session_response(inst, false);
reinit_completion(&inst->completion);
iris_hfi_gen1_packet_session_cmd(inst, &pkt,
HFI_CMD_SESSION_RELEASE_RESOURCES);
ret = iris_hfi_queue_cmd_write(core, &pkt, pkt.shdr.hdr.size);
if (!ret)
ret = iris_wait_for_session_response(inst, false);
iris_inst_change_sub_state(inst, IRIS_INST_SUB_LOAD_RESOURCES, 0);
iris_helper_buffers_done(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
VB2_BUF_STATE_ERROR);
iris_helper_buffers_done(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE,
VB2_BUF_STATE_ERROR);
} }
} else if (inst->sub_state & IRIS_INST_SUB_LOAD_RESOURCES) { } else {
reinit_completion(&inst->completion); if (inst->state == IRIS_INST_STREAMING ||
iris_hfi_gen1_packet_session_cmd(inst, &pkt, HFI_CMD_SESSION_STOP); inst->state == IRIS_INST_INPUT_STREAMING ||
ret = iris_hfi_queue_cmd_write(core, &pkt, pkt.shdr.hdr.size); inst->state == IRIS_INST_ERROR) {
if (!ret) reinit_completion(&inst->completion);
ret = iris_wait_for_session_response(inst, false); iris_hfi_gen1_packet_session_cmd(inst, &pkt, HFI_CMD_SESSION_STOP);
ret = iris_hfi_queue_cmd_write(core, &pkt, pkt.shdr.hdr.size);
if (!ret)
ret = iris_wait_for_session_response(inst, false);
reinit_completion(&inst->completion); reinit_completion(&inst->completion);
iris_hfi_gen1_packet_session_cmd(inst, &pkt, HFI_CMD_SESSION_RELEASE_RESOURCES); iris_hfi_gen1_packet_session_cmd(inst, &pkt,
ret = iris_hfi_queue_cmd_write(core, &pkt, pkt.shdr.hdr.size); HFI_CMD_SESSION_RELEASE_RESOURCES);
if (!ret) ret = iris_hfi_queue_cmd_write(core, &pkt, pkt.shdr.hdr.size);
ret = iris_wait_for_session_response(inst, false); if (!ret)
ret = iris_wait_for_session_response(inst, false);
iris_inst_change_sub_state(inst, IRIS_INST_SUB_LOAD_RESOURCES, 0); iris_inst_change_sub_state(inst, IRIS_INST_SUB_LOAD_RESOURCES, 0);
}
iris_helper_buffers_done(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE, iris_helper_buffers_done(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE,
VB2_BUF_STATE_ERROR); VB2_BUF_STATE_ERROR);
@ -549,7 +576,7 @@ static int iris_hfi_gen1_session_set_property(struct iris_inst *inst, u32 packet
return hfi_gen1_set_property(inst, packet_type, payload, payload_size); return hfi_gen1_set_property(inst, packet_type, payload, payload_size);
} }
static int iris_hfi_gen1_set_resolution(struct iris_inst *inst) static int iris_hfi_gen1_set_resolution(struct iris_inst *inst, u32 plane)
{ {
u32 ptype = HFI_PROPERTY_PARAM_FRAME_SIZE; u32 ptype = HFI_PROPERTY_PARAM_FRAME_SIZE;
struct hfi_framesize fs; struct hfi_framesize fs;
@ -564,14 +591,18 @@ static int iris_hfi_gen1_set_resolution(struct iris_inst *inst)
if (ret) if (ret)
return ret; return ret;
} }
fs.buffer_type = HFI_BUFFER_OUTPUT2; if (inst->domain == DECODER)
fs.buffer_type = HFI_BUFFER_OUTPUT2;
else
fs.buffer_type = HFI_BUFFER_OUTPUT;
fs.width = inst->fmt_dst->fmt.pix_mp.width; fs.width = inst->fmt_dst->fmt.pix_mp.width;
fs.height = inst->fmt_dst->fmt.pix_mp.height; fs.height = inst->fmt_dst->fmt.pix_mp.height;
return hfi_gen1_set_property(inst, ptype, &fs, sizeof(fs)); return hfi_gen1_set_property(inst, ptype, &fs, sizeof(fs));
} }
static int iris_hfi_gen1_decide_core(struct iris_inst *inst) static int iris_hfi_gen1_decide_core(struct iris_inst *inst, u32 plane)
{ {
const u32 ptype = HFI_PROPERTY_CONFIG_VIDEOCORES_USAGE; const u32 ptype = HFI_PROPERTY_CONFIG_VIDEOCORES_USAGE;
struct hfi_videocores_usage_type cu; struct hfi_videocores_usage_type cu;
@ -581,36 +612,45 @@ static int iris_hfi_gen1_decide_core(struct iris_inst *inst)
return hfi_gen1_set_property(inst, ptype, &cu, sizeof(cu)); return hfi_gen1_set_property(inst, ptype, &cu, sizeof(cu));
} }
static int iris_hfi_gen1_set_raw_format(struct iris_inst *inst) static int iris_hfi_gen1_set_raw_format(struct iris_inst *inst, u32 plane)
{ {
const u32 ptype = HFI_PROPERTY_PARAM_UNCOMPRESSED_FORMAT_SELECT; const u32 ptype = HFI_PROPERTY_PARAM_UNCOMPRESSED_FORMAT_SELECT;
u32 pixelformat = inst->fmt_dst->fmt.pix_mp.pixelformat;
struct hfi_uncompressed_format_select fmt; struct hfi_uncompressed_format_select fmt;
u32 pixelformat;
int ret; int ret;
if (iris_split_mode_enabled(inst)) { if (inst->domain == DECODER) {
fmt.buffer_type = HFI_BUFFER_OUTPUT; pixelformat = inst->fmt_dst->fmt.pix_mp.pixelformat;
fmt.format = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FORMAT_NV12_UBWC : 0; if (iris_split_mode_enabled(inst)) {
fmt.buffer_type = HFI_BUFFER_OUTPUT;
fmt.format = pixelformat == V4L2_PIX_FMT_NV12 ?
HFI_COLOR_FORMAT_NV12_UBWC : 0;
ret = hfi_gen1_set_property(inst, ptype, &fmt, sizeof(fmt)); ret = hfi_gen1_set_property(inst, ptype, &fmt, sizeof(fmt));
if (ret) if (ret)
return ret; return ret;
fmt.buffer_type = HFI_BUFFER_OUTPUT2; fmt.buffer_type = HFI_BUFFER_OUTPUT2;
fmt.format = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FORMAT_NV12 : 0; fmt.format = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FORMAT_NV12 : 0;
ret = hfi_gen1_set_property(inst, ptype, &fmt, sizeof(fmt)); ret = hfi_gen1_set_property(inst, ptype, &fmt, sizeof(fmt));
} else {
fmt.buffer_type = HFI_BUFFER_OUTPUT;
fmt.format = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FORMAT_NV12 : 0;
ret = hfi_gen1_set_property(inst, ptype, &fmt, sizeof(fmt));
}
} else { } else {
fmt.buffer_type = HFI_BUFFER_OUTPUT; pixelformat = inst->fmt_src->fmt.pix_mp.pixelformat;
fmt.buffer_type = HFI_BUFFER_INPUT;
fmt.format = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FORMAT_NV12 : 0; fmt.format = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FORMAT_NV12 : 0;
ret = hfi_gen1_set_property(inst, ptype, &fmt, sizeof(fmt)); ret = hfi_gen1_set_property(inst, ptype, &fmt, sizeof(fmt));
} }
return ret; return ret;
} }
static int iris_hfi_gen1_set_format_constraints(struct iris_inst *inst) static int iris_hfi_gen1_set_format_constraints(struct iris_inst *inst, u32 plane)
{ {
const u32 ptype = HFI_PROPERTY_PARAM_UNCOMPRESSED_PLANE_ACTUAL_CONSTRAINTS_INFO; const u32 ptype = HFI_PROPERTY_PARAM_UNCOMPRESSED_PLANE_ACTUAL_CONSTRAINTS_INFO;
struct hfi_uncompressed_plane_actual_constraints_info pconstraint; struct hfi_uncompressed_plane_actual_constraints_info pconstraint;
@ -630,7 +670,7 @@ static int iris_hfi_gen1_set_format_constraints(struct iris_inst *inst)
return hfi_gen1_set_property(inst, ptype, &pconstraint, sizeof(pconstraint)); return hfi_gen1_set_property(inst, ptype, &pconstraint, sizeof(pconstraint));
} }
static int iris_hfi_gen1_set_num_bufs(struct iris_inst *inst) static int iris_hfi_gen1_set_num_bufs(struct iris_inst *inst, u32 plane)
{ {
u32 ptype = HFI_PROPERTY_PARAM_BUFFER_COUNT_ACTUAL; u32 ptype = HFI_PROPERTY_PARAM_BUFFER_COUNT_ACTUAL;
struct hfi_buffer_count_actual buf_count; struct hfi_buffer_count_actual buf_count;
@ -644,20 +684,28 @@ static int iris_hfi_gen1_set_num_bufs(struct iris_inst *inst)
if (ret) if (ret)
return ret; return ret;
if (iris_split_mode_enabled(inst)) { if (inst->domain == DECODER) {
buf_count.type = HFI_BUFFER_OUTPUT; if (iris_split_mode_enabled(inst)) {
buf_count.count_actual = VIDEO_MAX_FRAME; buf_count.type = HFI_BUFFER_OUTPUT;
buf_count.count_min_host = VIDEO_MAX_FRAME; buf_count.count_actual = VIDEO_MAX_FRAME;
buf_count.count_min_host = VIDEO_MAX_FRAME;
ret = hfi_gen1_set_property(inst, ptype, &buf_count, sizeof(buf_count)); ret = hfi_gen1_set_property(inst, ptype, &buf_count, sizeof(buf_count));
if (ret) if (ret)
return ret; return ret;
buf_count.type = HFI_BUFFER_OUTPUT2; buf_count.type = HFI_BUFFER_OUTPUT2;
buf_count.count_actual = iris_vpu_buf_count(inst, BUF_DPB); buf_count.count_actual = iris_vpu_buf_count(inst, BUF_DPB);
buf_count.count_min_host = iris_vpu_buf_count(inst, BUF_DPB); buf_count.count_min_host = iris_vpu_buf_count(inst, BUF_DPB);
ret = hfi_gen1_set_property(inst, ptype, &buf_count, sizeof(buf_count)); ret = hfi_gen1_set_property(inst, ptype, &buf_count, sizeof(buf_count));
} else {
buf_count.type = HFI_BUFFER_OUTPUT;
buf_count.count_actual = VIDEO_MAX_FRAME;
buf_count.count_min_host = VIDEO_MAX_FRAME;
ret = hfi_gen1_set_property(inst, ptype, &buf_count, sizeof(buf_count));
}
} else { } else {
buf_count.type = HFI_BUFFER_OUTPUT; buf_count.type = HFI_BUFFER_OUTPUT;
buf_count.count_actual = VIDEO_MAX_FRAME; buf_count.count_actual = VIDEO_MAX_FRAME;
@ -669,7 +717,7 @@ static int iris_hfi_gen1_set_num_bufs(struct iris_inst *inst)
return ret; return ret;
} }
static int iris_hfi_gen1_set_multistream(struct iris_inst *inst) static int iris_hfi_gen1_set_multistream(struct iris_inst *inst, u32 plane)
{ {
u32 ptype = HFI_PROPERTY_PARAM_VDEC_MULTI_STREAM; u32 ptype = HFI_PROPERTY_PARAM_VDEC_MULTI_STREAM;
struct hfi_multi_stream multi = {0}; struct hfi_multi_stream multi = {0};
@ -704,7 +752,7 @@ static int iris_hfi_gen1_set_multistream(struct iris_inst *inst)
return ret; return ret;
} }
static int iris_hfi_gen1_set_bufsize(struct iris_inst *inst) static int iris_hfi_gen1_set_bufsize(struct iris_inst *inst, u32 plane)
{ {
const u32 ptype = HFI_PROPERTY_PARAM_BUFFER_SIZE_ACTUAL; const u32 ptype = HFI_PROPERTY_PARAM_BUFFER_SIZE_ACTUAL;
struct hfi_buffer_size_actual bufsz; struct hfi_buffer_size_actual bufsz;
@ -739,14 +787,49 @@ static int iris_hfi_gen1_set_bufsize(struct iris_inst *inst)
return ret; return ret;
} }
static int iris_hfi_gen1_set_frame_rate(struct iris_inst *inst, u32 plane)
{
const u32 ptype = HFI_PROPERTY_CONFIG_FRAME_RATE;
struct hfi_framerate frate;
if (V4L2_TYPE_IS_OUTPUT(plane))
return 0;
frate.buffer_type = HFI_BUFFER_OUTPUT;
frate.framerate = inst->frame_rate << 16;
return hfi_gen1_set_property(inst, ptype, &frate, sizeof(frate));
}
static int iris_hfi_gen1_set_stride(struct iris_inst *inst, u32 plane)
{
const u32 ptype = HFI_PROPERTY_PARAM_UNCOMPRESSED_PLANE_ACTUAL_INFO;
struct hfi_uncompressed_plane_actual_info plane_actual_info;
plane_actual_info.buffer_type = HFI_BUFFER_INPUT;
plane_actual_info.num_planes = 2;
plane_actual_info.plane_format[0].actual_stride =
ALIGN(inst->fmt_src->fmt.pix_mp.width, 128);
plane_actual_info.plane_format[0].actual_plane_buffer_height =
ALIGN(inst->fmt_src->fmt.pix_mp.height, 32);
plane_actual_info.plane_format[1].actual_stride =
ALIGN(inst->fmt_src->fmt.pix_mp.width, 128);
plane_actual_info.plane_format[1].actual_plane_buffer_height =
(ALIGN(inst->fmt_src->fmt.pix_mp.height, 32)) / 2;
return hfi_gen1_set_property(inst, ptype, &plane_actual_info, sizeof(plane_actual_info));
}
static int iris_hfi_gen1_session_set_config_params(struct iris_inst *inst, u32 plane) static int iris_hfi_gen1_session_set_config_params(struct iris_inst *inst, u32 plane)
{ {
struct iris_hfi_prop_type_handle const *handler = NULL;
u32 handler_size = 0;
struct iris_core *core = inst->core; struct iris_core *core = inst->core;
u32 config_params_size, i, j; u32 config_params_size, i, j;
const u32 *config_params; const u32 *config_params;
int ret; int ret;
static const struct iris_hfi_prop_type_handle prop_type_handle_inp_arr[] = { static const struct iris_hfi_prop_type_handle vdec_prop_type_handle_inp_arr[] = {
{HFI_PROPERTY_PARAM_FRAME_SIZE, {HFI_PROPERTY_PARAM_FRAME_SIZE,
iris_hfi_gen1_set_resolution}, iris_hfi_gen1_set_resolution},
{HFI_PROPERTY_CONFIG_VIDEOCORES_USAGE, {HFI_PROPERTY_CONFIG_VIDEOCORES_USAGE,
@ -763,7 +846,7 @@ static int iris_hfi_gen1_session_set_config_params(struct iris_inst *inst, u32 p
iris_hfi_gen1_set_bufsize}, iris_hfi_gen1_set_bufsize},
}; };
static const struct iris_hfi_prop_type_handle prop_type_handle_out_arr[] = { static const struct iris_hfi_prop_type_handle vdec_prop_type_handle_out_arr[] = {
{HFI_PROPERTY_PARAM_FRAME_SIZE, {HFI_PROPERTY_PARAM_FRAME_SIZE,
iris_hfi_gen1_set_resolution}, iris_hfi_gen1_set_resolution},
{HFI_PROPERTY_PARAM_UNCOMPRESSED_FORMAT_SELECT, {HFI_PROPERTY_PARAM_UNCOMPRESSED_FORMAT_SELECT,
@ -778,29 +861,43 @@ static int iris_hfi_gen1_session_set_config_params(struct iris_inst *inst, u32 p
iris_hfi_gen1_set_bufsize}, iris_hfi_gen1_set_bufsize},
}; };
config_params = core->iris_platform_data->input_config_params_default; static const struct iris_hfi_prop_type_handle venc_prop_type_handle_inp_arr[] = {
config_params_size = core->iris_platform_data->input_config_params_default_size; {HFI_PROPERTY_CONFIG_FRAME_RATE,
iris_hfi_gen1_set_frame_rate},
{HFI_PROPERTY_PARAM_UNCOMPRESSED_PLANE_ACTUAL_INFO,
iris_hfi_gen1_set_stride},
{HFI_PROPERTY_PARAM_FRAME_SIZE,
iris_hfi_gen1_set_resolution},
{HFI_PROPERTY_PARAM_UNCOMPRESSED_FORMAT_SELECT,
iris_hfi_gen1_set_raw_format},
{HFI_PROPERTY_PARAM_BUFFER_COUNT_ACTUAL,
iris_hfi_gen1_set_num_bufs},
};
if (V4L2_TYPE_IS_OUTPUT(plane)) { if (inst->domain == DECODER) {
for (i = 0; i < config_params_size; i++) { config_params = core->iris_platform_data->dec_input_config_params_default;
for (j = 0; j < ARRAY_SIZE(prop_type_handle_inp_arr); j++) { config_params_size = core->iris_platform_data->dec_input_config_params_default_size;
if (prop_type_handle_inp_arr[j].type == config_params[i]) { if (V4L2_TYPE_IS_OUTPUT(plane)) {
ret = prop_type_handle_inp_arr[j].handle(inst); handler = vdec_prop_type_handle_inp_arr;
if (ret) handler_size = ARRAY_SIZE(vdec_prop_type_handle_inp_arr);
return ret; } else if (V4L2_TYPE_IS_CAPTURE(plane)) {
break; handler = vdec_prop_type_handle_out_arr;
} handler_size = ARRAY_SIZE(vdec_prop_type_handle_out_arr);
}
} }
} else if (V4L2_TYPE_IS_CAPTURE(plane)) { } else {
for (i = 0; i < config_params_size; i++) { config_params = core->iris_platform_data->enc_input_config_params;
for (j = 0; j < ARRAY_SIZE(prop_type_handle_out_arr); j++) { config_params_size = core->iris_platform_data->enc_input_config_params_size;
if (prop_type_handle_out_arr[j].type == config_params[i]) { handler = venc_prop_type_handle_inp_arr;
ret = prop_type_handle_out_arr[j].handle(inst); handler_size = ARRAY_SIZE(venc_prop_type_handle_inp_arr);
if (ret) }
return ret;
break; for (i = 0; i < config_params_size; i++) {
} for (j = 0; j < handler_size; j++) {
if (handler[j].type == config_params[i]) {
ret = handler[j].handle(inst, plane);
if (ret)
return ret;
break;
} }
} }
} }

View File

@ -82,10 +82,12 @@
#define HFI_PROPERTY_SYS_IMAGE_VERSION 0x6 #define HFI_PROPERTY_SYS_IMAGE_VERSION 0x6
#define HFI_PROPERTY_PARAM_FRAME_SIZE 0x1001 #define HFI_PROPERTY_PARAM_FRAME_SIZE 0x1001
#define HFI_PROPERTY_PARAM_UNCOMPRESSED_PLANE_ACTUAL_INFO 0x1002
#define HFI_PROPERTY_PARAM_UNCOMPRESSED_FORMAT_SELECT 0x1003 #define HFI_PROPERTY_PARAM_UNCOMPRESSED_FORMAT_SELECT 0x1003
#define HFI_PROPERTY_PARAM_PROFILE_LEVEL_CURRENT 0x1005 #define HFI_PROPERTY_PARAM_PROFILE_LEVEL_CURRENT 0x1005
#define HFI_PROPERTY_PARAM_WORK_MODE 0x1015 #define HFI_PROPERTY_PARAM_WORK_MODE 0x1015
#define HFI_PROPERTY_PARAM_WORK_ROUTE 0x1017 #define HFI_PROPERTY_PARAM_WORK_ROUTE 0x1017
#define HFI_PROPERTY_CONFIG_FRAME_RATE 0x2001
#define HFI_PROPERTY_CONFIG_VIDEOCORES_USAGE 0x2002 #define HFI_PROPERTY_CONFIG_VIDEOCORES_USAGE 0x2002
#define HFI_PROPERTY_PARAM_VDEC_MULTI_STREAM 0x1003001 #define HFI_PROPERTY_PARAM_VDEC_MULTI_STREAM 0x1003001
@ -348,6 +350,17 @@ struct hfi_uncompressed_plane_actual_constraints_info {
struct hfi_uncompressed_plane_constraints plane_format[2]; struct hfi_uncompressed_plane_constraints plane_format[2];
}; };
struct hfi_uncompressed_plane_actual {
int actual_stride;
u32 actual_plane_buffer_height;
};
struct hfi_uncompressed_plane_actual_info {
u32 buffer_type;
u32 num_planes;
struct hfi_uncompressed_plane_actual plane_format[2];
};
struct hfi_buffer_count_actual { struct hfi_buffer_count_actual {
u32 type; u32 type;
u32 count_actual; u32 count_actual;
@ -375,6 +388,11 @@ struct hfi_buffer_requirements {
u32 alignment; u32 alignment;
}; };
struct hfi_framerate {
u32 buffer_type;
u32 framerate;
};
struct hfi_event_data { struct hfi_event_data {
u32 error; u32 error;
u32 height; u32 height;

View File

@ -88,15 +88,26 @@ static int iris_hfi_gen2_sys_pc_prep(struct iris_core *core)
return ret; return ret;
} }
static u32 iris_hfi_gen2_get_port(u32 plane) static u32 iris_hfi_gen2_get_port(struct iris_inst *inst, u32 plane)
{ {
switch (plane) { if (inst->domain == DECODER) {
case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE: switch (plane) {
return HFI_PORT_BITSTREAM; case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE: return HFI_PORT_BITSTREAM;
return HFI_PORT_RAW; case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
default: return HFI_PORT_RAW;
return HFI_PORT_NONE; default:
return HFI_PORT_NONE;
}
} else {
switch (plane) {
case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
return HFI_PORT_RAW;
case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
return HFI_PORT_BITSTREAM;
default:
return HFI_PORT_NONE;
}
} }
} }
@ -136,34 +147,77 @@ static int iris_hfi_gen2_session_set_property(struct iris_inst *inst, u32 packet
inst_hfi_gen2->packet->size); inst_hfi_gen2->packet->size);
} }
static int iris_hfi_gen2_set_bitstream_resolution(struct iris_inst *inst) static int iris_hfi_gen2_set_raw_resolution(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
u32 resolution = inst->fmt_src->fmt.pix_mp.width << 16 | u32 resolution = inst->fmt_src->fmt.pix_mp.width << 16 |
inst->fmt_src->fmt.pix_mp.height; inst->fmt_src->fmt.pix_mp.height;
u32 port = iris_hfi_gen2_get_port(inst, plane);
inst_hfi_gen2->src_subcr_params.bitstream_resolution = resolution; return iris_hfi_gen2_session_set_property(inst,
HFI_PROP_RAW_RESOLUTION,
HFI_HOST_FLAGS_NONE,
port,
HFI_PAYLOAD_32_PACKED,
&resolution,
sizeof(u32));
}
static int iris_hfi_gen2_set_bitstream_resolution(struct iris_inst *inst, u32 plane)
{
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(inst, plane);
enum hfi_packet_payload_info payload_type;
u32 resolution, codec_align;
if (inst->domain == DECODER) {
resolution = inst->fmt_src->fmt.pix_mp.width << 16 |
inst->fmt_src->fmt.pix_mp.height;
inst_hfi_gen2->src_subcr_params.bitstream_resolution = resolution;
payload_type = HFI_PAYLOAD_U32;
} else {
codec_align = inst->codec == V4L2_PIX_FMT_HEVC ? 32 : 16;
resolution = ALIGN(inst->fmt_dst->fmt.pix_mp.width, codec_align) << 16 |
ALIGN(inst->fmt_dst->fmt.pix_mp.height, codec_align);
inst_hfi_gen2->dst_subcr_params.bitstream_resolution = resolution;
payload_type = HFI_PAYLOAD_32_PACKED;
}
return iris_hfi_gen2_session_set_property(inst, return iris_hfi_gen2_session_set_property(inst,
HFI_PROP_BITSTREAM_RESOLUTION, HFI_PROP_BITSTREAM_RESOLUTION,
HFI_HOST_FLAGS_NONE, HFI_HOST_FLAGS_NONE,
port, port,
HFI_PAYLOAD_U32, payload_type,
&resolution, &resolution,
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_crop_offsets(struct iris_inst *inst) static int iris_hfi_gen2_set_crop_offsets(struct iris_inst *inst, u32 plane)
{ {
u32 bottom_offset = (inst->fmt_src->fmt.pix_mp.height - inst->crop.height);
u32 right_offset = (inst->fmt_src->fmt.pix_mp.width - inst->crop.width);
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE); u32 port = iris_hfi_gen2_get_port(inst, plane);
u32 left_offset = inst->crop.left; u32 bottom_offset, right_offset;
u32 top_offset = inst->crop.top; u32 left_offset, top_offset;
u32 payload[2]; u32 payload[2];
if (inst->domain == DECODER) {
if (V4L2_TYPE_IS_OUTPUT(plane)) {
bottom_offset = (inst->fmt_src->fmt.pix_mp.height - inst->crop.height);
right_offset = (inst->fmt_src->fmt.pix_mp.width - inst->crop.width);
left_offset = inst->crop.left;
top_offset = inst->crop.top;
} else {
bottom_offset = (inst->fmt_dst->fmt.pix_mp.height - inst->compose.height);
right_offset = (inst->fmt_dst->fmt.pix_mp.width - inst->compose.width);
left_offset = inst->compose.left;
top_offset = inst->compose.top;
}
} else {
bottom_offset = (inst->fmt_src->fmt.pix_mp.height - inst->crop.height);
right_offset = (inst->fmt_src->fmt.pix_mp.width - inst->crop.width);
left_offset = inst->crop.left;
top_offset = inst->crop.top;
}
payload[0] = FIELD_PREP(GENMASK(31, 16), left_offset) | top_offset; payload[0] = FIELD_PREP(GENMASK(31, 16), left_offset) | top_offset;
payload[1] = FIELD_PREP(GENMASK(31, 16), right_offset) | bottom_offset; payload[1] = FIELD_PREP(GENMASK(31, 16), right_offset) | bottom_offset;
inst_hfi_gen2->src_subcr_params.crop_offsets[0] = payload[0]; inst_hfi_gen2->src_subcr_params.crop_offsets[0] = payload[0];
@ -178,10 +232,10 @@ static int iris_hfi_gen2_set_crop_offsets(struct iris_inst *inst)
sizeof(u64)); sizeof(u64));
} }
static int iris_hfi_gen2_set_bit_depth(struct iris_inst *inst) static int iris_hfi_gen2_set_bit_depth(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE); u32 port = iris_hfi_gen2_get_port(inst, plane);
u32 bitdepth = BIT_DEPTH_8; u32 bitdepth = BIT_DEPTH_8;
inst_hfi_gen2->src_subcr_params.bit_depth = bitdepth; inst_hfi_gen2->src_subcr_params.bit_depth = bitdepth;
@ -195,10 +249,10 @@ static int iris_hfi_gen2_set_bit_depth(struct iris_inst *inst)
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_coded_frames(struct iris_inst *inst) static int iris_hfi_gen2_set_coded_frames(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE); u32 port = iris_hfi_gen2_get_port(inst, plane);
u32 coded_frames = 0; u32 coded_frames = 0;
if (inst->fw_caps[CODED_FRAMES].value == CODED_FRAMES_PROGRESSIVE) if (inst->fw_caps[CODED_FRAMES].value == CODED_FRAMES_PROGRESSIVE)
@ -214,11 +268,11 @@ static int iris_hfi_gen2_set_coded_frames(struct iris_inst *inst)
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_min_output_count(struct iris_inst *inst) static int iris_hfi_gen2_set_min_output_count(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
u32 min_output = inst->buffers[BUF_OUTPUT].min_count; u32 min_output = inst->buffers[BUF_OUTPUT].min_count;
u32 port = iris_hfi_gen2_get_port(inst, plane);
inst_hfi_gen2->src_subcr_params.fw_min_count = min_output; inst_hfi_gen2->src_subcr_params.fw_min_count = min_output;
@ -231,10 +285,10 @@ static int iris_hfi_gen2_set_min_output_count(struct iris_inst *inst)
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_picture_order_count(struct iris_inst *inst) static int iris_hfi_gen2_set_picture_order_count(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE); u32 port = iris_hfi_gen2_get_port(inst, plane);
u32 poc = 0; u32 poc = 0;
inst_hfi_gen2->src_subcr_params.pic_order_cnt = poc; inst_hfi_gen2->src_subcr_params.pic_order_cnt = poc;
@ -248,16 +302,16 @@ static int iris_hfi_gen2_set_picture_order_count(struct iris_inst *inst)
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_colorspace(struct iris_inst *inst) static int iris_hfi_gen2_set_colorspace(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
struct v4l2_pix_format_mplane *pixmp = &inst->fmt_src->fmt.pix_mp; struct v4l2_pix_format_mplane *pixmp = &inst->fmt_src->fmt.pix_mp;
u32 video_signal_type_present_flag = 0, color_info; u32 video_signal_type_present_flag = 0, color_info;
u32 matrix_coeff = HFI_MATRIX_COEFF_RESERVED; u32 matrix_coeff = HFI_MATRIX_COEFF_RESERVED;
u32 video_format = UNSPECIFIED_COLOR_FORMAT; u32 video_format = UNSPECIFIED_COLOR_FORMAT;
u32 full_range = V4L2_QUANTIZATION_DEFAULT; u32 full_range = V4L2_QUANTIZATION_DEFAULT;
u32 transfer_char = HFI_TRANSFER_RESERVED; u32 transfer_char = HFI_TRANSFER_RESERVED;
u32 port = iris_hfi_gen2_get_port(inst, plane);
u32 colour_description_present_flag = 0; u32 colour_description_present_flag = 0;
u32 primaries = HFI_PRIMARIES_RESERVED; u32 primaries = HFI_PRIMARIES_RESERVED;
@ -291,10 +345,10 @@ static int iris_hfi_gen2_set_colorspace(struct iris_inst *inst)
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_profile(struct iris_inst *inst) static int iris_hfi_gen2_set_profile(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE); u32 port = iris_hfi_gen2_get_port(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
u32 profile = 0; u32 profile = 0;
switch (inst->codec) { switch (inst->codec) {
@ -320,10 +374,10 @@ static int iris_hfi_gen2_set_profile(struct iris_inst *inst)
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_level(struct iris_inst *inst) static int iris_hfi_gen2_set_level(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE); u32 port = iris_hfi_gen2_get_port(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
u32 level = 0; u32 level = 0;
switch (inst->codec) { switch (inst->codec) {
@ -349,33 +403,47 @@ static int iris_hfi_gen2_set_level(struct iris_inst *inst)
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_colorformat(struct iris_inst *inst) static int iris_hfi_gen2_set_colorformat(struct iris_inst *inst, u32 plane)
{ {
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE); u32 port = iris_hfi_gen2_get_port(inst, plane);
u32 hfi_colorformat, pixelformat; u32 hfi_colorformat, pixelformat;
pixelformat = inst->fmt_dst->fmt.pix_mp.pixelformat; if (inst->domain == DECODER) {
hfi_colorformat = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FMT_NV12 : 0; pixelformat = inst->fmt_dst->fmt.pix_mp.pixelformat;
hfi_colorformat = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FMT_NV12 : 0;
} else {
pixelformat = inst->fmt_src->fmt.pix_mp.pixelformat;
hfi_colorformat = pixelformat == V4L2_PIX_FMT_NV12 ? HFI_COLOR_FMT_NV12 : 0;
}
return iris_hfi_gen2_session_set_property(inst, return iris_hfi_gen2_session_set_property(inst,
HFI_PROP_COLOR_FORMAT, HFI_PROP_COLOR_FORMAT,
HFI_HOST_FLAGS_NONE, HFI_HOST_FLAGS_NONE,
port, port,
HFI_PAYLOAD_U32, HFI_PAYLOAD_U32_ENUM,
&hfi_colorformat, &hfi_colorformat,
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_linear_stride_scanline(struct iris_inst *inst) static int iris_hfi_gen2_set_linear_stride_scanline(struct iris_inst *inst, u32 plane)
{ {
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE); u32 pixelformat, stride_y, stride_uv, scanline_y, scanline_uv;
u32 pixelformat = inst->fmt_dst->fmt.pix_mp.pixelformat; u32 port = iris_hfi_gen2_get_port(inst, plane);
u32 scanline_y = inst->fmt_dst->fmt.pix_mp.height;
u32 stride_y = inst->fmt_dst->fmt.pix_mp.width;
u32 scanline_uv = scanline_y / 2;
u32 stride_uv = stride_y;
u32 payload[2]; u32 payload[2];
if (inst->domain == DECODER) {
pixelformat = inst->fmt_dst->fmt.pix_mp.pixelformat;
stride_y = inst->fmt_dst->fmt.pix_mp.width;
scanline_y = inst->fmt_dst->fmt.pix_mp.height;
} else {
pixelformat = inst->fmt_src->fmt.pix_mp.pixelformat;
stride_y = ALIGN(inst->fmt_src->fmt.pix_mp.width, 128);
scanline_y = ALIGN(inst->fmt_src->fmt.pix_mp.height, 32);
}
stride_uv = stride_y;
scanline_uv = scanline_y / 2;
if (pixelformat != V4L2_PIX_FMT_NV12) if (pixelformat != V4L2_PIX_FMT_NV12)
return 0; return 0;
@ -386,15 +454,15 @@ static int iris_hfi_gen2_set_linear_stride_scanline(struct iris_inst *inst)
HFI_PROP_LINEAR_STRIDE_SCANLINE, HFI_PROP_LINEAR_STRIDE_SCANLINE,
HFI_HOST_FLAGS_NONE, HFI_HOST_FLAGS_NONE,
port, port,
HFI_PAYLOAD_U64, HFI_PAYLOAD_64_PACKED,
&payload, &payload,
sizeof(u64)); sizeof(u64));
} }
static int iris_hfi_gen2_set_tier(struct iris_inst *inst) static int iris_hfi_gen2_set_tier(struct iris_inst *inst, u32 plane)
{ {
struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst); struct iris_inst_hfi_gen2 *inst_hfi_gen2 = to_iris_inst_hfi_gen2(inst);
u32 port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE); u32 port = iris_hfi_gen2_get_port(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
u32 tier = inst->fw_caps[TIER].value; u32 tier = inst->fw_caps[TIER].value;
inst_hfi_gen2->src_subcr_params.tier = tier; inst_hfi_gen2->src_subcr_params.tier = tier;
@ -408,14 +476,29 @@ static int iris_hfi_gen2_set_tier(struct iris_inst *inst)
sizeof(u32)); sizeof(u32));
} }
static int iris_hfi_gen2_set_frame_rate(struct iris_inst *inst, u32 plane)
{
u32 port = iris_hfi_gen2_get_port(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
u32 frame_rate = inst->frame_rate << 16;
return iris_hfi_gen2_session_set_property(inst,
HFI_PROP_FRAME_RATE,
HFI_HOST_FLAGS_NONE,
port,
HFI_PAYLOAD_Q16,
&frame_rate,
sizeof(u32));
}
static int iris_hfi_gen2_session_set_config_params(struct iris_inst *inst, u32 plane) static int iris_hfi_gen2_session_set_config_params(struct iris_inst *inst, u32 plane)
{ {
struct iris_core *core = inst->core; const struct iris_platform_data *pdata = inst->core->iris_platform_data;
u32 config_params_size = 0, i, j; u32 config_params_size = 0, i, j;
const u32 *config_params = NULL; const u32 *config_params = NULL;
int ret; int ret;
static const struct iris_hfi_prop_type_handle prop_type_handle_arr[] = { static const struct iris_hfi_prop_type_handle prop_type_handle_arr[] = {
{HFI_PROP_RAW_RESOLUTION, iris_hfi_gen2_set_raw_resolution },
{HFI_PROP_BITSTREAM_RESOLUTION, iris_hfi_gen2_set_bitstream_resolution }, {HFI_PROP_BITSTREAM_RESOLUTION, iris_hfi_gen2_set_bitstream_resolution },
{HFI_PROP_CROP_OFFSETS, iris_hfi_gen2_set_crop_offsets }, {HFI_PROP_CROP_OFFSETS, iris_hfi_gen2_set_crop_offsets },
{HFI_PROP_CODED_FRAMES, iris_hfi_gen2_set_coded_frames }, {HFI_PROP_CODED_FRAMES, iris_hfi_gen2_set_coded_frames },
@ -428,29 +511,35 @@ static int iris_hfi_gen2_session_set_config_params(struct iris_inst *inst, u32 p
{HFI_PROP_COLOR_FORMAT, iris_hfi_gen2_set_colorformat }, {HFI_PROP_COLOR_FORMAT, iris_hfi_gen2_set_colorformat },
{HFI_PROP_LINEAR_STRIDE_SCANLINE, iris_hfi_gen2_set_linear_stride_scanline }, {HFI_PROP_LINEAR_STRIDE_SCANLINE, iris_hfi_gen2_set_linear_stride_scanline },
{HFI_PROP_TIER, iris_hfi_gen2_set_tier }, {HFI_PROP_TIER, iris_hfi_gen2_set_tier },
{HFI_PROP_FRAME_RATE, iris_hfi_gen2_set_frame_rate },
}; };
if (V4L2_TYPE_IS_OUTPUT(plane)) { if (inst->domain == DECODER) {
switch (inst->codec) { if (V4L2_TYPE_IS_OUTPUT(plane)) {
case V4L2_PIX_FMT_H264: if (inst->codec == V4L2_PIX_FMT_H264) {
config_params = core->iris_platform_data->input_config_params_default; config_params = pdata->dec_input_config_params_default;
config_params_size = config_params_size = pdata->dec_input_config_params_default_size;
core->iris_platform_data->input_config_params_default_size; } else if (inst->codec == V4L2_PIX_FMT_HEVC) {
break; config_params = pdata->dec_input_config_params_hevc;
case V4L2_PIX_FMT_HEVC: config_params_size = pdata->dec_input_config_params_hevc_size;
config_params = core->iris_platform_data->input_config_params_hevc; } else if (inst->codec == V4L2_PIX_FMT_VP9) {
config_params_size = config_params = pdata->dec_input_config_params_vp9;
core->iris_platform_data->input_config_params_hevc_size; config_params_size = pdata->dec_input_config_params_vp9_size;
break; } else {
case V4L2_PIX_FMT_VP9: return -EINVAL;
config_params = core->iris_platform_data->input_config_params_vp9; }
config_params_size = } else {
core->iris_platform_data->input_config_params_vp9_size; config_params = pdata->dec_output_config_params;
break; config_params_size = pdata->dec_output_config_params_size;
} }
} else { } else {
config_params = core->iris_platform_data->output_config_params; if (V4L2_TYPE_IS_OUTPUT(plane)) {
config_params_size = core->iris_platform_data->output_config_params_size; config_params = pdata->enc_input_config_params;
config_params_size = pdata->enc_input_config_params_size;
} else {
config_params = pdata->enc_output_config_params;
config_params_size = pdata->enc_output_config_params_size;
}
} }
if (!config_params || !config_params_size) if (!config_params || !config_params_size)
@ -459,7 +548,7 @@ static int iris_hfi_gen2_session_set_config_params(struct iris_inst *inst, u32 p
for (i = 0; i < config_params_size; i++) { for (i = 0; i < config_params_size; i++) {
for (j = 0; j < ARRAY_SIZE(prop_type_handle_arr); j++) { for (j = 0; j < ARRAY_SIZE(prop_type_handle_arr); j++) {
if (prop_type_handle_arr[j].type == config_params[i]) { if (prop_type_handle_arr[j].type == config_params[i]) {
ret = prop_type_handle_arr[j].handle(inst); ret = prop_type_handle_arr[j].handle(inst, plane);
if (ret) if (ret)
return ret; return ret;
break; break;
@ -477,14 +566,19 @@ static int iris_hfi_gen2_session_set_codec(struct iris_inst *inst)
switch (inst->codec) { switch (inst->codec) {
case V4L2_PIX_FMT_H264: case V4L2_PIX_FMT_H264:
codec = HFI_CODEC_DECODE_AVC; if (inst->domain == ENCODER)
codec = HFI_CODEC_ENCODE_AVC;
else
codec = HFI_CODEC_DECODE_AVC;
break; break;
case V4L2_PIX_FMT_HEVC: case V4L2_PIX_FMT_HEVC:
codec = HFI_CODEC_DECODE_HEVC; if (inst->domain == ENCODER)
codec = HFI_CODEC_ENCODE_HEVC;
else
codec = HFI_CODEC_DECODE_HEVC;
break; break;
case V4L2_PIX_FMT_VP9: case V4L2_PIX_FMT_VP9:
codec = HFI_CODEC_DECODE_VP9; codec = HFI_CODEC_DECODE_VP9;
break;
} }
iris_hfi_gen2_packet_session_property(inst, iris_hfi_gen2_packet_session_property(inst,
@ -550,9 +644,11 @@ static int iris_hfi_gen2_session_open(struct iris_inst *inst)
if (ret) if (ret)
goto fail_free_packet; goto fail_free_packet;
ret = iris_hfi_gen2_session_set_default_header(inst); if (inst->domain == DECODER) {
if (ret) ret = iris_hfi_gen2_session_set_default_header(inst);
goto fail_free_packet; if (ret)
goto fail_free_packet;
}
return 0; return 0;
@ -601,7 +697,7 @@ static int iris_hfi_gen2_session_subscribe_mode(struct iris_inst *inst,
cmd, cmd,
(HFI_HOST_FLAGS_RESPONSE_REQUIRED | (HFI_HOST_FLAGS_RESPONSE_REQUIRED |
HFI_HOST_FLAGS_INTR_REQUIRED), HFI_HOST_FLAGS_INTR_REQUIRED),
iris_hfi_gen2_get_port(plane), iris_hfi_gen2_get_port(inst, plane),
inst->session_id, inst->session_id,
payload_type, payload_type,
payload, payload,
@ -623,6 +719,9 @@ static int iris_hfi_gen2_subscribe_change_param(struct iris_inst *inst, u32 plan
u32 hfi_port = 0, i; u32 hfi_port = 0, i;
int ret; int ret;
if (inst->domain == ENCODER)
return 0;
if ((V4L2_TYPE_IS_OUTPUT(plane) && inst_hfi_gen2->ipsc_properties_set) || if ((V4L2_TYPE_IS_OUTPUT(plane) && inst_hfi_gen2->ipsc_properties_set) ||
(V4L2_TYPE_IS_CAPTURE(plane) && inst_hfi_gen2->opsc_properties_set)) { (V4L2_TYPE_IS_CAPTURE(plane) && inst_hfi_gen2->opsc_properties_set)) {
dev_err(core->dev, "invalid plane\n"); dev_err(core->dev, "invalid plane\n");
@ -631,19 +730,19 @@ static int iris_hfi_gen2_subscribe_change_param(struct iris_inst *inst, u32 plan
switch (inst->codec) { switch (inst->codec) {
case V4L2_PIX_FMT_H264: case V4L2_PIX_FMT_H264:
change_param = core->iris_platform_data->input_config_params_default; change_param = core->iris_platform_data->dec_input_config_params_default;
change_param_size = change_param_size =
core->iris_platform_data->input_config_params_default_size; core->iris_platform_data->dec_input_config_params_default_size;
break; break;
case V4L2_PIX_FMT_HEVC: case V4L2_PIX_FMT_HEVC:
change_param = core->iris_platform_data->input_config_params_hevc; change_param = core->iris_platform_data->dec_input_config_params_hevc;
change_param_size = change_param_size =
core->iris_platform_data->input_config_params_hevc_size; core->iris_platform_data->dec_input_config_params_hevc_size;
break; break;
case V4L2_PIX_FMT_VP9: case V4L2_PIX_FMT_VP9:
change_param = core->iris_platform_data->input_config_params_vp9; change_param = core->iris_platform_data->dec_input_config_params_vp9;
change_param_size = change_param_size =
core->iris_platform_data->input_config_params_vp9_size; core->iris_platform_data->dec_input_config_params_vp9_size;
break; break;
} }
@ -664,7 +763,7 @@ static int iris_hfi_gen2_subscribe_change_param(struct iris_inst *inst, u32 plan
if (V4L2_TYPE_IS_OUTPUT(plane)) { if (V4L2_TYPE_IS_OUTPUT(plane)) {
inst_hfi_gen2->ipsc_properties_set = true; inst_hfi_gen2->ipsc_properties_set = true;
} else { } else {
hfi_port = iris_hfi_gen2_get_port(V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE); hfi_port = iris_hfi_gen2_get_port(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
memcpy(&inst_hfi_gen2->dst_subcr_params, memcpy(&inst_hfi_gen2->dst_subcr_params,
&inst_hfi_gen2->src_subcr_params, &inst_hfi_gen2->src_subcr_params,
sizeof(inst_hfi_gen2->src_subcr_params)); sizeof(inst_hfi_gen2->src_subcr_params));
@ -759,6 +858,9 @@ static int iris_hfi_gen2_subscribe_property(struct iris_inst *inst, u32 plane)
payload[0] = HFI_MODE_PROPERTY; payload[0] = HFI_MODE_PROPERTY;
if (inst->domain == ENCODER)
return 0;
if (V4L2_TYPE_IS_OUTPUT(plane)) { if (V4L2_TYPE_IS_OUTPUT(plane)) {
subscribe_prop_size = core->iris_platform_data->dec_input_prop_size; subscribe_prop_size = core->iris_platform_data->dec_input_prop_size;
subcribe_prop = core->iris_platform_data->dec_input_prop; subcribe_prop = core->iris_platform_data->dec_input_prop;
@ -810,7 +912,7 @@ static int iris_hfi_gen2_session_start(struct iris_inst *inst, u32 plane)
HFI_CMD_START, HFI_CMD_START,
(HFI_HOST_FLAGS_RESPONSE_REQUIRED | (HFI_HOST_FLAGS_RESPONSE_REQUIRED |
HFI_HOST_FLAGS_INTR_REQUIRED), HFI_HOST_FLAGS_INTR_REQUIRED),
iris_hfi_gen2_get_port(plane), iris_hfi_gen2_get_port(inst, plane),
inst->session_id, inst->session_id,
HFI_PAYLOAD_NONE, HFI_PAYLOAD_NONE,
NULL, NULL,
@ -832,7 +934,7 @@ static int iris_hfi_gen2_session_stop(struct iris_inst *inst, u32 plane)
(HFI_HOST_FLAGS_RESPONSE_REQUIRED | (HFI_HOST_FLAGS_RESPONSE_REQUIRED |
HFI_HOST_FLAGS_INTR_REQUIRED | HFI_HOST_FLAGS_INTR_REQUIRED |
HFI_HOST_FLAGS_NON_DISCARDABLE), HFI_HOST_FLAGS_NON_DISCARDABLE),
iris_hfi_gen2_get_port(plane), iris_hfi_gen2_get_port(inst, plane),
inst->session_id, inst->session_id,
HFI_PAYLOAD_NONE, HFI_PAYLOAD_NONE,
NULL, NULL,
@ -854,7 +956,7 @@ static int iris_hfi_gen2_session_pause(struct iris_inst *inst, u32 plane)
HFI_CMD_PAUSE, HFI_CMD_PAUSE,
(HFI_HOST_FLAGS_RESPONSE_REQUIRED | (HFI_HOST_FLAGS_RESPONSE_REQUIRED |
HFI_HOST_FLAGS_INTR_REQUIRED), HFI_HOST_FLAGS_INTR_REQUIRED),
iris_hfi_gen2_get_port(plane), iris_hfi_gen2_get_port(inst, plane),
inst->session_id, inst->session_id,
HFI_PAYLOAD_NONE, HFI_PAYLOAD_NONE,
NULL, NULL,
@ -873,7 +975,7 @@ static int iris_hfi_gen2_session_resume_drc(struct iris_inst *inst, u32 plane)
HFI_CMD_RESUME, HFI_CMD_RESUME,
(HFI_HOST_FLAGS_RESPONSE_REQUIRED | (HFI_HOST_FLAGS_RESPONSE_REQUIRED |
HFI_HOST_FLAGS_INTR_REQUIRED), HFI_HOST_FLAGS_INTR_REQUIRED),
iris_hfi_gen2_get_port(plane), iris_hfi_gen2_get_port(inst, plane),
inst->session_id, inst->session_id,
HFI_PAYLOAD_U32, HFI_PAYLOAD_U32,
&payload, &payload,
@ -892,7 +994,7 @@ static int iris_hfi_gen2_session_resume_drain(struct iris_inst *inst, u32 plane)
HFI_CMD_RESUME, HFI_CMD_RESUME,
(HFI_HOST_FLAGS_RESPONSE_REQUIRED | (HFI_HOST_FLAGS_RESPONSE_REQUIRED |
HFI_HOST_FLAGS_INTR_REQUIRED), HFI_HOST_FLAGS_INTR_REQUIRED),
iris_hfi_gen2_get_port(plane), iris_hfi_gen2_get_port(inst, plane),
inst->session_id, inst->session_id,
HFI_PAYLOAD_U32, HFI_PAYLOAD_U32,
&payload, &payload,
@ -914,7 +1016,7 @@ static int iris_hfi_gen2_session_drain(struct iris_inst *inst, u32 plane)
(HFI_HOST_FLAGS_RESPONSE_REQUIRED | (HFI_HOST_FLAGS_RESPONSE_REQUIRED |
HFI_HOST_FLAGS_INTR_REQUIRED | HFI_HOST_FLAGS_INTR_REQUIRED |
HFI_HOST_FLAGS_NON_DISCARDABLE), HFI_HOST_FLAGS_NON_DISCARDABLE),
iris_hfi_gen2_get_port(plane), iris_hfi_gen2_get_port(inst, plane),
inst->session_id, inst->session_id,
HFI_PAYLOAD_NONE, HFI_PAYLOAD_NONE,
NULL, NULL,

View File

@ -49,6 +49,7 @@
#define HFI_PROP_TIER 0x03000109 #define HFI_PROP_TIER 0x03000109
#define HFI_PROP_STAGE 0x0300010a #define HFI_PROP_STAGE 0x0300010a
#define HFI_PROP_PIPE 0x0300010b #define HFI_PROP_PIPE 0x0300010b
#define HFI_PROP_FRAME_RATE 0x0300010c
#define HFI_PROP_LUMA_CHROMA_BIT_DEPTH 0x0300010f #define HFI_PROP_LUMA_CHROMA_BIT_DEPTH 0x0300010f
#define HFI_PROP_CODED_FRAMES 0x03000120 #define HFI_PROP_CODED_FRAMES 0x03000120
#define HFI_PROP_CABAC_SESSION 0x03000121 #define HFI_PROP_CABAC_SESSION 0x03000121
@ -69,6 +70,8 @@
#define HFI_PROP_DEC_DEFAULT_HEADER 0x03000168 #define HFI_PROP_DEC_DEFAULT_HEADER 0x03000168
#define HFI_PROP_DEC_START_FROM_RAP_FRAME 0x03000169 #define HFI_PROP_DEC_START_FROM_RAP_FRAME 0x03000169
#define HFI_PROP_NO_OUTPUT 0x0300016a #define HFI_PROP_NO_OUTPUT 0x0300016a
#define HFI_PROP_BUFFER_MARK 0x0300016c
#define HFI_PROP_RAW_RESOLUTION 0x03000178
#define HFI_PROP_TOTAL_PEAK_BITRATE 0x0300017C #define HFI_PROP_TOTAL_PEAK_BITRATE 0x0300017C
#define HFI_PROP_COMV_BUFFER_COUNT 0x03000193 #define HFI_PROP_COMV_BUFFER_COUNT 0x03000193
#define HFI_PROP_END 0x03FFFFFF #define HFI_PROP_END 0x03FFFFFF

View File

@ -227,14 +227,18 @@ struct iris_platform_data {
u32 max_core_mbpf; u32 max_core_mbpf;
/* max number of macroblocks per second supported */ /* max number of macroblocks per second supported */
u32 max_core_mbps; u32 max_core_mbps;
const u32 *input_config_params_default; const u32 *dec_input_config_params_default;
unsigned int input_config_params_default_size; unsigned int dec_input_config_params_default_size;
const u32 *input_config_params_hevc; const u32 *dec_input_config_params_hevc;
unsigned int input_config_params_hevc_size; unsigned int dec_input_config_params_hevc_size;
const u32 *input_config_params_vp9; const u32 *dec_input_config_params_vp9;
unsigned int input_config_params_vp9_size; unsigned int dec_input_config_params_vp9_size;
const u32 *output_config_params; const u32 *dec_output_config_params;
unsigned int output_config_params_size; unsigned int dec_output_config_params_size;
const u32 *enc_input_config_params;
unsigned int enc_input_config_params_size;
const u32 *enc_output_config_params;
unsigned int enc_output_config_params_size;
const u32 *dec_input_prop; const u32 *dec_input_prop;
unsigned int dec_input_prop_size; unsigned int dec_input_prop_size;
const u32 *dec_output_prop_avc; const u32 *dec_output_prop_avc;

View File

@ -658,11 +658,25 @@ static const u32 sm8550_vdec_input_config_param_vp9[] = {
HFI_PROP_LEVEL, HFI_PROP_LEVEL,
}; };
static const u32 sm8550_venc_input_config_params[] = {
HFI_PROP_COLOR_FORMAT,
HFI_PROP_RAW_RESOLUTION,
HFI_PROP_CROP_OFFSETS,
HFI_PROP_LINEAR_STRIDE_SCANLINE,
HFI_PROP_SIGNAL_COLOR_INFO,
};
static const u32 sm8550_vdec_output_config_params[] = { static const u32 sm8550_vdec_output_config_params[] = {
HFI_PROP_COLOR_FORMAT, HFI_PROP_COLOR_FORMAT,
HFI_PROP_LINEAR_STRIDE_SCANLINE, HFI_PROP_LINEAR_STRIDE_SCANLINE,
}; };
static const u32 sm8550_venc_output_config_params[] = {
HFI_PROP_BITSTREAM_RESOLUTION,
HFI_PROP_CROP_OFFSETS,
HFI_PROP_FRAME_RATE,
};
static const u32 sm8550_vdec_subscribe_input_properties[] = { static const u32 sm8550_vdec_subscribe_input_properties[] = {
HFI_PROP_NO_OUTPUT, HFI_PROP_NO_OUTPUT,
}; };
@ -726,22 +740,32 @@ struct iris_platform_data sm8550_data = {
.max_session_count = 16, .max_session_count = 16,
.max_core_mbpf = NUM_MBS_8K * 2, .max_core_mbpf = NUM_MBS_8K * 2,
.max_core_mbps = ((7680 * 4320) / 256) * 60, .max_core_mbps = ((7680 * 4320) / 256) * 60,
.input_config_params_default = .dec_input_config_params_default =
sm8550_vdec_input_config_params_default, sm8550_vdec_input_config_params_default,
.input_config_params_default_size = .dec_input_config_params_default_size =
ARRAY_SIZE(sm8550_vdec_input_config_params_default), ARRAY_SIZE(sm8550_vdec_input_config_params_default),
.input_config_params_hevc = .dec_input_config_params_hevc =
sm8550_vdec_input_config_param_hevc, sm8550_vdec_input_config_param_hevc,
.input_config_params_hevc_size = .dec_input_config_params_hevc_size =
ARRAY_SIZE(sm8550_vdec_input_config_param_hevc), ARRAY_SIZE(sm8550_vdec_input_config_param_hevc),
.input_config_params_vp9 = .dec_input_config_params_vp9 =
sm8550_vdec_input_config_param_vp9, sm8550_vdec_input_config_param_vp9,
.input_config_params_vp9_size = .dec_input_config_params_vp9_size =
ARRAY_SIZE(sm8550_vdec_input_config_param_vp9), ARRAY_SIZE(sm8550_vdec_input_config_param_vp9),
.output_config_params = .dec_output_config_params =
sm8550_vdec_output_config_params, sm8550_vdec_output_config_params,
.output_config_params_size = .dec_output_config_params_size =
ARRAY_SIZE(sm8550_vdec_output_config_params), ARRAY_SIZE(sm8550_vdec_output_config_params),
.enc_input_config_params =
sm8550_venc_input_config_params,
.enc_input_config_params_size =
ARRAY_SIZE(sm8550_venc_input_config_params),
.enc_output_config_params =
sm8550_venc_output_config_params,
.enc_output_config_params_size =
ARRAY_SIZE(sm8550_venc_output_config_params),
.dec_input_prop = sm8550_vdec_subscribe_input_properties, .dec_input_prop = sm8550_vdec_subscribe_input_properties,
.dec_input_prop_size = ARRAY_SIZE(sm8550_vdec_subscribe_input_properties), .dec_input_prop_size = ARRAY_SIZE(sm8550_vdec_subscribe_input_properties),
.dec_output_prop_avc = sm8550_vdec_subscribe_output_properties_avc, .dec_output_prop_avc = sm8550_vdec_subscribe_output_properties_avc,
@ -804,22 +828,32 @@ struct iris_platform_data sm8650_data = {
.max_session_count = 16, .max_session_count = 16,
.max_core_mbpf = NUM_MBS_8K * 2, .max_core_mbpf = NUM_MBS_8K * 2,
.max_core_mbps = ((7680 * 4320) / 256) * 60, .max_core_mbps = ((7680 * 4320) / 256) * 60,
.input_config_params_default = .dec_input_config_params_default =
sm8550_vdec_input_config_params_default, sm8550_vdec_input_config_params_default,
.input_config_params_default_size = .dec_input_config_params_default_size =
ARRAY_SIZE(sm8550_vdec_input_config_params_default), ARRAY_SIZE(sm8550_vdec_input_config_params_default),
.input_config_params_hevc = .dec_input_config_params_hevc =
sm8550_vdec_input_config_param_hevc, sm8550_vdec_input_config_param_hevc,
.input_config_params_hevc_size = .dec_input_config_params_hevc_size =
ARRAY_SIZE(sm8550_vdec_input_config_param_hevc), ARRAY_SIZE(sm8550_vdec_input_config_param_hevc),
.input_config_params_vp9 = .dec_input_config_params_vp9 =
sm8550_vdec_input_config_param_vp9, sm8550_vdec_input_config_param_vp9,
.input_config_params_vp9_size = .dec_input_config_params_vp9_size =
ARRAY_SIZE(sm8550_vdec_input_config_param_vp9), ARRAY_SIZE(sm8550_vdec_input_config_param_vp9),
.output_config_params = .dec_output_config_params =
sm8550_vdec_output_config_params, sm8550_vdec_output_config_params,
.output_config_params_size = .dec_output_config_params_size =
ARRAY_SIZE(sm8550_vdec_output_config_params), ARRAY_SIZE(sm8550_vdec_output_config_params),
.enc_input_config_params =
sm8550_venc_input_config_params,
.enc_input_config_params_size =
ARRAY_SIZE(sm8550_venc_input_config_params),
.enc_output_config_params =
sm8550_venc_output_config_params,
.enc_output_config_params_size =
ARRAY_SIZE(sm8550_venc_output_config_params),
.dec_input_prop = sm8550_vdec_subscribe_input_properties, .dec_input_prop = sm8550_vdec_subscribe_input_properties,
.dec_input_prop_size = ARRAY_SIZE(sm8550_vdec_subscribe_input_properties), .dec_input_prop_size = ARRAY_SIZE(sm8550_vdec_subscribe_input_properties),
.dec_output_prop_avc = sm8550_vdec_subscribe_output_properties_avc, .dec_output_prop_avc = sm8550_vdec_subscribe_output_properties_avc,
@ -872,22 +906,32 @@ struct iris_platform_data sm8750_data = {
.num_vpp_pipe = 4, .num_vpp_pipe = 4,
.max_session_count = 16, .max_session_count = 16,
.max_core_mbpf = NUM_MBS_8K * 2, .max_core_mbpf = NUM_MBS_8K * 2,
.input_config_params_default = .dec_input_config_params_default =
sm8550_vdec_input_config_params_default, sm8550_vdec_input_config_params_default,
.input_config_params_default_size = .dec_input_config_params_default_size =
ARRAY_SIZE(sm8550_vdec_input_config_params_default), ARRAY_SIZE(sm8550_vdec_input_config_params_default),
.input_config_params_hevc = .dec_input_config_params_hevc =
sm8550_vdec_input_config_param_hevc, sm8550_vdec_input_config_param_hevc,
.input_config_params_hevc_size = .dec_input_config_params_hevc_size =
ARRAY_SIZE(sm8550_vdec_input_config_param_hevc), ARRAY_SIZE(sm8550_vdec_input_config_param_hevc),
.input_config_params_vp9 = .dec_input_config_params_vp9 =
sm8550_vdec_input_config_param_vp9, sm8550_vdec_input_config_param_vp9,
.input_config_params_vp9_size = .dec_input_config_params_vp9_size =
ARRAY_SIZE(sm8550_vdec_input_config_param_vp9), ARRAY_SIZE(sm8550_vdec_input_config_param_vp9),
.output_config_params = .dec_output_config_params =
sm8550_vdec_output_config_params, sm8550_vdec_output_config_params,
.output_config_params_size = .dec_output_config_params_size =
ARRAY_SIZE(sm8550_vdec_output_config_params), ARRAY_SIZE(sm8550_vdec_output_config_params),
.enc_input_config_params =
sm8550_venc_input_config_params,
.enc_input_config_params_size =
ARRAY_SIZE(sm8550_venc_input_config_params),
.enc_output_config_params =
sm8550_venc_output_config_params,
.enc_output_config_params_size =
ARRAY_SIZE(sm8550_venc_output_config_params),
.dec_input_prop = sm8550_vdec_subscribe_input_properties, .dec_input_prop = sm8550_vdec_subscribe_input_properties,
.dec_input_prop_size = ARRAY_SIZE(sm8550_vdec_subscribe_input_properties), .dec_input_prop_size = ARRAY_SIZE(sm8550_vdec_subscribe_input_properties),
.dec_output_prop_avc = sm8550_vdec_subscribe_output_properties_avc, .dec_output_prop_avc = sm8550_vdec_subscribe_output_properties_avc,
@ -946,22 +990,32 @@ struct iris_platform_data qcs8300_data = {
.max_session_count = 16, .max_session_count = 16,
.max_core_mbpf = ((4096 * 2176) / 256) * 4, .max_core_mbpf = ((4096 * 2176) / 256) * 4,
.max_core_mbps = (((3840 * 2176) / 256) * 120), .max_core_mbps = (((3840 * 2176) / 256) * 120),
.input_config_params_default = .dec_input_config_params_default =
sm8550_vdec_input_config_params_default, sm8550_vdec_input_config_params_default,
.input_config_params_default_size = .dec_input_config_params_default_size =
ARRAY_SIZE(sm8550_vdec_input_config_params_default), ARRAY_SIZE(sm8550_vdec_input_config_params_default),
.input_config_params_hevc = .dec_input_config_params_hevc =
sm8550_vdec_input_config_param_hevc, sm8550_vdec_input_config_param_hevc,
.input_config_params_hevc_size = .dec_input_config_params_hevc_size =
ARRAY_SIZE(sm8550_vdec_input_config_param_hevc), ARRAY_SIZE(sm8550_vdec_input_config_param_hevc),
.input_config_params_vp9 = .dec_input_config_params_vp9 =
sm8550_vdec_input_config_param_vp9, sm8550_vdec_input_config_param_vp9,
.input_config_params_vp9_size = .dec_input_config_params_vp9_size =
ARRAY_SIZE(sm8550_vdec_input_config_param_vp9), ARRAY_SIZE(sm8550_vdec_input_config_param_vp9),
.output_config_params = .dec_output_config_params =
sm8550_vdec_output_config_params, sm8550_vdec_output_config_params,
.output_config_params_size = .dec_output_config_params_size =
ARRAY_SIZE(sm8550_vdec_output_config_params), ARRAY_SIZE(sm8550_vdec_output_config_params),
.enc_input_config_params =
sm8550_venc_input_config_params,
.enc_input_config_params_size =
ARRAY_SIZE(sm8550_venc_input_config_params),
.enc_output_config_params =
sm8550_venc_output_config_params,
.enc_output_config_params_size =
ARRAY_SIZE(sm8550_venc_output_config_params),
.dec_input_prop = sm8550_vdec_subscribe_input_properties, .dec_input_prop = sm8550_vdec_subscribe_input_properties,
.dec_input_prop_size = ARRAY_SIZE(sm8550_vdec_subscribe_input_properties), .dec_input_prop_size = ARRAY_SIZE(sm8550_vdec_subscribe_input_properties),
.dec_output_prop_avc = sm8550_vdec_subscribe_output_properties_avc, .dec_output_prop_avc = sm8550_vdec_subscribe_output_properties_avc,

View File

@ -38,6 +38,14 @@ static struct platform_inst_fw_cap inst_fw_cap_sm8250_dec[] = {
}; };
static struct platform_inst_fw_cap inst_fw_cap_sm8250_enc[] = { static struct platform_inst_fw_cap inst_fw_cap_sm8250_enc[] = {
{
.cap_id = STAGE,
.min = STAGE_1,
.max = STAGE_2,
.step_or_mask = 1,
.value = STAGE_2,
.hfi_id = HFI_PROPERTY_PARAM_WORK_MODE,
},
{ {
.cap_id = PROFILE_H264, .cap_id = PROFILE_H264,
.min = V4L2_MPEG_VIDEO_H264_PROFILE_BASELINE, .min = V4L2_MPEG_VIDEO_H264_PROFILE_BASELINE,
@ -268,6 +276,14 @@ static const u32 sm8250_vdec_input_config_param_default[] = {
HFI_PROPERTY_PARAM_BUFFER_ALLOC_MODE, HFI_PROPERTY_PARAM_BUFFER_ALLOC_MODE,
}; };
static const u32 sm8250_venc_input_config_param[] = {
HFI_PROPERTY_CONFIG_FRAME_RATE,
HFI_PROPERTY_PARAM_UNCOMPRESSED_PLANE_ACTUAL_INFO,
HFI_PROPERTY_PARAM_FRAME_SIZE,
HFI_PROPERTY_PARAM_UNCOMPRESSED_FORMAT_SELECT,
HFI_PROPERTY_PARAM_BUFFER_COUNT_ACTUAL,
};
static const u32 sm8250_dec_ip_int_buf_tbl[] = { static const u32 sm8250_dec_ip_int_buf_tbl[] = {
BUF_BIN, BUF_BIN,
BUF_SCRATCH_1, BUF_SCRATCH_1,
@ -310,10 +326,13 @@ struct iris_platform_data sm8250_data = {
.max_session_count = 16, .max_session_count = 16,
.max_core_mbpf = NUM_MBS_8K, .max_core_mbpf = NUM_MBS_8K,
.max_core_mbps = ((7680 * 4320) / 256) * 60, .max_core_mbps = ((7680 * 4320) / 256) * 60,
.input_config_params_default = .dec_input_config_params_default =
sm8250_vdec_input_config_param_default, sm8250_vdec_input_config_param_default,
.input_config_params_default_size = .dec_input_config_params_default_size =
ARRAY_SIZE(sm8250_vdec_input_config_param_default), ARRAY_SIZE(sm8250_vdec_input_config_param_default),
.enc_input_config_params = sm8250_venc_input_config_param,
.enc_input_config_params_size =
ARRAY_SIZE(sm8250_venc_input_config_param),
.dec_ip_int_buf_tbl = sm8250_dec_ip_int_buf_tbl, .dec_ip_int_buf_tbl = sm8250_dec_ip_int_buf_tbl,
.dec_ip_int_buf_tbl_size = ARRAY_SIZE(sm8250_dec_ip_int_buf_tbl), .dec_ip_int_buf_tbl_size = ARRAY_SIZE(sm8250_dec_ip_int_buf_tbl),

View File

@ -7,9 +7,11 @@
#include <media/v4l2-event.h> #include <media/v4l2-event.h>
#include <media/v4l2-mem2mem.h> #include <media/v4l2-mem2mem.h>
#include "iris_common.h"
#include "iris_instance.h" #include "iris_instance.h"
#include "iris_vb2.h" #include "iris_vb2.h"
#include "iris_vdec.h" #include "iris_vdec.h"
#include "iris_venc.h"
#include "iris_power.h" #include "iris_power.h"
static int iris_check_inst_mbpf(struct iris_inst *inst) static int iris_check_inst_mbpf(struct iris_inst *inst)
@ -174,19 +176,35 @@ int iris_vb2_start_streaming(struct vb2_queue *q, unsigned int count)
if (ret) if (ret)
goto error; goto error;
if (V4L2_TYPE_IS_OUTPUT(q->type)) if (V4L2_TYPE_IS_OUTPUT(q->type)) {
ret = iris_vdec_streamon_input(inst); if (inst->domain == DECODER)
else if (V4L2_TYPE_IS_CAPTURE(q->type)) ret = iris_vdec_streamon_input(inst);
ret = iris_vdec_streamon_output(inst); else
ret = iris_venc_streamon_input(inst);
} else if (V4L2_TYPE_IS_CAPTURE(q->type)) {
if (inst->domain == DECODER)
ret = iris_vdec_streamon_output(inst);
else
ret = iris_venc_streamon_output(inst);
}
if (ret) if (ret)
goto error; goto error;
buf_type = iris_v4l2_type_to_driver(q->type); buf_type = iris_v4l2_type_to_driver(q->type);
if (inst->state == IRIS_INST_STREAMING) if (inst->domain == DECODER) {
ret = iris_queue_internal_deferred_buffers(inst, BUF_DPB); if (inst->state == IRIS_INST_STREAMING)
if (!ret) ret = iris_queue_internal_deferred_buffers(inst, BUF_DPB);
ret = iris_queue_deferred_buffers(inst, buf_type); if (!ret)
ret = iris_queue_deferred_buffers(inst, buf_type);
} else {
if (inst->state == IRIS_INST_STREAMING) {
ret = iris_queue_deferred_buffers(inst, BUF_INPUT);
if (!ret)
ret = iris_queue_deferred_buffers(inst, BUF_OUTPUT);
}
}
if (ret) if (ret)
goto error; goto error;
@ -218,7 +236,7 @@ void iris_vb2_stop_streaming(struct vb2_queue *q)
!V4L2_TYPE_IS_CAPTURE(q->type)) !V4L2_TYPE_IS_CAPTURE(q->type))
goto exit; goto exit;
ret = iris_vdec_session_streamoff(inst, q->type); ret = iris_session_streamoff(inst, q->type);
if (ret) if (ret)
goto exit; goto exit;

View File

@ -7,6 +7,7 @@
#include <media/v4l2-mem2mem.h> #include <media/v4l2-mem2mem.h>
#include "iris_buffer.h" #include "iris_buffer.h"
#include "iris_common.h"
#include "iris_ctrls.h" #include "iris_ctrls.h"
#include "iris_instance.h" #include "iris_instance.h"
#include "iris_power.h" #include "iris_power.h"
@ -312,125 +313,6 @@ void iris_vdec_src_change(struct iris_inst *inst)
v4l2_event_queue_fh(&inst->fh, &event); v4l2_event_queue_fh(&inst->fh, &event);
} }
static void iris_vdec_flush_deferred_buffers(struct iris_inst *inst,
enum iris_buffer_type type)
{
struct v4l2_m2m_ctx *m2m_ctx = inst->m2m_ctx;
struct v4l2_m2m_buffer *buffer, *n;
struct iris_buffer *buf;
if (type == BUF_INPUT) {
v4l2_m2m_for_each_src_buf_safe(m2m_ctx, buffer, n) {
buf = to_iris_buffer(&buffer->vb);
if (buf->attr & BUF_ATTR_DEFERRED) {
if (!(buf->attr & BUF_ATTR_BUFFER_DONE)) {
buf->attr |= BUF_ATTR_BUFFER_DONE;
buf->data_size = 0;
iris_vb2_buffer_done(inst, buf);
}
}
}
} else {
v4l2_m2m_for_each_dst_buf_safe(m2m_ctx, buffer, n) {
buf = to_iris_buffer(&buffer->vb);
if (buf->attr & BUF_ATTR_DEFERRED) {
if (!(buf->attr & BUF_ATTR_BUFFER_DONE)) {
buf->attr |= BUF_ATTR_BUFFER_DONE;
buf->data_size = 0;
iris_vb2_buffer_done(inst, buf);
}
}
}
}
}
static void iris_vdec_kill_session(struct iris_inst *inst)
{
const struct iris_hfi_command_ops *hfi_ops = inst->core->hfi_ops;
if (!inst->session_id)
return;
hfi_ops->session_close(inst);
iris_inst_change_state(inst, IRIS_INST_ERROR);
}
int iris_vdec_session_streamoff(struct iris_inst *inst, u32 plane)
{
const struct iris_hfi_command_ops *hfi_ops = inst->core->hfi_ops;
enum iris_buffer_type buffer_type;
int ret;
switch (plane) {
case V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE:
buffer_type = BUF_INPUT;
break;
case V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE:
buffer_type = BUF_OUTPUT;
break;
default:
return -EINVAL;
}
ret = hfi_ops->session_stop(inst, plane);
if (ret)
goto error;
ret = iris_inst_state_change_streamoff(inst, plane);
if (ret)
goto error;
iris_vdec_flush_deferred_buffers(inst, buffer_type);
return 0;
error:
iris_vdec_kill_session(inst);
iris_vdec_flush_deferred_buffers(inst, buffer_type);
return ret;
}
static int iris_vdec_process_streamon_input(struct iris_inst *inst)
{
const struct iris_hfi_command_ops *hfi_ops = inst->core->hfi_ops;
enum iris_inst_sub_state set_sub_state = 0;
int ret;
iris_scale_power(inst);
ret = hfi_ops->session_start(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
if (inst->sub_state & IRIS_INST_SUB_INPUT_PAUSE) {
ret = iris_inst_change_sub_state(inst, IRIS_INST_SUB_INPUT_PAUSE, 0);
if (ret)
return ret;
}
if (inst->sub_state & IRIS_INST_SUB_DRC ||
inst->sub_state & IRIS_INST_SUB_DRAIN ||
inst->sub_state & IRIS_INST_SUB_FIRST_IPSC) {
if (!(inst->sub_state & IRIS_INST_SUB_INPUT_PAUSE)) {
if (hfi_ops->session_pause) {
ret = hfi_ops->session_pause(inst,
V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
}
set_sub_state = IRIS_INST_SUB_INPUT_PAUSE;
}
}
ret = iris_inst_state_change_streamon(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
return iris_inst_change_sub_state(inst, 0, set_sub_state);
}
int iris_vdec_streamon_input(struct iris_inst *inst) int iris_vdec_streamon_input(struct iris_inst *inst)
{ {
int ret; int ret;
@ -457,71 +339,7 @@ int iris_vdec_streamon_input(struct iris_inst *inst)
if (ret) if (ret)
return ret; return ret;
return iris_vdec_process_streamon_input(inst); return iris_process_streamon_input(inst);
}
static int iris_vdec_process_streamon_output(struct iris_inst *inst)
{
const struct iris_hfi_command_ops *hfi_ops = inst->core->hfi_ops;
bool drain_active = false, drc_active = false;
enum iris_inst_sub_state clear_sub_state = 0;
int ret = 0;
iris_scale_power(inst);
drain_active = inst->sub_state & IRIS_INST_SUB_DRAIN &&
inst->sub_state & IRIS_INST_SUB_DRAIN_LAST;
drc_active = inst->sub_state & IRIS_INST_SUB_DRC &&
inst->sub_state & IRIS_INST_SUB_DRC_LAST;
if (drc_active)
clear_sub_state = IRIS_INST_SUB_DRC | IRIS_INST_SUB_DRC_LAST;
else if (drain_active)
clear_sub_state = IRIS_INST_SUB_DRAIN | IRIS_INST_SUB_DRAIN_LAST;
if (inst->sub_state & IRIS_INST_SUB_INPUT_PAUSE) {
ret = iris_alloc_and_queue_input_int_bufs(inst);
if (ret)
return ret;
ret = iris_set_stage(inst, STAGE);
if (ret)
return ret;
ret = iris_set_pipe(inst, PIPE);
if (ret)
return ret;
}
if (inst->state == IRIS_INST_INPUT_STREAMING &&
inst->sub_state & IRIS_INST_SUB_INPUT_PAUSE) {
if (!drain_active)
ret = hfi_ops->session_resume_drc(inst,
V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
else if (hfi_ops->session_resume_drain)
ret = hfi_ops->session_resume_drain(inst,
V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
clear_sub_state |= IRIS_INST_SUB_INPUT_PAUSE;
}
if (inst->sub_state & IRIS_INST_SUB_FIRST_IPSC)
clear_sub_state |= IRIS_INST_SUB_FIRST_IPSC;
ret = hfi_ops->session_start(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
if (ret)
return ret;
if (inst->sub_state & IRIS_INST_SUB_OUTPUT_PAUSE)
clear_sub_state |= IRIS_INST_SUB_OUTPUT_PAUSE;
ret = iris_inst_state_change_streamon(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
if (ret)
return ret;
inst->last_buffer_dequeued = false;
return iris_inst_change_sub_state(inst, clear_sub_state, 0);
} }
int iris_vdec_streamon_output(struct iris_inst *inst) int iris_vdec_streamon_output(struct iris_inst *inst)
@ -543,7 +361,7 @@ int iris_vdec_streamon_output(struct iris_inst *inst)
if (ret) if (ret)
return ret; return ret;
ret = iris_vdec_process_streamon_output(inst); ret = iris_process_streamon_output(inst);
if (ret) if (ret)
goto error; goto error;
@ -554,7 +372,7 @@ int iris_vdec_streamon_output(struct iris_inst *inst)
return ret; return ret;
error: error:
iris_vdec_session_streamoff(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE); iris_session_streamoff(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
return ret; return ret;
} }

View File

@ -21,6 +21,5 @@ int iris_vdec_streamon_output(struct iris_inst *inst);
int iris_vdec_qbuf(struct iris_inst *inst, struct vb2_v4l2_buffer *vbuf); int iris_vdec_qbuf(struct iris_inst *inst, struct vb2_v4l2_buffer *vbuf);
int iris_vdec_start_cmd(struct iris_inst *inst); int iris_vdec_start_cmd(struct iris_inst *inst);
int iris_vdec_stop_cmd(struct iris_inst *inst); int iris_vdec_stop_cmd(struct iris_inst *inst);
int iris_vdec_session_streamoff(struct iris_inst *inst, u32 plane);
#endif #endif

View File

@ -7,6 +7,7 @@
#include <media/v4l2-mem2mem.h> #include <media/v4l2-mem2mem.h>
#include "iris_buffer.h" #include "iris_buffer.h"
#include "iris_common.h"
#include "iris_ctrls.h" #include "iris_ctrls.h"
#include "iris_instance.h" #include "iris_instance.h"
#include "iris_venc.h" #include "iris_venc.h"
@ -425,3 +426,34 @@ int iris_venc_g_param(struct iris_inst *inst, struct v4l2_streamparm *s_parm)
return 0; return 0;
} }
int iris_venc_streamon_input(struct iris_inst *inst)
{
int ret;
ret = iris_set_properties(inst, V4L2_BUF_TYPE_VIDEO_OUTPUT_MPLANE);
if (ret)
return ret;
return iris_process_streamon_input(inst);
}
int iris_venc_streamon_output(struct iris_inst *inst)
{
int ret;
ret = iris_set_properties(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
if (ret)
goto error;
ret = iris_process_streamon_output(inst);
if (ret)
goto error;
return ret;
error:
iris_session_streamoff(inst, V4L2_BUF_TYPE_VIDEO_CAPTURE_MPLANE);
return ret;
}

View File

@ -18,5 +18,7 @@ int iris_venc_subscribe_event(struct iris_inst *inst, const struct v4l2_event_su
int iris_venc_s_selection(struct iris_inst *inst, struct v4l2_selection *s); int iris_venc_s_selection(struct iris_inst *inst, struct v4l2_selection *s);
int iris_venc_g_param(struct iris_inst *inst, struct v4l2_streamparm *s_parm); int iris_venc_g_param(struct iris_inst *inst, struct v4l2_streamparm *s_parm);
int iris_venc_s_param(struct iris_inst *inst, struct v4l2_streamparm *s_parm); int iris_venc_s_param(struct iris_inst *inst, struct v4l2_streamparm *s_parm);
int iris_venc_streamon_input(struct iris_inst *inst);
int iris_venc_streamon_output(struct iris_inst *inst);
#endif #endif

View File

@ -656,6 +656,8 @@ static const struct v4l2_ioctl_ops iris_v4l2_ioctl_ops_enc = {
.vidioc_s_selection = iris_s_selection, .vidioc_s_selection = iris_s_selection,
.vidioc_s_parm = iris_s_parm, .vidioc_s_parm = iris_s_parm,
.vidioc_g_parm = iris_g_parm, .vidioc_g_parm = iris_g_parm,
.vidioc_streamon = v4l2_m2m_ioctl_streamon,
.vidioc_streamoff = v4l2_m2m_ioctl_streamoff,
}; };
void iris_init_ops(struct iris_core *core) void iris_init_ops(struct iris_core *core)