762 lines
22 KiB
C++
762 lines
22 KiB
C++
/*
|
|
* Copyright (C) 2024 Amlogic Corporation.
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
#include "BinderServer.h"
|
|
#include "MesonVideoCompositor.h"
|
|
#include "DispAdptLog.h"
|
|
#include "VscalerEvent.h"
|
|
|
|
#define GET_DISPLAY(display) \
|
|
std::shared_ptr<MesonDisplay> mesonDisplay; \
|
|
std::map<int, std::shared_ptr<MesonDisplay>>::iterator it = \
|
|
mDisplays.find(display); \
|
|
if (it != mDisplays.end()) { \
|
|
mesonDisplay = it->second; \
|
|
} else {\
|
|
DISPLAY_LOGE("(%s) met invalid display id (%d)",\
|
|
__func__, (int)display); \
|
|
return MESON_ERROR_BAD_DISPLAY; \
|
|
}
|
|
|
|
mesonVideoCompositor::mesonVideoCompositor()
|
|
{
|
|
DispAdptLogInit();
|
|
|
|
mGpscFd = open(GP_FILE_PATH, O_RDWR);
|
|
for (uint32_t i = 0; i < 1; i ++) {
|
|
/*create meson display*/
|
|
auto disp = std::make_shared<MesonDisplay>(i);
|
|
disp->initialize();
|
|
disp->createGpscPlane(mGpscFd);
|
|
mDisplays.emplace(i, disp);
|
|
}
|
|
mDrmLeaseFd = -1;
|
|
|
|
if (mGpscFd >= 0) {
|
|
mExitThread = false;
|
|
if (pthread_create(&mGpscThread, NULL, GpscThreadMain, (void *)this))
|
|
DISPLAY_LOGE("create gpsc thread fail: %d\n", errno);
|
|
}
|
|
}
|
|
|
|
mesonVideoCompositor::~mesonVideoCompositor()
|
|
{
|
|
if (mDrmLeaseFd >= 0)
|
|
close(mDrmLeaseFd);
|
|
mDrmLeaseFd = -1;
|
|
}
|
|
|
|
void* mesonVideoCompositor::GpscThreadMain(void *data) {
|
|
mesonVideoCompositor *pThis = (mesonVideoCompositor *)data;
|
|
struct pollfd pfd;
|
|
|
|
pfd.fd = pThis->mGpscFd;
|
|
pfd.events = POLLIN | POLLRDNORM;
|
|
pfd.revents = 0;
|
|
int pollrtn;
|
|
|
|
while (true) {
|
|
if (pThis->mExitThread) {
|
|
pthread_exit(0);
|
|
return NULL;
|
|
}
|
|
|
|
pollrtn = poll(&pfd, 1, 32);
|
|
if (pollrtn <= 0)
|
|
continue;
|
|
if (pfd.revents & POLLIN) {
|
|
unsigned int connectId;
|
|
if (ioctl(pThis->mGpscFd, GPSCALER_GET_CONNECT_ID, &connectId) >= 0) {
|
|
for (auto it = pThis->mDisplays.begin(); it != pThis->mDisplays.end(); it++) {
|
|
it->second->setGpscConnectId(connectId);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
meson_videotunnel_id_t mesonVideoCompositor::GetVideoTunnelId(int32_t src, int32_t attr, int32_t scalerId)
|
|
{
|
|
int id = MESON_USE_VDEC_TUNNEL;
|
|
|
|
if (src == V4L2_EXT_VSC_INPUT_SRC_JPEG) { // VO
|
|
if (scalerId == VT_SCALER_0)
|
|
id = MESON_USE_VO_TUNNEL;
|
|
else if (scalerId == VT_SCALER_1)
|
|
id = MESON_USE_VO_EXT_TUNNEL;
|
|
}
|
|
if (src == V4L2_EXT_VSC_INPUT_SRC_HDMI || // HDMI
|
|
(src == V4L2_EXT_VSC_INPUT_SRC_AVD && attr == 0) || // ATV
|
|
src == V4L2_EXT_VSC_INPUT_SRC_TEXTURE) { // TTV
|
|
if (scalerId == VT_SCALER_0)
|
|
id = MESON_USE_TVIN_TUNNEL;
|
|
else if (scalerId == VT_SCALER_1)
|
|
id = MESON_USE_TVIN_EXT_TUNNEL;
|
|
}
|
|
if (src == V4L2_EXT_VSC_INPUT_SRC_VDEC) // VDEC
|
|
id = MESON_USE_VDEC_TUNNEL + scalerId;
|
|
if (!src)
|
|
id += scalerId;
|
|
|
|
return (meson_videotunnel_id_t)id;
|
|
}
|
|
|
|
int mesonVideoCompositor::connectScaler(int32_t displayId, int32_t scalerId)
|
|
{
|
|
std::lock_guard<std::mutex> lock(mMutex);
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = 0;
|
|
|
|
auto layer_it = mLayers.find(scalerId);
|
|
if (layer_it == mLayers.end()) {
|
|
mesonDisplay->createLayer(layerId);
|
|
mLayers.emplace(scalerId, layerId);
|
|
}
|
|
mConnectCount[scalerId]++;
|
|
DISPLAY_LOGV("connect scaler: %d, layer: %d, count: %d\n",
|
|
scalerId, layerId, mConnectCount[scalerId]);
|
|
|
|
return MESON_ERROR_NONE;
|
|
}
|
|
|
|
int mesonVideoCompositor::disconnectScaler(int32_t displayId, int32_t scalerId, int32_t index)
|
|
{
|
|
std::lock_guard<std::mutex> lock(mMutex);
|
|
GET_DISPLAY(displayId);
|
|
|
|
auto layer_it = mLayers.find(scalerId);
|
|
if (layer_it != mLayers.end()) {
|
|
mConnectCount[scalerId]--;
|
|
if (mConnectCount[scalerId] == 0) {
|
|
DISPLAY_LOGV("disconnect scaler: %d\n", scalerId);
|
|
mesonDisplay->destroyLayer(layer_it->second);
|
|
mLayers.erase(layer_it);
|
|
}
|
|
}
|
|
|
|
if (mLayers.size() == 0)
|
|
mesonDisplay->clearPlane();
|
|
|
|
return MESON_ERROR_NONE;
|
|
}
|
|
|
|
int32_t mesonVideoCompositor::getLayerIdByScaler(int32_t scalerId)
|
|
{
|
|
int32_t layerId;
|
|
auto it = mLayers.find(scalerId);
|
|
if (it != mLayers.end()) {
|
|
layerId = it->second;
|
|
} else {
|
|
DISPLAY_LOGE("error not connect scaler: %d\n", scalerId);
|
|
layerId = 0;
|
|
}
|
|
return layerId;
|
|
}
|
|
|
|
int mesonVideoCompositor::getLayerWinRegion(int32_t displayId,
|
|
int32_t scalerId, struct v4l2_ext_vsc_win_region &win)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->getLayerWinRegion(layerId, win);
|
|
}
|
|
|
|
int mesonVideoCompositor::setOriginalResolution(int32_t displayId,
|
|
int32_t scalerId, meson_rect_t rect, meson_rect_t punch)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
if (layerId == 0)
|
|
return MESON_ERROR_BAD_LAYER;
|
|
|
|
mesonDisplay->setLayerOriginalResolution(layerId, rect, punch);
|
|
return MESON_ERROR_NONE;
|
|
}
|
|
|
|
int mesonVideoCompositor::setScalerSourceCrop(int32_t displayId,
|
|
int32_t scalerId, struct rect crop)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->setLayerSourceCrop(layerId, crop);
|
|
}
|
|
|
|
int mesonVideoCompositor::setScalerDisplayFrame(int32_t displayId,
|
|
int32_t scalerId, struct rect frame)
|
|
{
|
|
drm_rect_t rect = { 0 };
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
GET_DISPLAY(displayId);
|
|
|
|
rect.left = frame.x;
|
|
rect.top = frame.y;
|
|
rect.right = frame.x + frame.w;
|
|
rect.bottom = frame.y + frame.h;
|
|
return mesonDisplay->setLayerDispFrame(layerId, rect);
|
|
}
|
|
|
|
int mesonVideoCompositor::setScalerTransform(int32_t displayId,
|
|
int32_t scalerId, int32_t transform)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
if (layerId == 0)
|
|
return MESON_ERROR_BAD_LAYER;
|
|
|
|
int ret = mesonDisplay->setLayerTransform(layerId, transform);
|
|
|
|
uint8_t dat[EVENT_WINDOW_REGION_MAX] = { 0 };
|
|
struct v4l2_ext_vsc_win_region win = { 0 };
|
|
struct v4l2_ext_video_rect disFrame;
|
|
VscEventWindowRegionInfo *info = (VscEventWindowRegionInfo *)dat;
|
|
|
|
VscEventType vEventType = { 0 };
|
|
VscalerEvent *vEvent = &(VscalerEvent::getInstance());
|
|
|
|
getLayerWinRegion(displayId, scalerId, win);
|
|
|
|
disFrame = win.out;
|
|
info->x = disFrame.x;
|
|
info->y = disFrame.y;
|
|
info->w = disFrame.w;
|
|
info->h = disFrame.h;
|
|
info->time = mesonDisplay->getVideoDelay(DEFAULT_FPS);
|
|
info->px = win.punch.x;
|
|
info->py = win.punch.y;
|
|
info->pw = win.punch.w;
|
|
info->ph = win.punch.h;
|
|
vEventType = vEvent->makeEventData(displayId, scalerId,
|
|
V4L2_CID_EXT_VSC_SUBSCRIBE_APPLYING_DONE_WINDOW_REGION,
|
|
dat, EVENT_WINDOW_REGION_MAX);
|
|
vEvent->addEventToQueue(scalerId, vEventType);
|
|
|
|
return ret;
|
|
}
|
|
|
|
int mesonVideoCompositor::getZorder(int32_t displayId,
|
|
int32_t scalerId, struct v4l2_ext_vsc_zorder &z)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->getLayerZorder(layerId, z);
|
|
}
|
|
|
|
int mesonVideoCompositor::setZorder(int32_t displayId, int32_t scalerId, int32_t zorder, int32_t alpha)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
if (layerId == 0)
|
|
return MESON_ERROR_BAD_LAYER;
|
|
|
|
float alp = (float)alpha / 255;
|
|
mesonDisplay->setLayerZorder(layerId, zorder);
|
|
mesonDisplay->setLayerPlaneAlpha(layerId, alp);
|
|
|
|
return MESON_ERROR_NONE;
|
|
}
|
|
|
|
int mesonVideoCompositor::getConnectInfo(int32_t displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_connect_info &info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
if (layerId == 0)
|
|
return MESON_ERROR_BAD_LAYER;
|
|
|
|
return mesonDisplay->getLayerConnectInfo(layerId, info);
|
|
}
|
|
|
|
int mesonVideoCompositor::setConnectInfo(int32_t displayId, int32_t scalerId,
|
|
int32_t src, int32_t index, int32_t attr, int32_t out, int32_t openIndex)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
if (layerId == 0)
|
|
return MESON_ERROR_BAD_LAYER;
|
|
|
|
mesonDisplay->setLayerConnectInfo(layerId, src, index, attr, out);
|
|
if (src == V4L2_EXT_VSC_INPUT_SRC_NONE || out == V4L2_EXT_VSC_DEST_NONE) {
|
|
// todo: disable display
|
|
return MESON_ERROR_NONE;
|
|
}
|
|
|
|
meson_videotunnel_id_t tunnelId = GetVideoTunnelId(src, attr, scalerId);
|
|
if (out == V4L2_EXT_VSC_DEST_DISPLAY) {
|
|
mesonDisplay->setTunnelId(layerId, tunnelId);
|
|
if (scalerId == VT_SCALER_0) {
|
|
struct v4l2_ext_vsc_win_prop prop;
|
|
mesonDisplay->getLayerWinProp(getLayerIdByScaler(VT_SCALER_1), prop);
|
|
if (prop.mirror_mode == V4L2_EXT_VSC_MIRROR_MODE_ON)
|
|
mesonDisplay->setTunnelId(getLayerIdByScaler(VT_SCALER_1), tunnelId);
|
|
}
|
|
}
|
|
|
|
return MESON_ERROR_NONE;
|
|
}
|
|
|
|
int mesonVideoCompositor::getWinProp(int32_t displayId,
|
|
int32_t scalerId, struct v4l2_ext_vsc_win_prop &prop)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->getLayerWinProp(layerId, prop);
|
|
}
|
|
|
|
int mesonVideoCompositor::setWinProp(int32_t displayId, int32_t scalerId,
|
|
int32_t winmode, int32_t mirrormode, int32_t memtype)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
if (scalerId == VT_SCALER_0)
|
|
return MESON_ERROR_NONE;
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
if (layerId == 0)
|
|
return MESON_ERROR_BAD_LAYER;
|
|
|
|
struct v4l2_ext_vsc_connect_info info;
|
|
int ret = 0;
|
|
|
|
mesonDisplay->setLayerWinProp(layerId, winmode, mirrormode, memtype);
|
|
|
|
if (mirrormode != V4L2_EXT_VSC_MIRROR_MODE_NONE) {
|
|
if (mirrormode == V4L2_EXT_VSC_MIRROR_MODE_ON) {
|
|
ret = mesonDisplay->getLayerConnectInfo(getLayerIdByScaler(VT_SCALER_0), info);
|
|
if (!ret && info.in.src != V4L2_EXT_VSC_INPUT_SRC_NONE)
|
|
scalerId = VT_SCALER_0;
|
|
} else {
|
|
ret = mesonDisplay->getLayerConnectInfo(getLayerIdByScaler(scalerId), info);
|
|
}
|
|
|
|
if (ret)
|
|
return ret;
|
|
meson_videotunnel_id_t tunnelId = GetVideoTunnelId(info.in.src, info.in.attr, scalerId);
|
|
|
|
mesonDisplay->setTunnelId(layerId, tunnelId);
|
|
}
|
|
|
|
return MESON_ERROR_NONE;
|
|
}
|
|
|
|
int mesonVideoCompositor::setAspectratio(int32_t displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_aspectratio_policy policy)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
|
|
return mesonDisplay->setAspectratio(layerId, policy);
|
|
}
|
|
|
|
int mesonVideoCompositor::setLayerOrbitWindow(int32_t displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_orbit_window &info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->setLayerOrbitWindow(layerId, info);
|
|
}
|
|
|
|
int mesonVideoCompositor::setLayerOrbitMove(int32_t displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_orbit_move &info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->setLayerOrbitMove(layerId, info);
|
|
}
|
|
|
|
int mesonVideoCompositor::getHDR(int32_t displayId, int *value)
|
|
{
|
|
int ret = -1;
|
|
GET_DISPLAY(displayId);
|
|
|
|
*value = V4L2_EXT_VSC_HDR_TYPE_HDR_RESERVED2;
|
|
ret = mesonDisplay->getHDR();
|
|
if (ret == MESON_HDR10PLUS ||
|
|
ret == MESON_HDR10_ST2084 ||
|
|
ret == MESON_HDR10_TRADITIONAL)
|
|
*value = V4L2_EXT_VSC_HDR_TYPE_HDR10;
|
|
|
|
if (ret == MESON_DOLBYVISION_STD)
|
|
*value = V4L2_EXT_VSC_HDR_TYPE_DOLBY;
|
|
|
|
if (ret == MESON_DOLBYVISION_LL)
|
|
*value = V4L2_EXT_VSC_HDR_TYPE_DOLBY_LL;
|
|
|
|
if (ret == MESON_HDR_HLG)
|
|
*value = V4L2_EXT_VSC_HDR_TYPE_HLG;
|
|
|
|
if (ret == MESON_SDR)
|
|
*value = V4L2_EXT_VSC_HDR_TYPE_SDR;
|
|
|
|
return ret >= 0 ? 0 : -1;
|
|
}
|
|
|
|
int mesonVideoCompositor::setHDR(int32_t displayId, int value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
int hdr = MESON_SDR;
|
|
|
|
if (value == V4L2_EXT_VSC_HDR_TYPE_SDR)
|
|
hdr = MESON_SDR;
|
|
|
|
if (value == V4L2_EXT_VSC_HDR_TYPE_HDR10)
|
|
hdr = MESON_HDR10_ST2084;
|
|
|
|
if (value == V4L2_EXT_VSC_HDR_TYPE_DOLBY)
|
|
hdr = MESON_DOLBYVISION_STD;
|
|
|
|
if (value == V4L2_EXT_VSC_HDR_TYPE_HLG)
|
|
hdr = MESON_HDR_HLG;
|
|
|
|
if (value == V4L2_EXT_VSC_HDR_TYPE_DOLBY_LL)
|
|
hdr = MESON_DOLBYVISION_LL;
|
|
|
|
return mesonDisplay->setHDR(hdr);
|
|
}
|
|
|
|
int mesonVideoCompositor::getBgColor(int32_t displayId, int *value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getBgColor(value);
|
|
}
|
|
|
|
int mesonVideoCompositor::setBgColor(int32_t displayId, int32_t scalerId, int value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
int ret = mesonDisplay->setBgColor(value);
|
|
if (value == V4L2_EXT_VSC_WIN_COLOR_NORMAL) {
|
|
VscalerEvent *vEvent = &(VscalerEvent::getInstance());
|
|
vEvent->makeMuteOff(scalerId);
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
int mesonVideoCompositor::getLayerFreeze(int32_t displayId, int32_t scalerId, int *freeze)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->getLayerFreeze(layerId, freeze);
|
|
}
|
|
|
|
int mesonVideoCompositor::setLayerFreeze(int32_t displayId, int32_t scalerId, int freeze)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->setLayerFreeze(layerId, freeze);
|
|
}
|
|
|
|
int mesonVideoCompositor::getLayerFreezeFrameBuffer(int32_t displayId, int32_t scalerId, int *freeze)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->getLayerFreezeFrameBuffer(layerId, freeze);
|
|
}
|
|
|
|
int mesonVideoCompositor::setLayerFreezeFrameBuffer(int32_t displayId, int32_t scalerId, int freeze)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->setLayerFreezeFrameBuffer(layerId, freeze);
|
|
}
|
|
|
|
/* hdmi tx function begin */
|
|
int mesonVideoCompositor::getHdmitxConnection(int32_t displayId, int &state)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getHdmitxConnection(state);
|
|
}
|
|
|
|
int mesonVideoCompositor::getHdmitxHdrType(int32_t displayId, int &value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getHdmitxHdrType(value);
|
|
}
|
|
|
|
int mesonVideoCompositor::getHdmitxHdcpVersion(int32_t displayId, int &value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getHdmitxHdcpVersion(value);
|
|
}
|
|
|
|
int mesonVideoCompositor::getHdmitxHdrPolicy(int32_t displayId, int &value)
|
|
{
|
|
int ret = -1;
|
|
int policy = -1;
|
|
GET_DISPLAY(displayId);
|
|
|
|
ret = mesonDisplay->getHdmitxHdrPolicy(policy);
|
|
switch (policy) {
|
|
case MESON_HDR_POLICY_FOLLOW_SINK:
|
|
value = V4L2_EXT_HDMITX_HDR_POLICY_ENABLE;
|
|
break;
|
|
case MESON_HDR_POLICY_FOLLOW_SOURCE:
|
|
value = V4L2_EXT_HDMITX_HDR_POLICY_AUTO;
|
|
break;
|
|
default:
|
|
value = V4L2_EXT_HDMITX_HDR_POLICY_DISABLE;
|
|
break;
|
|
}
|
|
return ret;
|
|
}
|
|
|
|
int mesonVideoCompositor::setHdmitxHdrPolicy(int32_t displayId, int value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setHdmitxHdrPolicy(value);
|
|
}
|
|
|
|
int mesonVideoCompositor::setHdmitxAvMute(int32_t displayId, enum v4l2_ext_hdmitx_avmute value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setHdmitxAvMute(value);
|
|
}
|
|
|
|
int mesonVideoCompositor::setHdmitxHdcpAuth(int32_t displayId, enum v4l2_ext_hdmitx_hdcp_auth value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setHdmitxHdcpAuth(value);
|
|
}
|
|
|
|
int mesonVideoCompositor::getHdmitxHdcpStatus(int32_t displayId, enum v4l2_ext_hdmitx_hdcp_status &value)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getHdmitxHdcpStatus(value);
|
|
}
|
|
|
|
int mesonVideoCompositor::getHdmiTiming(int32_t displayId, struct v4l2_ext_hdmitx_timing_info &info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getHdmiTiming(info);
|
|
}
|
|
|
|
int mesonVideoCompositor::setHdmiTiming(int32_t displayId, struct v4l2_ext_hdmitx_timing_info &info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setHdmiTiming(info);
|
|
}
|
|
|
|
int mesonVideoCompositor::getHdmitxColor(int32_t displayId, struct v4l2_ext_hdmitx_color_attr &attr)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getHdmitxColor(attr);
|
|
}
|
|
|
|
int mesonVideoCompositor::setHdmitxColor(int32_t displayId, struct v4l2_ext_hdmitx_color_attr attr)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setHdmitxColor(attr);
|
|
}
|
|
|
|
int mesonVideoCompositor::getHdmitxRawEdid(int32_t displayId, char **dat, int &len)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getHdmitxRawEdid(dat, len);
|
|
}
|
|
/* hdmi tx function end */
|
|
|
|
int mesonVideoCompositor::getAlphaZorder(int displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_zorder_info *info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int ret = 0;
|
|
|
|
info->length = 0;
|
|
for (auto it = mLayers.begin(); it != mLayers.end(); it++) {
|
|
int layerId = it->second;
|
|
if (it->first < VT_SCALER_MAX - 1) {
|
|
ret |= mesonDisplay->getLayerZorder(layerId, info->z[it->first]);
|
|
info->length++;
|
|
}
|
|
}
|
|
|
|
DISPLAY_LOGV("%s[%d]: size: %d, length: %d\n",
|
|
__func__, __LINE__, mLayers.size(), info->length);
|
|
return ret;
|
|
}
|
|
|
|
int mesonVideoCompositor::setAlphaZorder(int displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_zorder_info *info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
for (int i = 0; i < info->length; i++) {
|
|
int32_t layerId = getLayerIdByScaler(i);
|
|
if (layerId == 0)
|
|
continue;
|
|
|
|
float alp = (float)info->z[i].alpha / 255;
|
|
mesonDisplay->setLayerZorder(layerId, info->z[i].zorder);
|
|
mesonDisplay->setLayerPlaneAlpha(layerId, alp);
|
|
}
|
|
return 0;
|
|
}
|
|
|
|
int mesonVideoCompositor::getOrbitPolicy(int displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_orbit_policy *info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->getOrbitPolicy(layerId, info);
|
|
}
|
|
|
|
int mesonVideoCompositor::setOrbitPolicy(int displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_orbit_policy *info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->setOrbitPolicy(layerId, *info);
|
|
}
|
|
|
|
int mesonVideoCompositor::getSeamlessInfo(int displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_seamless_info *info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->getSeamlessInfo(layerId, info);
|
|
}
|
|
|
|
int mesonVideoCompositor::setSeamlessInfo(int displayId, int32_t scalerId,
|
|
struct v4l2_ext_vsc_seamless_info *info)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
int32_t layerId = getLayerIdByScaler(scalerId);
|
|
return mesonDisplay->setSeamlessInfo(layerId, *info);
|
|
}
|
|
|
|
int mesonVideoCompositor::setDrmLeaseFd(int32_t displayId, int fd)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
if (mDrmLeaseFd >= 0)
|
|
close(mDrmLeaseFd);
|
|
mDrmLeaseFd = fd;
|
|
return mesonDisplay->setDrmLeaseFd(fd);
|
|
}
|
|
|
|
/* displayadapter interface begin */
|
|
int mesonVideoCompositor::createLayer(int32_t displayId, int32_t* layerId)
|
|
{
|
|
int32_t id = 0;
|
|
int ret;
|
|
GET_DISPLAY(displayId);
|
|
|
|
ret = mesonDisplay->createLayer(id);
|
|
*layerId = id;
|
|
return ret;
|
|
}
|
|
|
|
int mesonVideoCompositor::destroyLayer(int32_t displayId, int32_t layerId)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
|
|
return mesonDisplay->destroyLayer(layerId);
|
|
}
|
|
|
|
int mesonVideoCompositor::setTunnelId(int32_t displayId, int32_t layerId, int32_t tunnelId)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setTunnelId(layerId, tunnelId);
|
|
}
|
|
|
|
int mesonVideoCompositor::setLayerIndex(int32_t displayId, int32_t layerId, int32_t index)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setLayerIndex(layerId, index);
|
|
}
|
|
|
|
int mesonVideoCompositor::setLayerZorder(int32_t displayId, int32_t layerId, int32_t zorder)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setLayerZorder(layerId, zorder);
|
|
}
|
|
|
|
int mesonVideoCompositor::setSourceCrop(int32_t displayId, int32_t layerId, struct rect crop)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setLayerSourceCrop(layerId, crop);
|
|
}
|
|
|
|
int mesonVideoCompositor::setDisplayFrame(int32_t displayId, int32_t layerId, struct rect frame)
|
|
{
|
|
drm_rect_t rect = { 0 };
|
|
GET_DISPLAY(displayId);
|
|
|
|
rect.left = frame.x;
|
|
rect.top = frame.y;
|
|
rect.right = frame.x + frame.w;
|
|
rect.bottom = frame.y + frame.h;
|
|
return mesonDisplay->setLayerDispFrame(layerId, rect);
|
|
}
|
|
|
|
int mesonVideoCompositor::getDelayLatency(int32_t displayId, int32_t layerId)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getVsyncDelayLatency(layerId);
|
|
}
|
|
|
|
int mesonVideoCompositor::setToMainPlane(int32_t displayId)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->setVideoDisplaytoMainplane();
|
|
}
|
|
|
|
int mesonVideoCompositor::getUiSize(int32_t displayId, int32_t* width, int32_t* height)
|
|
{
|
|
GET_DISPLAY(displayId);
|
|
return mesonDisplay->getUiSize(width, height);
|
|
}
|
|
/* displayadapter interface end */
|
|
|
|
int main(int argc, char **argv) {
|
|
(void)argc;
|
|
(void)argv;
|
|
|
|
printf("main run\n");
|
|
std::shared_ptr<mesonVideoCompositor> meson = std::make_shared<mesonVideoCompositor>();
|
|
std::shared_ptr<BinderServer> binS = std::make_shared<BinderServer>();
|
|
VscalerEvent *vEvent = &(VscalerEvent::getInstance());
|
|
|
|
binS->setMesonCompositor(meson);
|
|
vEvent->setBinder(binS);
|
|
binS->run(binS);
|
|
|
|
while (true) {
|
|
usleep(1000);
|
|
}
|
|
return 0;
|
|
}
|