Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit bbd0455e authored by Linux Build Service Account's avatar Linux Build Service Account Committed by Gerrit - the friendly Code Review server
Browse files

Merge "msm: vidc: Add H.264 MVC codec"

parents 0381505f 96fa9f89
Loading
Loading
Loading
Loading
+86 −1
Original line number Diff line number Diff line
@@ -33,6 +33,7 @@ static int profile_table[] = {
	[ilog2(HAL_H264_PROFILE_CONSTRAINED_HIGH)] =
		HFI_H264_PROFILE_CONSTRAINED_HIGH,
	[ilog2(HAL_VPX_PROFILE_VERSION_1)] = HFI_VPX_PROFILE_VERSION_1,
	[ilog2(HAL_MVC_PROFILE_STEREO_HIGH)] = HFI_H264_PROFILE_STEREO_HIGH,
};

static int entropy_mode[] = {
@@ -106,6 +107,74 @@ static inline int hal_to_hfi_type(int property, int hal_type)
	}
}

static inline u32 get_hfi_layout(enum hal_buffer_layout_type hal_buf_layout)
{
	u32 hfi_layout;
	switch (hal_buf_layout) {
	case HAL_BUFFER_LAYOUT_TOP_BOTTOM:
		hfi_layout = HFI_MVC_BUFFER_LAYOUT_TOP_BOTTOM;
		break;
	case HAL_BUFFER_LAYOUT_SEQ:
		hfi_layout = HFI_MVC_BUFFER_LAYOUT_SEQ;
		break;
	default:
		dprintk(VIDC_ERR, "Invalid buffer layout: 0x%x\n",
			hal_buf_layout);
		hfi_layout = HFI_MVC_BUFFER_LAYOUT_SEQ;
		break;
	}
	return hfi_layout;
}

static inline u32 get_hfi_codec(enum hal_video_codec hal_codec)
{
	u32 hfi_codec;
	switch (hal_codec) {
	case HAL_VIDEO_CODEC_MVC:
	case HAL_VIDEO_CODEC_H264:
		hfi_codec = HFI_VIDEO_CODEC_H264;
		break;
	case HAL_VIDEO_CODEC_H263:
		hfi_codec = HFI_VIDEO_CODEC_H263;
		break;
	case HAL_VIDEO_CODEC_MPEG1:
		hfi_codec = HFI_VIDEO_CODEC_MPEG1;
		break;
	case HAL_VIDEO_CODEC_MPEG2:
		hfi_codec = HFI_VIDEO_CODEC_MPEG2;
		break;
	case HAL_VIDEO_CODEC_MPEG4:
		hfi_codec = HFI_VIDEO_CODEC_MPEG4;
		break;
	case HAL_VIDEO_CODEC_DIVX_311:
		hfi_codec = HFI_VIDEO_CODEC_DIVX_311;
		break;
	case HAL_VIDEO_CODEC_DIVX:
		hfi_codec = HFI_VIDEO_CODEC_DIVX;
		break;
	case HAL_VIDEO_CODEC_VC1:
		hfi_codec = HFI_VIDEO_CODEC_VC1;
		break;
	case HAL_VIDEO_CODEC_SPARK:
		hfi_codec = HFI_VIDEO_CODEC_SPARK;
		break;
	case HAL_VIDEO_CODEC_VP8:
		hfi_codec = HFI_VIDEO_CODEC_VP8;
		break;
	case HAL_VIDEO_CODEC_HEVC:
		hfi_codec = HFI_VIDEO_CODEC_HEVC;
		break;
	case HAL_VIDEO_CODEC_HEVC_HYBRID:
		hfi_codec = HFI_VIDEO_CODEC_HEVC_HYBRID;
		break;
	default:
		dprintk(VIDC_ERR, "Invalid codec 0x%x\n", hal_codec);
		hfi_codec = 0;
		break;
	}
	return hfi_codec;
}

int create_pkt_cmd_sys_init(struct hfi_cmd_sys_init_packet *pkt,
			   u32 arch_type)
{
@@ -246,7 +315,9 @@ inline int create_pkt_cmd_sys_session_init(
	pkt->packet_type = HFI_CMD_SYS_SESSION_INIT;
	pkt->session_id = session_id;
	pkt->session_domain = session_domain;
	pkt->session_codec = session_codec;
	pkt->session_codec = get_hfi_codec(session_codec);
	if (!pkt->session_codec)
		return -EINVAL;

	return rc;
}
@@ -1498,6 +1569,20 @@ int create_pkt_cmd_session_set_property(
		pkt->size += sizeof(u32) + sizeof(struct hfi_scs_threshold);
		break;
	}
	case HAL_PARAM_MVC_BUFFER_LAYOUT:
	{
		struct hfi_mvc_buffer_layout_descp_type *hfi;
		struct hal_mvc_buffer_layout *layout_info = pdata;
		pkt->rg_property_data[0] = HFI_PROPERTY_PARAM_MVC_BUFFER_LAYOUT;
		hfi = (struct hfi_mvc_buffer_layout_descp_type *)
			&pkt->rg_property_data[1];
		hfi->layout_type = get_hfi_layout(layout_info->layout_type);
		hfi->bright_view_first = layout_info->bright_view_first;
		hfi->ngap = layout_info->ngap;
		pkt->size += sizeof(u32) +
			sizeof(struct hfi_mvc_buffer_layout_descp_type);
		break;
	}
	/* FOLLOWING PROPERTIES ARE NOT IMPLEMENTED IN CORE YET */
	case HAL_CONFIG_BUFFER_REQUIREMENTS:
	case HAL_CONFIG_PRIORITY:
+79 −2
Original line number Diff line number Diff line
@@ -119,6 +119,11 @@ static const char *const vp8_profile_level[] = {
	"3.0",
};

static const char *const mpeg_vidc_video_h264_mvc_layout[] = {
	"Frame packing arrangement sequential",
	"Frame packing arrangement top-bottom",
};

static struct msm_vidc_ctrl msm_vdec_ctrls[] = {
	{
		.id = V4L2_CID_MPEG_VIDC_VIDEO_STREAM_FORMAT,
@@ -380,23 +385,23 @@ static struct msm_vidc_ctrl msm_vdec_ctrls[] = {
		.id = V4L2_CID_MPEG_VIDEO_H264_PROFILE,
		.name = "H264 Profile",
		.type = V4L2_CTRL_TYPE_MENU,
		.minimum = V4L2_MPEG_VIDEO_H264_PROFILE_BASELINE,
		.maximum = V4L2_MPEG_VIDEO_H264_PROFILE_CONSTRAINED_HIGH,
		.default_value = V4L2_MPEG_VIDEO_H264_PROFILE_BASELINE,
		.menu_skip_mask = 0,
		.cluster = 0,
		.flags = V4L2_CTRL_FLAG_VOLATILE,
		.qmenu = NULL,
	},
	{
		.id = V4L2_CID_MPEG_VIDEO_H264_LEVEL,
		.name = "H264 Level",
		.type = V4L2_CTRL_TYPE_MENU,
		.minimum = V4L2_MPEG_VIDEO_H264_LEVEL_1_0,
		.maximum = V4L2_MPEG_VIDEO_H264_LEVEL_5_2,
		.default_value = V4L2_MPEG_VIDEO_H264_LEVEL_1_0,
		.menu_skip_mask = 0,
		.cluster = 0,
		.flags = V4L2_CTRL_FLAG_VOLATILE,
		.qmenu = NULL,
	},
	{
		.id = V4L2_CID_MPEG_VIDC_VIDEO_H263_PROFILE,
@@ -490,6 +495,19 @@ static struct msm_vidc_ctrl msm_vdec_ctrls[] = {
		.qmenu = NULL,
		.cluster = 0,
	},
	{
		.id = V4L2_CID_MPEG_VIDC_VIDEO_MVC_BUFFER_LAYOUT,
		.name = "MVC buffer layout",
		.type = V4L2_CTRL_TYPE_MENU,
		.maximum = V4L2_MPEG_VIDC_VIDEO_MVC_TOP_BOTTOM,
		.default_value = V4L2_MPEG_VIDC_VIDEO_MVC_SEQUENTIAL,
		.menu_skip_mask = ~(
			(1 << V4L2_MPEG_VIDC_VIDEO_MVC_SEQUENTIAL) |
			(1 << V4L2_MPEG_VIDC_VIDEO_MVC_TOP_BOTTOM)
			),
		.qmenu = mpeg_vidc_video_h264_mvc_layout,
		.cluster = 0,
	},
};

#define NUM_CTRLS ARRAY_SIZE(msm_vdec_ctrls)
@@ -506,6 +524,43 @@ static u32 get_frame_size_compressed(int plane,
	return (width * height * 3/2)/2;
}

static int is_ctrl_valid_for_codec(struct msm_vidc_inst *inst,
					struct v4l2_ctrl *ctrl)
{
	int rc = 0;
	switch (ctrl->id) {
	case V4L2_CID_MPEG_VIDC_VIDEO_MVC_BUFFER_LAYOUT:
		if (inst->fmts[OUTPUT_PORT]->fourcc != V4L2_PIX_FMT_H264_MVC) {
			dprintk(VIDC_ERR, "Control 0x%x only valid for MVC",
					ctrl->id);
			rc = -ENOTSUPP;
			break;
		}
		break;
	case V4L2_CID_MPEG_VIDEO_H264_PROFILE:
		if (inst->fmts[OUTPUT_PORT]->fourcc == V4L2_PIX_FMT_H264_MVC &&
			ctrl->val != V4L2_MPEG_VIDEO_H264_PROFILE_STEREO_HIGH) {
			dprintk(VIDC_ERR, "Profile 0x%x not supported for MVC",
					ctrl->val);
			rc = -ENOTSUPP;
			break;
		}
		break;
	case V4L2_CID_MPEG_VIDEO_H264_LEVEL:
		if (inst->fmts[OUTPUT_PORT]->fourcc == V4L2_PIX_FMT_H264_MVC &&
			ctrl->val >= V4L2_MPEG_VIDEO_H264_LEVEL_5_2) {
			dprintk(VIDC_ERR, "Level 0x%x not supported for MVC",
					ctrl->val);
			rc = -ENOTSUPP;
			break;
		}
		break;
	default:
		break;
	}
	return rc;
}

struct msm_vidc_format vdec_formats[] = {
	{
		.name = "YCbCr Semiplanar 4:2:0",
@@ -563,6 +618,14 @@ struct msm_vidc_format vdec_formats[] = {
		.get_frame_size = get_frame_size_compressed,
		.type = OUTPUT_PORT,
	},
	{
		.name = "H264_MVC",
		.description = "H264_MVC compressed format",
		.fourcc = V4L2_PIX_FMT_H264_MVC,
		.num_planes = 1,
		.get_frame_size = get_frame_size_compressed,
		.type = OUTPUT_PORT,
	},
	{
		.name = "HEVC",
		.description = "HEVC compressed format",
@@ -1765,6 +1828,7 @@ static int try_set_ctrl(struct msm_vidc_inst *inst, struct v4l2_ctrl *ctrl)
	struct hal_buffer_alloc_mode alloc_mode;
	struct hal_multi_stream multi_stream;
	struct hfi_scs_threshold scs_threshold;
	struct hal_mvc_buffer_layout layout;

	if (!inst || !inst->core || !inst->core->device) {
		dprintk(VIDC_ERR, "%s invalid parameters", __func__);
@@ -1772,6 +1836,10 @@ static int try_set_ctrl(struct msm_vidc_inst *inst, struct v4l2_ctrl *ctrl)
	}
	hdev = inst->core->device;

	rc = is_ctrl_valid_for_codec(inst, ctrl);
	if (rc)
		return rc;

	switch (ctrl->id) {
	case V4L2_CID_MPEG_VIDC_VIDEO_STREAM_FORMAT:
		property_id =
@@ -1961,6 +2029,15 @@ static int try_set_ctrl(struct msm_vidc_inst *inst, struct v4l2_ctrl *ctrl)
		scs_threshold.threshold_value = ctrl->val;
		pdata = &scs_threshold;
		break;
	case V4L2_CID_MPEG_VIDC_VIDEO_MVC_BUFFER_LAYOUT:
	{
		property_id = HAL_PARAM_MVC_BUFFER_LAYOUT;
		layout.layout_type = msm_comm_get_hal_buffer_layout(ctrl->val);
		layout.bright_view_first = 0;
		layout.ngap = 0;
		pdata = &layout;
		break;
	}
	default:
		break;
	}
+20 −4
Original line number Diff line number Diff line
@@ -1633,6 +1633,9 @@ enum hal_video_codec get_hal_codec_type(int fourcc)
	case V4L2_PIX_FMT_H264_NO_SC:
		codec = HAL_VIDEO_CODEC_H264;
		break;
	case V4L2_PIX_FMT_H264_MVC:
		codec = HAL_VIDEO_CODEC_MVC;
		break;
	case V4L2_PIX_FMT_H263:
		codec = HAL_VIDEO_CODEC_H263;
		break;
@@ -1658,10 +1661,6 @@ enum hal_video_codec get_hal_codec_type(int fourcc)
	case V4L2_PIX_FMT_DIVX:
		codec = HAL_VIDEO_CODEC_DIVX;
		break;
		/*HAL_VIDEO_CODEC_MVC
		  HAL_VIDEO_CODEC_SPARK
		  HAL_VIDEO_CODEC_VP6
		  HAL_VIDEO_CODEC_VP7*/
	case V4L2_PIX_FMT_HEVC:
		codec = HAL_VIDEO_CODEC_HEVC;
		break;
@@ -3214,6 +3213,23 @@ enum hal_extradata_id msm_comm_get_hal_extradata_index(
	return ret;
};

enum hal_buffer_layout_type msm_comm_get_hal_buffer_layout(
	enum v4l2_mpeg_vidc_video_mvc_layout index)
{
	int ret = 0;
	switch (index) {
	case V4L2_MPEG_VIDC_VIDEO_MVC_SEQUENTIAL:
		ret = HAL_BUFFER_LAYOUT_SEQ;
		break;
	case V4L2_MPEG_VIDC_VIDEO_MVC_TOP_BOTTOM:
		ret = HAL_BUFFER_LAYOUT_TOP_BOTTOM;
		break;
	default:
		break;
	}
	return ret;
}

int msm_comm_get_domain_partition(struct msm_vidc_inst *inst, u32 flags,
	enum v4l2_buf_type buf_type, int *domain, int *partition)
{
+2 −0
Original line number Diff line number Diff line
@@ -42,6 +42,8 @@ int msm_comm_release_persist_buffers(struct msm_vidc_inst *inst);
int msm_comm_force_cleanup(struct msm_vidc_inst *inst);
enum hal_extradata_id msm_comm_get_hal_extradata_index(
	enum v4l2_mpeg_vidc_extradata index);
enum hal_buffer_layout_type msm_comm_get_hal_buffer_layout(
	enum v4l2_mpeg_vidc_video_mvc_layout index);
int msm_comm_get_domain_partition(struct msm_vidc_inst *inst, u32 flags,
	enum v4l2_buf_type buf_type, int *domain, int *partition);
struct hal_buffer_requirements *get_buff_req_buffer(
+13 −1
Original line number Diff line number Diff line
@@ -185,6 +185,7 @@ enum hal_property {
	HAL_PARAM_VDEC_CONCEAL_COLOR,
	HAL_PARAM_VDEC_SCS_THRESHOLD,
	HAL_PARAM_GET_BUFFER_REQUIREMENTS,
	HAL_PARAM_MVC_BUFFER_LAYOUT,
};

enum hal_domain {
@@ -392,7 +393,6 @@ enum hal_divx_profile {

enum hal_mvc_profile {
	HAL_MVC_PROFILE_STEREO_HIGH  = 0x00000001,
	HAL_MVC_PROFILE_MV_HIGH      = 0x00000002,
	HAL_UNUSED_MVC_PROFILE = 0x10000000,
};

@@ -788,6 +788,18 @@ struct hal_multi_view_format {
	u32 rg_view_order[1];
};

enum hal_buffer_layout_type {
	HAL_BUFFER_LAYOUT_TOP_BOTTOM,
	HAL_BUFFER_LAYOUT_SEQ,
	HAL_UNUSED_BUFFER_LAYOUT = 0x10000000,
};

struct hal_mvc_buffer_layout {
	enum hal_buffer_layout_type layout_type;
	u32 bright_view_first;
	u32 ngap;
};

struct hal_seq_header_info {
	u32 nax_header_len;
};
Loading