diff --git a/build_dependencies.sh b/build_dependencies.sh index 090f105a..566fca25 100644 --- a/build_dependencies.sh +++ b/build_dependencies.sh @@ -47,7 +47,7 @@ cd rfc autoreconf -i ./configure --enable-rfctool=yes --enable-tr181set=yes cd rfcapi -make librfcapi_la_CPPFLAGS="-I/usr/include/cjson" +make CXXFLAGS="-DUSE_IARMBUS" librfcapi_la_CPPFLAGS="-I/usr/include/cjson" make install export RFC_PATH=$ROOT/rfc diff --git a/cov_build.sh b/cov_build.sh index 22e8d7d4..712e7ae0 100644 --- a/cov_build.sh +++ b/cov_build.sh @@ -70,4 +70,4 @@ find $WORKDIR -iname "*.o" -exec rm -v {} \; find $WORKDIR -iname "*.so*" -exec rm -v {} \; echo "##### Triggering make" -make CFLAGS+='-fPIC -DDSMGR_LOGGER_ENABLED=ON -DRDK_DSHAL_NAME=\"libdshal.so\" -I${DS_IF_PATH}/include -I${DS_HAL_PATH} -I${DS_MGRS}/stubs -I${IARMBUS_PATH}/core -I${IARMBUS_PATH}/core/include -I${IARM_MGRS}/sysmgr/include -I${DS_MGRS}/ds/include -I${DS_MGRS}/rpc/include -I${POWER_IF_PATH}/include/ -I/usr/include/glib-2.0 -I/usr/lib/x86_64-linux-gnu/glib-2.0/include -I${IARM_MGRS}/mfr/include/ -I${IARM_MGRS}/mfr/common -I${DEEPSLEEP_IF_PATH}/include -I${IARM_MGRS}/hal/include -I${IARM_MGRS}/power -I${IARM_MGRS}/power/include' LDFLAGS="-L/usr/lib/x86_64-linux-gnu/ -L/usr/local/include -lglib-2.0 -lIARMBus -lWPEFrameworkPowerController -ldshal" \ No newline at end of file +make CFLAGS+='-fPIC -DDSMGR_LOGGER_ENABLED=ON -DDS_ENABLE_IARM_PATH -DRDK_DSHAL_NAME=\"libdshal.so\" -I${DS_IF_PATH}/include -I${DS_HAL_PATH} -I${DS_MGRS}/stubs -I${IARMBUS_PATH}/core -I${IARMBUS_PATH}/core/include -I${IARM_MGRS}/sysmgr/include -I${DS_MGRS}/ds/include -I${DS_MGRS}/ds/include/iarm -I${DS_MGRS}/rpc/include -I${POWER_IF_PATH}/include/ -I/usr/include/glib-2.0 -I/usr/lib/x86_64-linux-gnu/glib-2.0/include -I${IARM_MGRS}/mfr/include/ -I${IARM_MGRS}/mfr/common -I${DEEPSLEEP_IF_PATH}/include -I${IARM_MGRS}/hal/include -I${IARM_MGRS}/power -I${IARM_MGRS}/power/include' LDFLAGS="-L/usr/lib/x86_64-linux-gnu/ -L/usr/local/include -lglib-2.0 -lIARMBus -lWPEFrameworkPowerController -ldshal" diff --git a/ds/hdmiIn.cpp b/ds/hdmiIn.cpp index 18b2ac97..6a50f0f3 100755 --- a/ds/hdmiIn.cpp +++ b/ds/hdmiIn.cpp @@ -66,6 +66,7 @@ #include "dsUtl.h" #include "edid-parser.hpp" #include "dsInternal.h" +#include "iarmHdmiIn.hpp" namespace device @@ -82,6 +83,7 @@ namespace device * @callergraph */ HdmiInput::HdmiInput() + : implHdmiIn(std::unique_ptr(new IarmHdmiInput())) { dsHdmiInInit(); } @@ -98,6 +100,7 @@ HdmiInput::HdmiInput() HdmiInput::~HdmiInput() { dsHdmiInTerm(); + implHdmiIn.reset(); } /** @@ -678,6 +681,38 @@ void HdmiInput::getHdmiVersion (int iHdmiPort, dsHdmiMaxCapabilityVersion_t *cap printf ("%s:%d - HDMI Compatibility Version = %d\n", __PRETTY_FUNCTION__, __LINE__, *capversion); } +uint32_t HdmiInput::Register(IEvent *listener) +{ + uint32_t retStatus=FAIL; + + INT_INFO("HdmiInput::Register Entry \n"); + if(implHdmiIn) + { + retStatus = implHdmiIn->Register(listener); + } + else + { + INT_INFO("HdmiInput::Register impl is null\n"); + } + return retStatus; +} + +uint32_t HdmiInput::UnRegister(IEvent *listener) +{ + uint32_t retStatus=FAIL; + + INT_INFO("HdmiInput::UnRegister Entry \n"); + if(implHdmiIn) + { + retStatus = implHdmiIn->UnRegister(listener); + } + else + { + INT_INFO("HdmiInput::UnRegister impl is null\n"); + } + return retStatus; +} + } diff --git a/ds/iarmHdmiIn.cpp b/ds/iarmHdmiIn.cpp new file mode 100644 index 00000000..18e19e78 --- /dev/null +++ b/ds/iarmHdmiIn.cpp @@ -0,0 +1,185 @@ +/* + * If not stated otherwise in this file or this component's LICENSE file the + * following copyright and licenses apply: + * + * Copyright 2025 RDK Management + * + * 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. + */ + + +/** + * @file IarmHdmiIn.cpp + * @brief Configuration of HDMI Input + */ + +/** +* @defgroup devicesettings +* @{ +* @defgroup ds +* @{ +**/ + + +#include +#include +#include +#include +#include "hdmiIn.hpp" +#include "illegalArgumentException.hpp" +#include "host.hpp" + +#include "dslogger.h" +#include "dsError.h" +#include "dsTypes.h" +#include "dsHdmiIn.h" +#include "dsUtl.h" +#include "edid-parser.hpp" +#include "dsInternal.h" + +#include "utils.h" // for Utils::IARM and IARM_CHECK + + +#include "iarmHdmiIn.hpp" +#include +#include + +// Static data definitions +std::mutex IarmHdmiInput::s_mutex; +std::vector IarmHdmiInput::hdmiInListener; + +constexpr IarmHdmiInput::EventHandlerMapping IarmHdmiInput::eventHandlers[] = { + { IARM_BUS_DSMGR_EVENT_HDMI_IN_HOTPLUG, IarmHdmiInput::OnHDMIInEventHotPlug }, + { IARM_BUS_DSMGR_EVENT_HDMI_IN_SIGNAL_STATUS, IarmHdmiInput::OnHDMIInEventSignalStatus }, + { IARM_BUS_DSMGR_EVENT_HDMI_IN_STATUS, IarmHdmiInput::OnHDMIInEventStatus }, + { IARM_BUS_DSMGR_EVENT_HDMI_IN_VIDEO_MODE_UPDATE, IarmHdmiInput::OnHDMInVideoModeUpdate }, + { IARM_BUS_DSMGR_EVENT_HDMI_IN_ALLM_STATUS, IarmHdmiInput::OnHDMInAllmStatus }, + { IARM_BUS_DSMGR_EVENT_HDMI_IN_AVI_CONTENT_TYPE, IarmHdmiInput::OnHDMInAVIContentType }, + { IARM_BUS_DSMGR_EVENT_HDMI_IN_AV_LATENCY, IarmHdmiInput::OnHDMInAVLatency }, + { IARM_BUS_DSMGR_EVENT_ZOOM_SETTINGS, IarmHdmiInput::OnHDMInVRRStatus }, + { IARM_BUS_DSMGR_EVENT_HDMI_HOTPLUG, IarmHdmiInput::OnHDMIHotPlug } +}; + +const char* IarmHdmiInput::OWNER_NAME = IARM_BUS_DSMGR_NAME; + +IarmHdmiInput::IarmHdmiInput() {} +IarmHdmiInput::~IarmHdmiInput() {} + + +uint32_t IarmHdmiInput::Register(device::HdmiInput::IEvent* listener) { + std::lock_guard lock(s_mutex); + + // First listener, register all handlers + if (hdmiInListener.empty()) { + for (auto& eh : eventHandlers) { + IARM_Bus_RegisterEventHandler(OWNER_NAME, eh.eventId, eh.handler); + } + } + + // Add to listener list if not already present + if (std::find(hdmiInListener.begin(), hdmiInListener.end(), listener) == hdmiInListener.end()) { + hdmiInListener.push_back(listener); + } + + return 0; // Success +} + +// Unregister a listener and remove IARM handlers if last listener +uint32_t IarmHdmiInput::UnRegister(device::HdmiInput::IEvent* listener) { + std::lock_guard lock(s_mutex); + + auto it = std::remove(hdmiInListener.begin(), hdmiInListener.end(), listener); + if (it != hdmiInListener.end()) { + hdmiInListener.erase(it, hdmiInListener.end()); + } + + // If no more listeners, unregister all handlers + if (hdmiInListener.empty()) { + for (auto& eh : eventHandlers) { + IARM_Bus_UnRegisterEventHandler(OWNER_NAME, eh.eventId); + } + } + + return 0; // Success +} + + + +template + +void IarmHdmiInput::Dispatch(F&& fn) { + std::lock_guard lock(s_mutex); + for (auto* listener : hdmiInListener) { + fn(listener); + } +} + +// === Handlers Implementation === + +// Each handler receives the event and dispatches to all listeners +void IarmHdmiInput::OnHDMIInEventHotPlug(const char* owner, IARM_EventId_t eventId, void *data, size_t len) { + // Cast data to the expected struct + IARM_Bus_DSMgr_EventData_t* eventData = static_cast(data); + dsHdmiInPort_t port = static_cast(eventData->data.hdmi_in_connect.port); + bool isConnected = eventData->data.hdmi_in_connect.isPortConnected; + Dispatch([&](device::HdmiInput::IEvent* l) { l->OnHDMIInEventHotPlug(port, isConnected); }); +} + +void IarmHdmiInput::OnHDMIInEventSignalStatus(const char* owner, IARM_EventId_t eventId, void *data, size_t len) { + IARM_Bus_DSMgr_EventData_t* eventData = static_cast(data); + dsHdmiInPort_t port = static_cast(eventData->data.hdmi_in_sig_status.port); + dsHdmiInSignalStatus_t status = static_cast(eventData->data.hdmi_in_sig_status.status); + Dispatch([&](device::HdmiInput::IEvent* l) { l->OnHDMIInEventSignalStatus(port, status); }); +} + +void IarmHdmiInput::OnHDMIInEventStatus(const char* owner, IARM_EventId_t eventId, void *data, size_t len) { + IARM_Bus_DSMgr_EventData_t* eventData = static_cast(data); + dsHdmiInPort_t activePort = static_cast(eventData->data.hdmi_in_status.activePort); + bool isPresented = eventData->data.hdmi_in_status.isPresented; + Dispatch([&](device::HdmiInput::IEvent* l) { l->OnHDMIInEventStatus(activePort, isPresented); }); +} + +void IarmHdmiInput::OnHDMInVideoModeUpdate(const char* owner, IARM_EventId_t eventId, void *data, size_t len) { + IARM_Bus_DSMgr_EventData_t* eventData = static_cast(data); + dsHdmiInPort_t port = static_cast(eventData->data.hdmi_in_videomode.port); + const dsVideoPortResolution_t& res = eventData->data.hdmi_in_videomode.resolution; + Dispatch([&](device::HdmiInput::IEvent* l) { l->OnHDMInVideoModeUpdate(port, res); }); +} + +void IarmHdmiInput::OnHDMInAllmStatus(const char* owner, IARM_EventId_t eventId, void *data, size_t len) { + IARM_Bus_DSMgr_EventData_t* eventData = static_cast(data); + dsHdmiInPort_t port = static_cast(eventData->data.hdmi_in_allm.port); + bool status = eventData->data.hdmi_in_allm.status; + Dispatch([&](device::HdmiInput::IEvent* l) { l->OnHDMInAllmStatus(port, status); }); +} + +void IarmHdmiInput::OnHDMInAVIContentType(const char* owner, IARM_EventId_t eventId, void *data, size_t len) { + IARM_Bus_DSMgr_EventData_t* eventData = static_cast(data); + dsHdmiInPort_t port = static_cast(eventData->data.hdmi_in_avi_ct.port); + dsAviContentType_t type = static_cast(eventData->data.hdmi_in_avi_ct.avi_ct); + Dispatch([&](device::HdmiInput::IEvent* l) { l->OnHDMInAVIContentType(port, type); }); +} + +void IarmHdmiInput::OnHDMInAVLatency(const char* owner, IARM_EventId_t eventId, void *data, size_t len) { + IARM_Bus_DSMgr_EventData_t* eventData = static_cast(data); + int audioDelay = eventData->data.hdmi_in_av_latency.audio_latency; + int videoDelay = eventData->data.hdmi_in_av_latency.video_latency; + Dispatch([&](device::HdmiInput::IEvent* l) { l->OnHDMInAVLatency(audioDelay, videoDelay); }); +} + +void IarmHdmiInput::OnHDMInVRRStatus(const char* owner, IARM_EventId_t eventId, void *data, size_t len) { + IARM_Bus_DSMgr_EventData_t* eventData = static_cast(data); + dsVideoZoom_t zoom = static_cast(eventData->data.zoomSettings.zoomSetting); + Dispatch([&](device::HdmiInput::IEvent* l) { l->OnZoomSettingsChanged(zoom); }); +} + diff --git a/ds/include/hdmiIn.hpp b/ds/include/hdmiIn.hpp index eb2da3dc..1241c97f 100755 --- a/ds/include/hdmiIn.hpp +++ b/ds/include/hdmiIn.hpp @@ -2,7 +2,7 @@ * If not stated otherwise in this file or this component's LICENSE file the * following copyright and licenses apply: * - * Copyright 2016 RDK Management + * Copyright 2025 RDK Management * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -17,25 +17,6 @@ * limitations under the License. */ -/* - * If not stated otherwise in this file or this component's LICENSE file the - * following copyright and licenses apply: - * - * Copyright ARRIS Enterprises, Inc. 2015. - * - * 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 -*/ - /** * @defgroup devicesettings @@ -53,6 +34,17 @@ #include "dsTypes.h" +#include +#include "dsHdmiInTypes.h" +#include "dsAVDTypes.h" +#include "dsVideoDeviceTypes.h" + + +#ifdef DS_ENABLE_IARM_PATH +class IarmHdmiInput; //Forward Declaration +#else +//include the plugin file +#endif /** * @file hdmiIn.hpp @@ -62,6 +54,9 @@ static const int8_t HDMI_IN_PORT_NONE = -1; +#define SUCCESS (0) +#define FAIL (1) + namespace device { @@ -73,7 +68,72 @@ namespace device class HdmiInput { +#ifdef DS_ENABLE_IARM_PATH + using DefaultImpl = IarmHdmiInput; +#else + //include the plugin file class as the DefaultImpl +#endif + public: + + struct IEvent { + // @brief HDMI Event Hot Plug + // @text onHDMIInEventHotPlug + // @param port: port 0 or 1 et al + // @param isConnected: is it connected (true) or not (false) + virtual void OnHDMIInEventHotPlug(dsHdmiInPort_t port, bool isConnected) { }; + + // @brief HDMI Event Signal status + // @text OnHDMIInEventSignalStatus + // @param port: port 0 or 1 et al + // @param signalStatus: Signal Status + virtual void OnHDMIInEventSignalStatus(dsHdmiInPort_t port, dsHdmiInSignalStatus_t signalStatus) { }; + + // @brief HDMI Event Signal status + // @text onHDMIInEventStatus + // @param activePort: port 0 or 1 et al + // @param isPresented: is it presented or not + virtual void OnHDMIInEventStatus(dsHdmiInPort_t activePort, bool isPresented) { }; + + // @brief HDMI Video Mode update + // @text onHDMInVideoModeUpdate + // @param port: port 0 or 1 et al + // @param videoPortResolution: Video port resolution + virtual void OnHDMInVideoModeUpdate(dsHdmiInPort_t port, const dsVideoPortResolution_t& videoPortResolution) { }; + + // @brief HDMI ALLM (Auto Low Latency Mode) status + // @text onHDMInAllmStatus + // @param port: port 0 or 1 et al + // @param allmStatus: allm status + virtual void OnHDMInAllmStatus(dsHdmiInPort_t port, bool allmStatus) { }; + + // @brief HDMI Event AVI content type + // @text OnHDMInAVIContentType + // @param port: port 0 or 1 et al + // @param aviContentType: AVI content type + virtual void OnHDMInAVIContentType(dsHdmiInPort_t port, dsAviContentType_t aviContentType) { }; + + // @brief HDMI Event AV Latency + // @text OnHDMInAVLatency + // @param audioDelay: audio delay (in millisecs) + // @param videoDelay: video delay (in millisecs) + virtual void OnHDMInAVLatency(int audioDelay, int videoDelay) { }; + + // @brief HDMI VRR status + // @text OnHDMInVRRStatus + // @param port: port 0 or 1 et al + // @param vrrType: VRR type + virtual void OnHDMInVRRStatus(dsHdmiInPort_t port, dsVRRType_t vrrType) { }; + + // @brief Zoom settings changed + // @text OnZoomSettingsChanged + // @param zoomSetting: Currently applied zoom setting + virtual void OnZoomSettingsChanged(dsVideoZoom_t zoomSetting) { }; + }; + + uint32_t Register(IEvent *listener); + uint32_t UnRegister(IEvent *listener); + static HdmiInput & getInstance(); uint8_t getNumberOfInputs () const; @@ -103,7 +163,8 @@ class HdmiInput void getHdmiVersion (int iHdmiPort, dsHdmiMaxCapabilityVersion_t *capversion); private: HdmiInput (); /* default constructor */ - virtual ~HdmiInput (); /* destructor */ + ~HdmiInput (); /* destructor */ + std::unique_ptr implHdmiIn; }; diff --git a/ds/include/iarmHdmiIn.hpp b/ds/include/iarmHdmiIn.hpp new file mode 100644 index 00000000..24f0a4a2 --- /dev/null +++ b/ds/include/iarmHdmiIn.hpp @@ -0,0 +1,83 @@ + +/* + * If not stated otherwise in this file or this component's LICENSE file the + * following copyright and licenses apply: + * + * Copyright 2025 RDK Management + * + * 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. +*/ + +/** +* @defgroup devicesettings +* @{ +* @defgroup ds +* @{ +**/ + + +#ifndef _IARM_HDMIIN_HPP_ +#define _IARM_HDMIIN_HPP_ + +#include +#include "dsTypes.h" +#include + + +#pragma once +#include "HdmiIn.hpp" +#include "dsMgr.h" +#include "libIARM.h" +#include +#include + +class IarmHdmiInput { +public: + IarmHdmiInput(); + ~IarmHdmiInput(); + + uint32_t Register(device::HdmiInput::IEvent* listener); + uint32_t UnRegister(device::HdmiInput::IEvent* listener); + +private: + // Event Handlers + static void OnHDMIInEventHotPlug(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + static void OnHDMIInEventSignalStatus(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + static void OnHDMIInEventStatus(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + static void OnHDMInVideoModeUpdate(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + static void OnHDMInAllmStatus(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + static void OnHDMInAVIContentType(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + static void OnHDMInAVLatency(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + static void OnHDMInVRRStatus(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + static void OnHDMIHotPlug(const char* owner, IARM_EventId_t eventId, void *data, size_t len); + + template + static void Dispatch(F&& fn); + + struct EventHandlerMapping { + IARM_EventId_t eventId; + IARM_EventHandler_t handler; + }; + + static constexpr EventHandlerMapping eventHandlers[]; + static constexpr const char* OWNER_NAME; + + static std::mutex s_mutex; + static std::vector hdmiInListener; +}; + +#endif /* _IARM_HDMIIN_HPP_ */ + + +/** @} */ +/** @} */