diff --git a/.gitignore b/.gitignore index 942913b8..ae827539 100644 --- a/.gitignore +++ b/.gitignore @@ -34,3 +34,7 @@ source/**/Makefile source/**/Makefile.in source/**/*.deps/ source/**/.libs/ + +# Libtool wrapper scripts +source/telemetry2_0 +source/commonlib/telemetry2_0_client diff --git a/source/ccspinterface/rbusInterface.c b/source/ccspinterface/rbusInterface.c index c566005a..ca73b723 100644 --- a/source/ccspinterface/rbusInterface.c +++ b/source/ccspinterface/rbusInterface.c @@ -61,6 +61,7 @@ static xconfPrivacyModesDoNotShareCallBack privacyModesDoNotShareCallBack; static ReportProfilesDeleteDNDCallBack mprofilesDeleteCallBack; #if defined(PRIVACYMODES_CONTROL) static char* privacyModeVal = NULL; +static pthread_mutex_t privacyModeMutex = PTHREAD_MUTEX_INITIALIZER; #endif static uint32_t t2ReadyStatus = T2_STATE_NOT_READY; static char* reportProfileVal = NULL ; @@ -379,6 +380,54 @@ rbusError_t eventSubHandler(rbusHandle_t handle, rbusEventSubAction_t action, co return RBUS_ERROR_SUCCESS; } +#if defined(PRIVACYMODES_CONTROL) +/** + * Worker thread to handle privacy mode callbacks off the RBUS handler thread. + * Prevents RBUS handler starvation by moving heavy operations (profile deletion, + * XConf restart) to a detached thread. + */ +static void* privacyModeCallbackWorker(void *arg) +{ + char* mode = (char*)arg; + if(mode == NULL) + { + T2Error("%s called with NULL arg\n", __FUNCTION__); + return NULL; + } + T2Debug("%s ++in mode=%s\n", __FUNCTION__, mode); + + if(strcmp(mode, "DO_NOT_SHARE") == 0) + { + if(mprofilesDeleteCallBack != NULL) + { + if(mprofilesDeleteCallBack() != T2ERROR_SUCCESS) + { + T2Error("mprofilesDeleteCallBack failed in privacy worker\n"); + } + } + else + { + T2Debug("mprofilesDeleteCallBack not registered, skipping profile deletion\n"); + } + } + + if(privacyModesDoNotShareCallBack != NULL) + { + if(privacyModesDoNotShareCallBack() != T2ERROR_SUCCESS) + { + T2Error("privacyModesDoNotShareCallBack failed in privacy worker\n"); + } + } + else + { + T2Debug("privacyModesDoNotShareCallBack not registered, skipping DO_NOT_SHARE handling\n"); + } + + free(mode); + T2Debug("%s --out\n", __FUNCTION__); + return NULL; +} +#endif /** * Data set handler for event receiving datamodel * Data being set will be an rbusProperty object with - @@ -577,34 +626,38 @@ rbusError_t t2PropertyDataSetHandler(rbusHandle_t handle, rbusProperty_t prop, r { T2Debug("Inside datamodel handler for privacymodes profile \n"); char* data = rbusValue_ToString(paramValue_t, NULL, 0); - if(privacyModeVal != NULL) + if(!data) { - free(privacyModeVal); - privacyModeVal = NULL; + T2Error("rbusValue_ToString failed for privacy mode parameter %s\n", paramName); + return RBUS_ERROR_INVALID_INPUT; } if((strcmp(data, "SHARE") != 0) && (strcmp(data, "DO_NOT_SHARE") != 0)) { - T2Info("Unexpected privacy Mode value %s\n", data); - free(data); - return RBUS_ERROR_INVALID_INPUT; + T2Debug("PrivacyMode data is %s\n", data); + } + pthread_mutex_lock(&privacyModeMutex); + if(privacyModeVal != NULL) + { + free(privacyModeVal); + privacyModeVal = NULL; } privacyModeVal = strdup(data); - free(data); - T2Debug("PrivacyMode data is %s\n", privacyModeVal); - if(T2ERROR_SUCCESS != setPrivacyMode(privacyModeVal)) + pthread_mutex_unlock(&privacyModeMutex); + if(T2ERROR_SUCCESS != setPrivacyMode(data)) { + free(data); return RBUS_ERROR_INVALID_INPUT; } - if(strcmp(privacyModeVal, "DO_NOT_SHARE") == 0) + /* Dispatch heavy callbacks to a worker thread to avoid blocking the RBUS handler */ + pthread_t privacyWorker; + if(pthread_create(&privacyWorker, NULL, privacyModeCallbackWorker, (void*)data) == 0) { - if(mprofilesDeleteCallBack() != T2ERROR_SUCCESS) - { - return RBUS_ERROR_INVALID_INPUT; - } + pthread_detach(privacyWorker); } - if(privacyModesDoNotShareCallBack() != T2ERROR_SUCCESS) + else { - return RBUS_ERROR_INVALID_INPUT; + T2Error("Failed to create privacy mode callback worker thread\n"); + free(data); } } else @@ -751,6 +804,7 @@ rbusError_t t2PropertyDataGetHandler(rbusHandle_t handle, rbusProperty_t propert { rbusValue_t value; rbusValue_Init(&value); + pthread_mutex_lock(&privacyModeMutex); if(privacyModeVal != NULL) { rbusValue_SetString(value, privacyModeVal); @@ -758,13 +812,22 @@ rbusError_t t2PropertyDataGetHandler(rbusHandle_t handle, rbusProperty_t propert else { char *data = NULL; + pthread_mutex_unlock(&privacyModeMutex); getPrivacyMode(&data); + pthread_mutex_lock(&privacyModeMutex); if(data != NULL) { T2Debug("Privacy mode fetched from the persistent folder is %s\n", data); - rbusValue_SetString(value, data); + if(privacyModeVal == NULL) + { + privacyModeVal = data; + data = NULL; + } + rbusValue_SetString(value, privacyModeVal); + free(data); } } + pthread_mutex_unlock(&privacyModeMutex); rbusProperty_SetValue(property, value); rbusValue_Release(value); } diff --git a/source/utils/persistence.c b/source/utils/persistence.c index 065983fa..8f990e9b 100644 --- a/source/utils/persistence.c +++ b/source/utils/persistence.c @@ -48,7 +48,7 @@ static void persistReportMethodInit( ) T2ERROR fetchLocalConfigs(const char* path, Vector *configList) { - if(path == NULL || ((strcmp(path, SHORTLIVED_PROFILES_PATH) != 0) && configList == NULL)) + if(path == NULL || path[0] == '\0' || ((strcmp(path, SHORTLIVED_PROFILES_PATH) != 0) && configList == NULL)) { T2Error("Path is NULL or Configlist is NULL.. Invalid argument\n"); return T2ERROR_INVALID_ARGS; @@ -239,7 +239,7 @@ void clearPersistenceFolder(const char* path) } #else char command[256] = {'\0'}; - snprintf(command, sizeof(command), "rm -f %s*", path); + snprintf(command, sizeof(command), "rm -rf %s*", path); T2Debug("Executing command : %s\n", command); if (system(command) != 0) { @@ -254,7 +254,7 @@ void clearPersistenceFolder(const char* path) void removeProfileFromDisk(const char* path, const char* fileName) { - if(path == NULL || fileName == NULL) + if(path == NULL || path[0] == '\0' || fileName == NULL) { return; } diff --git a/source/xconf-client/Makefile.am b/source/xconf-client/Makefile.am index 201526b7..f5b08e4b 100644 --- a/source/xconf-client/Makefile.am +++ b/source/xconf-client/Makefile.am @@ -25,6 +25,8 @@ libxconfclient_la_LDFLAGS = -shared -fPIC -lcjson -lcurl if IS_LIBRDKCERTSEL_ENABLED libxconfclient_la_CFLAGS = $(LIBRDKCERTSEL_FLAG) libxconfclient_la_LDFLAGS += -lRdkCertSelector -lrdkconfig +else +libxconfclient_la_CFLAGS = endif libxconfclient_la_LIBADD = ${top_builddir}/source/t2parser/libt2parser.la ${top_builddir}/source/ccspinterface/libccspinterface.la libxconfclient_la_CPPFLAGS = -fPIC -I${PKG_CONFIG_SYSROOT_DIR}$(includedir)/dbus-1.0 \ @@ -41,3 +43,9 @@ libxconfclient_la_CPPFLAGS = -fPIC -I${PKG_CONFIG_SYSROOT_DIR}$(includedir)/dbus -I${top_srcdir}/source/protocol/http libxconfclient_la_DEPENDENCIES = ${top_builddir}/source/ccspinterface/libccspinterface.la ${top_builddir}/source/t2parser/libt2parser.la + +if IS_PRIVACYCONTROL_ENABLED +libxconfclient_la_CFLAGS += $(PRIVACYCONTROL_FLAG) +libxconfclient_la_CPPFLAGS += -I${top_srcdir}/source/privacycontrol +libxconfclient_la_DEPENDENCIES += ${top_builddir}/source/privacycontrol/libt2thunder_privacycontrol.la +endif diff --git a/source/xconf-client/xconfclient.c b/source/xconf-client/xconfclient.c index b2cc656c..212e40cb 100644 --- a/source/xconf-client/xconfclient.c +++ b/source/xconf-client/xconfclient.c @@ -42,6 +42,9 @@ #include "persistence.h" #include "telemetry2_0.h" #include "busInterface.h" +#if defined(PRIVACYMODES_CONTROL) +#include "rdkservices_privacyutils.h" +#endif #ifdef GTEST_ENABLE #define curl_easy_setopt curl_easy_setopt_mock #define curl_easy_getinfo curl_easy_getinfo_mock @@ -503,22 +506,13 @@ T2ERROR appendRequestParams(CURLU *uri) rc = curl_url_set(uri, CURLUPART_QUERY, "version=2", CURLU_APPENDQUERY); T2_CURL_APPENDREQUEST_ERROR(rc); #if defined(PRIVACYMODES_CONTROL) - if(T2ERROR_SUCCESS == getParameterValue(PRIVACYMODES_RFC, ¶mVal)) - { - memset(tempBuf, 0, MAX_URL_ARG_LEN); - snprintf(tempBuf, MAX_URL_ARG_LEN, "privacyModes=%s", paramVal); - rc = curl_url_set(uri, CURLUPART_QUERY, tempBuf, CURLU_URLENCODE | CURLU_APPENDQUERY); - T2_CURL_APPENDREQUEST_ERROR(rc); - free(paramVal); - paramVal = NULL; - } - else - { - T2Error("Failed to get Value for %s\n", PRIVACYMODES_RFC); - ret = T2ERROR_FAILURE; - goto error; - } - + getPrivacyMode(¶mVal); + memset(tempBuf, 0, MAX_URL_ARG_LEN); + snprintf(tempBuf, MAX_URL_ARG_LEN, "privacyModes=%s", paramVal); + rc = curl_url_set(uri, CURLUPART_QUERY, tempBuf, CURLU_URLENCODE | CURLU_APPENDQUERY); + T2_CURL_APPENDREQUEST_ERROR(rc); + free(paramVal); + paramVal = NULL; #endif error: if (NULL != tempBuf)