summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorPraveen Chavan <pchavan@codeaurora.org>2013-10-10 19:23:45 -0700
committerEd Tam <etam@google.com>2013-10-12 16:39:26 +0000
commitac64d24c26fd060fb3e2b1c9a1db4ab18dbf7c5d (patch)
tree0bdbfdcfac5ba31181da01ae36869ae34015726d
parent7e25ac152e83fc589f26de1b68ba923075746197 (diff)
downloadandroid_hardware_qcom_media-ac64d24c26fd060fb3e2b1c9a1db4ab18dbf7c5d.tar.gz
android_hardware_qcom_media-ac64d24c26fd060fb3e2b1c9a1db4ab18dbf7c5d.tar.bz2
android_hardware_qcom_media-ac64d24c26fd060fb3e2b1c9a1db4ab18dbf7c5d.zip
mm-video: support adaptive playback mode
In this mode client checks and sets an extension to indicate that the content can change resolutuion, within the pre- announced maximum height/width. Component overallocates buffers for the max resolution and dbp, and notifies client of any crop change when resolution changes within bounds. Reoslution changes beyond set max width/height will result in port-reconfiguration notification, while adapting to the new resolution Bug: 10192531 Ack-ed by Deepak Verma <dverma@codeaurora.org> Change-Id: I3e4deb10b3fe89398ee0ddc3a0f46d5fc22feab8
-rw-r--r--mm-core/inc/OMX_QCOMExtns.h2
-rw-r--r--mm-video-legacy/vidc/vdec/inc/omx_vdec.h2
-rw-r--r--mm-video-legacy/vidc/vdec/src/omx_vdec.cpp144
3 files changed, 127 insertions, 21 deletions
diff --git a/mm-core/inc/OMX_QCOMExtns.h b/mm-core/inc/OMX_QCOMExtns.h
index bef762d1..fb12082a 100644
--- a/mm-core/inc/OMX_QCOMExtns.h
+++ b/mm-core/inc/OMX_QCOMExtns.h
@@ -406,6 +406,8 @@ enum OMX_QCOM_EXTN_INDEXTYPE
OMX_QcomIndexParamSequenceHeaderWithIDR = 0x7F00002A,
OMX_QcomIndexParamEnableVUIStreamRestrictFlag = 0x7F00002B,
+
+ OMX_GoogleAndroidIndexPrepareForAdaptivePlayback = 0x7F00002C,
};
/**
diff --git a/mm-video-legacy/vidc/vdec/inc/omx_vdec.h b/mm-video-legacy/vidc/vdec/inc/omx_vdec.h
index f3cfa5b9..bb5c40ef 100644
--- a/mm-video-legacy/vidc/vdec/inc/omx_vdec.h
+++ b/mm-video-legacy/vidc/vdec/inc/omx_vdec.h
@@ -823,6 +823,8 @@ private:
// added for smooth streaming
private_handle_t * native_buffer[MAX_NUM_INPUT_OUTPUT_BUFFERS];
bool m_use_smoothstreaming;
+ OMX_U32 m_smoothstreaming_height;
+ OMX_U32 m_smoothstreaming_width;
unsigned int m_fill_output_msg;
class allocate_color_convert_buf {
diff --git a/mm-video-legacy/vidc/vdec/src/omx_vdec.cpp b/mm-video-legacy/vidc/vdec/src/omx_vdec.cpp
index e1ab8fb7..1b20c71a 100644
--- a/mm-video-legacy/vidc/vdec/src/omx_vdec.cpp
+++ b/mm-video-legacy/vidc/vdec/src/omx_vdec.cpp
@@ -149,6 +149,14 @@ char ouputextradatafilename [] = "/data/extradata";
bool omx_vdec::m_secure_display = false;
+#ifdef MAX_RES_1080P
+static const OMX_U32 kMaxSmoothStreamingWidth = 1920;
+static const OMX_U32 kMaxSmoothStreamingHeight = 1088;
+#else
+static const OMX_U32 kMaxSmoothStreamingWidth = 1280;
+static const OMX_U32 kMaxSmoothStreamingHeight = 720;
+#endif
+
void* async_message_thread (void *input)
{
struct vdec_ioctl_msg ioctl_msg;
@@ -492,6 +500,8 @@ omx_vdec::omx_vdec(): m_state(OMX_StateInvalid),
,m_desc_buffer_ptr(NULL)
,m_extradata(NULL)
,m_use_smoothstreaming(false)
+ ,m_smoothstreaming_height(0)
+ ,m_smoothstreaming_width(0)
{
/* Assumption is that , to begin with , we have all the frames with decoder */
DEBUG_PRINT_HIGH("In OMX vdec Constructor");
@@ -1440,15 +1450,16 @@ OMX_ERRORTYPE omx_vdec::component_init(OMX_STRING role)
VDEC_IOCTL_SET_CONT_ON_RECONFIG);
if(rc < 0) {
DEBUG_PRINT_ERROR("Failed to enable Smooth Streaming on driver.");
+ } else {
+ m_smoothstreaming_width = kMaxSmoothStreamingWidth;
+ m_smoothstreaming_height = kMaxSmoothStreamingHeight;
}
}
-#ifdef MAX_RES_720P
- update_resolution(1280, 720);
-#endif
-#ifdef MAX_RES_1080P
- update_resolution(1920, 1088);
-#endif
+ if (m_use_smoothstreaming)
+ update_resolution(kMaxSmoothStreamingWidth, kMaxSmoothStreamingHeight);
+ else
+ update_resolution(176, 144);
ioctl_msg.in = &drv_ctx.video_resolution;
ioctl_msg.out = NULL;
@@ -3089,20 +3100,28 @@ OMX_ERRORTYPE omx_vdec::set_parameter(OMX_IN OMX_HANDLETYPE hComp,
portDefn->format.video.nFrameWidth,
portDefn->format.video.nFrameHeight);
if (portDefn->format.video.nFrameHeight != 0x0 &&
- portDefn->format.video.nFrameWidth != 0x0)
- {
- update_resolution(portDefn->format.video.nFrameWidth,
- portDefn->format.video.nFrameHeight);
- ioctl_msg.in = &drv_ctx.video_resolution;
- ioctl_msg.out = NULL;
- if (ioctl (drv_ctx.video_driver_fd, VDEC_IOCTL_SET_PICRES,
- (void*)&ioctl_msg) < 0)
- {
- DEBUG_PRINT_ERROR("\n Set Resolution failed");
- eRet = OMX_ErrorUnsupportedSetting;
- }
- else
- eRet = get_buffer_req(&drv_ctx.op_buf);
+ portDefn->format.video.nFrameWidth != 0x0) {
+ if (m_use_smoothstreaming &&
+ ((portDefn->format.video.nFrameHeight * portDefn->format.video.nFrameWidth) <
+ (m_smoothstreaming_height * m_smoothstreaming_width))) {
+
+ update_resolution(m_smoothstreaming_width, m_smoothstreaming_height);
+ DEBUG_PRINT_HIGH("NOTE: Setting initial resolution [%u x %u] in"
+ "smothstreaming mode [%u x %u]",
+ portDefn->format.video.nFrameWidth, portDefn->format.video.nFrameHeight,
+ drv_ctx.video_resolution.frame_width, drv_ctx.video_resolution.frame_height);
+ } else {
+ update_resolution(portDefn->format.video.nFrameWidth,
+ portDefn->format.video.nFrameHeight);
+ }
+ ioctl_msg.in = &drv_ctx.video_resolution;
+ ioctl_msg.out = NULL;
+ if (ioctl (drv_ctx.video_driver_fd, VDEC_IOCTL_SET_PICRES,
+ (void*)&ioctl_msg) < 0) {
+ DEBUG_PRINT_ERROR("\n Set Resolution failed");
+ eRet = OMX_ErrorUnsupportedSetting;
+ } else
+ eRet = get_buffer_req(&drv_ctx.op_buf);
}
}
else if (portDefn->nBufferCountActual >= drv_ctx.ip_buf.mincount
@@ -3560,6 +3579,66 @@ OMX_ERRORTYPE omx_vdec::set_parameter(OMX_IN OMX_HANDLETYPE hComp,
}
}
break;
+
+#if defined (_ANDROID_HONEYCOMB_) || defined (_ANDROID_ICS_)
+ case OMX_GoogleAndroidIndexPrepareForAdaptivePlayback:
+ {
+ DEBUG_PRINT_LOW("set_parameter: "
+ "OMX_GoogleAndroidIndexPrepareForAdaptivePlayback");
+ PrepareForAdaptivePlaybackParams* adaptivePlaybackParams =
+ (PrepareForAdaptivePlaybackParams *) paramData;
+ if (adaptivePlaybackParams->nPortIndex == OMX_CORE_OUTPUT_PORT_INDEX) {
+ if (!adaptivePlaybackParams->bEnable) {
+ return OMX_ErrorNone;
+ }
+ if (adaptivePlaybackParams->nMaxFrameWidth > kMaxSmoothStreamingWidth
+ || adaptivePlaybackParams->nMaxFrameHeight > kMaxSmoothStreamingHeight) {
+ DEBUG_PRINT_ERROR("Adaptive playback request exceeds max supported "
+ "resolution : [%d x %d] vs [%d x %d]",
+ adaptivePlaybackParams->nMaxFrameWidth,
+ adaptivePlaybackParams->nMaxFrameHeight,
+ kMaxSmoothStreamingWidth, kMaxSmoothStreamingHeight);
+ eRet = OMX_ErrorBadParameter;
+ } else {
+ int rc = ioctl(drv_ctx.video_driver_fd,
+ VDEC_IOCTL_SET_CONT_ON_RECONFIG);
+ if (rc < 0) {
+ DEBUG_PRINT_ERROR("Failed to enable Smooth Streaming on driver.");
+ eRet = OMX_ErrorInsufficientResources;
+ } else {
+ update_resolution(adaptivePlaybackParams->nMaxFrameWidth,
+ adaptivePlaybackParams->nMaxFrameHeight);
+
+ ioctl_msg.in = &drv_ctx.video_resolution;
+ ioctl_msg.out = NULL;
+
+ if (ioctl (drv_ctx.video_driver_fd,VDEC_IOCTL_SET_PICRES,
+ (void*)&ioctl_msg) < 0) {
+ DEBUG_PRINT_ERROR("Adaptive-playback: Set Resolution failed");
+ eRet = OMX_ErrorInsufficientResources;
+ } else {
+ eRet = get_buffer_req(&drv_ctx.op_buf);
+ if (eRet != OMX_ErrorNone) {
+ DEBUG_PRINT_ERROR("get_buffer_req(op_buf) failed!!");
+ } else {
+ DEBUG_PRINT_ERROR("Enabling Adaptive playback for %d x %d",
+ adaptivePlaybackParams->nMaxFrameWidth,
+ adaptivePlaybackParams->nMaxFrameHeight);
+ m_use_smoothstreaming = true;
+ m_smoothstreaming_width = adaptivePlaybackParams->nMaxFrameWidth;
+ m_smoothstreaming_height = adaptivePlaybackParams->nMaxFrameHeight;
+ }
+ }
+ }
+ }
+ } else {
+ DEBUG_PRINT_ERROR("Prepare for adaptive playback supported only "
+ "on output port");
+ eRet = OMX_ErrorBadParameter;
+ }
+ }
+ break;
+#endif
default:
{
DEBUG_PRINT_ERROR("Setparameter: unknown param %d\n", paramIndex);
@@ -3905,6 +3984,10 @@ OMX_ERRORTYPE omx_vdec::get_extension_index(OMX_IN OMX_HANDLETYPE hComp,
else if(!strncmp(paramName,"OMX.google.android.index.getAndroidNativeBufferUsage", sizeof("OMX.google.android.index.getAndroidNativeBufferUsage") - 1)) {
*indexType = (OMX_INDEXTYPE)OMX_GoogleAndroidIndexGetAndroidNativeBufferUsage;
}
+ else if (!strncmp(paramName,"OMX.google.android.index.prepareForAdaptivePlayback",
+ sizeof("OMX.google.android.index.prepareForAdaptivePlayback") - 1)) {
+ *indexType = (OMX_INDEXTYPE)OMX_GoogleAndroidIndexPrepareForAdaptivePlayback;
+ }
#endif
else {
DEBUG_PRINT_ERROR("Extension: %s not implemented\n", paramName);
@@ -6588,7 +6671,8 @@ OMX_ERRORTYPE omx_vdec::fill_buffer_done(OMX_HANDLETYPE hComp,
dim.sliceWidth = m_port_def.format.video.nStride;
dim.sliceHeight = m_port_def.format.video.nSliceHeight;
handle = (private_handle_t *)native_buffer[buf_index];
- DEBUG_PRINT_LOW("set metadata: update buffer geo with stride %d slice %d", dim.sliceWidth, dim.sliceHeight);
+ DEBUG_PRINT_LOW("NOTE: set metadata: update buffer geo with "
+ "stride %d slice %d", dim.sliceWidth, dim.sliceHeight);
setMetaData(handle, UPDATE_BUFFER_GEOMETRY, (void*)&dim);
}
@@ -7773,9 +7857,26 @@ OMX_ERRORTYPE omx_vdec::start_port_reconfig()
}
}
in_reconfig = true;
+
op_buf_rcnfg.buffer_type = VDEC_BUFFER_TYPE_OUTPUT;
eRet = get_buffer_req(&op_buf_rcnfg);
}
+ if (m_use_smoothstreaming) {
+ if (drv_ctx.video_resolution.frame_width > kMaxSmoothStreamingWidth ||
+ drv_ctx.video_resolution.frame_height > kMaxSmoothStreamingHeight) {
+ DEBUG_PRINT_ERROR("NOTE: Exceeds max smoothstreaming resolution");
+ eRet = OMX_ErrorInsufficientResources;
+ } else {
+ if (drv_ctx.video_resolution.frame_width > m_smoothstreaming_width)
+ m_smoothstreaming_width = drv_ctx.video_resolution.frame_width;
+ if (drv_ctx.video_resolution.frame_height > m_smoothstreaming_height)
+ m_smoothstreaming_height = drv_ctx.video_resolution.frame_height;
+
+ DEBUG_PRINT_HIGH("Port Settings changed : "
+ "Will continue smoosthtreaming @ [%u x %u]",
+ m_smoothstreaming_width, m_smoothstreaming_height);
+ }
+ }
}
return eRet;
}
@@ -7791,6 +7892,7 @@ OMX_ERRORTYPE omx_vdec::update_picture_resolution()
DEBUG_PRINT_ERROR("Error VDEC_IOCTL_GET_PICRES");
eRet = OMX_ErrorHardware;
}
+
return eRet;
}