diff options
author | Zhu,Tianyang <tianyang.zhu@intel.com> | 2014-05-08 16:05:49 +0800 |
---|---|---|
committer | buildslave <sys_buildbot@intel.com> | 2014-05-19 00:48:50 +0000 |
commit | c3439ed85f37967b4e3f0433e9db259ca70f458b (patch) | |
tree | 8c873e0a12b57577eee405ed20190350ac293b11 | |
parent | 9c9829d3ea5f72dbe1ceb1f09607b1c2ed13faa7 (diff) | |
download | hwcomposer-c3439ed85f37967b4e3f0433e9db259ca70f458b.tar.gz |
For Widi downscaling feature
BZ: 188797
Follow below steps to enable downscaling
a: Disconnect WIDI;
b: adb shell setprop "widi.video.dscaling.enable" "true";
c: re-connect WIDI
TBD: need WIDI team help
a: Default value: offX = 0; offY = 0; bufWidth = 1920; bufHeight = 1080;
b: Calling "setDownscaling" in "prepare" isn't resonable and has
a time sequence issue, the first video frame hasn't got right DS params
and doecder to a wrong buffer;
Change-Id: I817060bde30d5a60633223ec90c5597ab5e03be0
Signed-off-by: Zhu,Tianyang <tianyang.zhu@intel.com>
-rw-r--r-- | common/devices/VirtualDevice.cpp | 80 | ||||
-rw-r--r-- | common/observers/MultiDisplayObserver.cpp | 32 | ||||
-rw-r--r-- | common/observers/MultiDisplayObserver.h | 9 | ||||
-rw-r--r-- | include/IVideoPayloadManager.h | 7 | ||||
-rw-r--r-- | include/VirtualDevice.h | 3 | ||||
-rw-r--r-- | ips/common/VideoPayloadManager.cpp | 12 |
6 files changed, 138 insertions, 5 deletions
diff --git a/common/devices/VirtualDevice.cpp b/common/devices/VirtualDevice.cpp index b648d07..36c4cf0 100644 --- a/common/devices/VirtualDevice.cpp +++ b/common/devices/VirtualDevice.cpp @@ -35,6 +35,7 @@ #include <binder/IServiceManager.h> #include <binder/ProcessState.h> +#include <cutils/properties.h> #include <sync/sync.h> @@ -113,7 +114,8 @@ VirtualDevice::VirtualDevice(Hwcomposer& hwc, DisplayPlaneManager& dpm) mOrigContentWidth(0), mOrigContentHeight(0), mFirstVideoFrame(true), - mCachedBufferCapcity(16) + mCachedBufferCapcity(16), + mDScalingEnabled(false) { CTRACE(); mNextConfig.frameServerActive = false; @@ -207,13 +209,22 @@ status_t VirtualDevice::start(sp<IFrameTypeChangeListener> typeChangeListener) mNextConfig.policy.refresh = 60; mNextConfig.extendedModeEnabled = Hwcomposer::getInstance().getDisplayAnalyzer()->isVideoExtModeEnabled(); - if (mNextConfig.extendedModeEnabled) - Hwcomposer::getInstance().getMultiDisplayObserver()->notifyWidiConnectionStatus(true); + MultiDisplayObserver* mds = mHwc.getMultiDisplayObserver(); + if (mds != NULL) + mds->notifyWidiConnectionStatus(true); mVideoFramerate = 0; mFirstVideoFrame = true; mNextConfig.frameServerActive = true; mNextConfig.forceNotifyFrameType = true; mNextConfig.forceNotifyBufferInfo = true; + char prop[PROPERTY_VALUE_MAX]; + if (property_get("widi.video.dscaling.enable", prop, NULL) > 0 && + strncmp(prop, "true", PROPERTY_VALUE_MAX) == 0) { + ITRACE("widi.video.dscaling is enabled, %s", prop); + mDScalingEnabled = true; + } else { + ITRACE("widi.video.dscaling is disabled"); + } if (mThread == NULL) { mThread = new WidiBlitThread(this); @@ -266,6 +277,7 @@ status_t VirtualDevice::setResolution(const FrameProcessingPolicy& policy, sp<IF Mutex::Autolock _l(mConfigLock); mNextConfig.frameListener = listener; mNextConfig.policy = policy; + // setDownScalingSize(policy.scaledWidth, policy.scaledHeight); return NO_ERROR; } @@ -339,6 +351,20 @@ bool VirtualDevice::prepare(hwc_display_contents_1_t *display) } } } + // FIXME: It isn't resonable to set downscaling at here + for (size_t i = 0; i < display->numHwLayers-1; i++) { + hwc_layer_1_t& layer = display->hwLayers[i]; + if (analyzer->isVideoLayer(layer)) { + int dswidth = 1280;//mCurrentConfig.policy.scaledWidth; + int dsheight = 720; //mCurrentConfig.policy.scaledHeight; + int offX = 0; + int offY = 0; + int bufWidth = 1920; + int bufHeight = 1080; + setDownScaling(dswidth, dsheight, offX, offY, bufWidth, bufHeight); + break; + } + } bool protectedLayer = false; bool presentationLayer = false; @@ -544,13 +570,32 @@ bool VirtualDevice::sendToWidi(const hwc_layer_1_t& layer, bool isProtected) outputFrameInfo.bufferFormat = metadata.format; handleType = HWC_HANDLE_TYPE_KBUF; - if (metadata.kHandle != 0) { + bool isRotated = false; + if (metadata.transform == HAL_TRANSFORM_ROT_90 || + metadata.transform == HAL_TRANSFORM_ROT_180 || + metadata.transform == HAL_TRANSFORM_ROT_270) { + isRotated = true; + } + if (!isRotated && metadata.scaling_khandle) { + handle = metadata.scaling_khandle; + outputFrameInfo.bufferWidth = metadata.scaling_width; + outputFrameInfo.bufferHeight = ((metadata.scaling_height + 0x1f) & (~0x1f)); + outputFrameInfo.lumaUStride = metadata.scaling_luma_stride; + outputFrameInfo.chromaUStride = metadata.scaling_chroma_u_stride; + outputFrameInfo.chromaVStride = metadata.scaling_chroma_v_stride; + outputFrameInfo.contentWidth = metadata.scaling_width; + outputFrameInfo.contentHeight =((metadata.scaling_height + 0x1f) & (~0x1f)); + } else if (metadata.kHandle != 0) { handle = metadata.kHandle; outputFrameInfo.bufferWidth = metadata.width; outputFrameInfo.bufferHeight = ((metadata.height + 0x1f) & (~0x1f)); outputFrameInfo.lumaUStride = metadata.lumaStride; outputFrameInfo.chromaUStride = metadata.chromaUStride; outputFrameInfo.chromaVStride = metadata.chromaVStride; + if (metadata.scaling_khandle && isRotated) { + outputFrameInfo.contentWidth = metadata.scaling_height; + outputFrameInfo.contentHeight = ((metadata.scaling_width + 0x1f) & (~0x1f)); + } } else { ETRACE("Couldn't get any khandle"); return false; @@ -686,7 +731,6 @@ bool VirtualDevice::sendToWidi(const hwc_layer_1_t& layer, bool isProtected) if (handleType == HWC_HANDLE_TYPE_GRALLOC) mMappedBufferCache.clear(); } - if (handleType == HWC_HANDLE_TYPE_KBUF && handle == mExtLastKhandle && mediaTimestamp == mExtLastTimestamp) { return true; // Do not switch to clone mode here. @@ -1042,5 +1086,31 @@ void VirtualDevice::deinitialize() mInitialized = false; } +// Shold make sure below 4 conditions are met, +// 1: only for video playback case +// 2: only be called ONE time +// 3: is called before video driver begin to decode +// 4: offX & offY are 64 aligned +status_t VirtualDevice::setDownScaling( + int dswidth, int dsheight, + int offX, int offY, + int bufWidth, int bufHeight) { + status_t ret = UNKNOWN_ERROR; + if (!mDScalingEnabled) + return ret; + int sessionID = mHwc.getDisplayAnalyzer()->getFirstVideoInstanceSessionID(); + if (sessionID >= 0 && mFirstVideoFrame) { + MultiDisplayObserver* mds = mHwc.getMultiDisplayObserver(); + ret = mds->setDecoderOutputResolution(sessionID, dswidth, dsheight, offX, offY, bufWidth, bufHeight); + if (ret == NO_ERROR) { + ITRACE("set video down scaling: %dx%d, %dx%d, %dx%d", + dswidth, dsheight, offX, offY, bufWidth, bufHeight); + } else { + WTRACE("Failed to set video down scaling"); + } + } + return ret; +} + } // namespace intel } // namespace android diff --git a/common/observers/MultiDisplayObserver.cpp b/common/observers/MultiDisplayObserver.cpp index 488f07f..bc76092 100644 --- a/common/observers/MultiDisplayObserver.cpp +++ b/common/observers/MultiDisplayObserver.cpp @@ -103,6 +103,7 @@ MultiDisplayObserver::MultiDisplayObserver() mMDSInfoProvider(NULL), mMDSConnObserver(NULL), mMDSCallback(NULL), + mMDSDecoderConfig(NULL), mLock(), mCondition(), mThreadLoopCount(0), @@ -172,6 +173,11 @@ bool MultiDisplayObserver::initMDSClient() ETRACE("failed to create mds video Client"); return false; } + mMDSDecoderConfig = mds->getDecoderConfig(); + if (mMDSDecoderConfig.get() == NULL) { + ETRACE("failed to create mds decoder Client"); + return false; + } status_t ret = mMDSCbRegistrar->registerCallback(mMDSCallback); if (ret != NO_ERROR) { @@ -197,6 +203,7 @@ void MultiDisplayObserver::deinitMDSClient() mMDSInfoProvider = NULL; mMDSCallback = NULL; mMDSConnObserver = NULL; + mMDSDecoderConfig = NULL; } bool MultiDisplayObserver::initMDSClientAsync() @@ -409,6 +416,31 @@ status_t MultiDisplayObserver::notifyWidiConnectionStatus( bool connected) return mMDSConnObserver->updateWidiConnectionStatus(connected); } +status_t MultiDisplayObserver::setDecoderOutputResolution( + int sessionID, + int32_t width, int32_t height, + int32_t offX, int32_t offY, + int32_t bufWidth, int32_t bufHeight) +{ + Mutex::Autolock _l(mLock); + if (mMDSDecoderConfig.get() == NULL) { + return NO_INIT; + } + if (width <= 0 || height <= 0 || + offX < 0 || offY < 0 || + bufWidth <= 0 || bufHeight <= 0) { + ETRACE(" Invalid parameter: %dx%d, %dx%d, %dx%d", width, height, offX, offY, bufWidth, bufHeight); + return UNKNOWN_ERROR; + } + + status_t ret = mMDSDecoderConfig->setDecoderOutputResolution(sessionID, width, height, offX, offY, bufWidth, bufHeight); + if (ret == NO_ERROR) { + ITRACE("Video Session[%d] output resolution %dx%d ", sessionID, width, height); + } + return ret; +} + + #endif //TARGET_HAS_MULTIPLE_DISPLAY } // namespace intel diff --git a/common/observers/MultiDisplayObserver.h b/common/observers/MultiDisplayObserver.h index 5c6f939..f434c4d 100644 --- a/common/observers/MultiDisplayObserver.h +++ b/common/observers/MultiDisplayObserver.h @@ -79,6 +79,10 @@ public: int getVideoSessionNumber(); bool isExternalDeviceTimingFixed() const; status_t notifyWidiConnectionStatus(bool connected); + status_t setDecoderOutputResolution(int sessionID, + int32_t width, int32_t height, + int32_t offX, int32_t offY, + int32_t bufWidth, int32_t bufHeight); private: bool isMDSRunning(); @@ -101,6 +105,7 @@ private: sp<IMultiDisplayCallbackRegistrar> mMDSCbRegistrar; sp<IMultiDisplayInfoProvider> mMDSInfoProvider; sp<IMultiDisplayConnectionObserver> mMDSConnObserver; + sp<IMultiDisplayDecoderConfig> mMDSDecoderConfig; sp<MultiDisplayCallback> mMDSCallback; mutable Mutex mLock; Condition mCondition; @@ -129,6 +134,10 @@ public: int getVideoSessionNumber() { return 0; } bool isExternalDeviceTimingFixed() const { return false; } status_t notifyWidiConnectionStatus(bool connected) { return NO_ERROR; } + status_t setDecoderOutputResolution( + int sessionID, + int32_t width, int32_t height, + int32_t, int32_t, int32_t, int32_t) { return NO_ERROR; } }; #endif //TARGET_HAS_MULTIPLE_DISPLAY diff --git a/include/IVideoPayloadManager.h b/include/IVideoPayloadManager.h index df7e809..4d37223 100644 --- a/include/IVideoPayloadManager.h +++ b/include/IVideoPayloadManager.h @@ -53,6 +53,13 @@ public: int64_t timestamp; uint32_t crop_width; uint32_t crop_height; + // Downscaling + uint32_t scaling_khandle; + uint32_t scaling_width; + uint32_t scaling_height; + uint32_t scaling_luma_stride; + uint32_t scaling_chroma_u_stride; + uint32_t scaling_chroma_v_stride; }; public: diff --git a/include/VirtualDevice.h b/include/VirtualDevice.h index 0591cec..f628c6b 100644 --- a/include/VirtualDevice.h +++ b/include/VirtualDevice.h @@ -114,6 +114,7 @@ protected: FrameInfo mLastOutputFrameInfo; int32_t mVideoFramerate; + bool mDScalingEnabled; android::KeyedVector<uint32_t, android::sp<CachedBuffer> > mMappedBufferCache; android::Mutex mHeldBuffersLock; @@ -128,6 +129,8 @@ private: void copyVideo(buffer_handle_t videoHandle, uint8_t* destPtr, uint32_t destWidth, uint32_t destHeight); bool vanillaPrepare(hwc_display_contents_1_t *display); bool vanillaCommit(hwc_display_contents_1_t *display); + status_t setDownScaling(int width, int height, + int offX, int offY, int bufWidth, int bufHeight); public: VirtualDevice(Hwcomposer& hwc, DisplayPlaneManager& dpm); diff --git a/ips/common/VideoPayloadManager.cpp b/ips/common/VideoPayloadManager.cpp index 1967440..d540e40 100644 --- a/ips/common/VideoPayloadManager.cpp +++ b/ips/common/VideoPayloadManager.cpp @@ -60,6 +60,13 @@ bool VideoPayloadManager::getMetaData(BufferMapper *mapper, MetaData *metadata) metadata->format = p->format; metadata->transform = p->metadata_transform; metadata->timestamp = p->timestamp; + metadata->scaling_khandle = p->scaling_khandle; + metadata->scaling_width = p->scaling_width; + metadata->scaling_height = p->scaling_height; + + metadata->scaling_luma_stride = p->scaling_luma_stride; + metadata->scaling_chroma_u_stride = p->scaling_chroma_u_stride; + metadata->scaling_chroma_v_stride = p->scaling_chroma_v_stride; if (p->metadata_transform == 0) { metadata->width = p->width; @@ -76,6 +83,11 @@ bool VideoPayloadManager::getMetaData(BufferMapper *mapper, MetaData *metadata) metadata->chromaVStride = p->rotate_chroma_v_stride; metadata->kHandle = p->rotated_buffer_handle; } + if (metadata->scaling_khandle) + VTRACE("Scaled video buffer, %dx%d", + metadata->scaling_width, metadata->scaling_height); + if (metadata->transform != 0) + VTRACE("Rotated video buffer, %dx%d", metadata->width, metadata->height); if ((p->metadata_transform == 0) || (p->metadata_transform == HAL_TRANSFORM_ROT_180)) { metadata->crop_width = p->crop_width; |