26 #include "semaphore.h"
29 #include "XrdkCentralComRFCStore.h"
30 #include "hostIf_utils.h"
32 #define TR181_RFC_STORE_KEY "TR181_STORE_FILENAME"
33 #define RFC_PROPERTIES_FILE "/etc/rfc.properties"
34 #define RFCDEFAULTS_FILE "/tmp/rfcdefaults.ini"
35 #define TR181_STORE_NONPERSISTENT_FILE "/opt/secure/RFC/tr181store_nonpersist.ini"
36 #define TR181_RFC_NONPERSISTENT_PREFIX "Device.DeviceInfo.X_RDKCENTRAL-COM_RFC.Feature.NonPersistent."
37 #define RFCDEFAULTS_ETC_DIR "/etc/rfcdefaults/"
39 #ifdef ENABLE_LLAMA_PLATCO
40 #define TR181_LOCAL_STORE_KEY "TR181_LOCAL_STORE_AMLOGIC_FILENAME"
42 #define TR181_LOCAL_STORE_KEY "TR181_LOCAL_STORE_FILENAME"
45 #define TR181_CLEAR_PARAM "Device.DeviceInfo.X_RDKCENTRAL-COM_RFC.ClearParam"
46 XRFCStore* XRFCStore::xrfcInstance = NULL;
47 const char *semName =
"localstore";
49 void XRFCStore::clearAll()
51 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
54 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Init Failed, can't handle the request\n");
57 if(m_updateInProgress)
59 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Duplicate clear DB request.. ignoring\n");
62 m_updateInProgress =
true;
64 ofstream ofs(m_filename, ofstream::trunc);
67 ofstream ofs2(TR181_STORE_NONPERSISTENT_FILE, ofstream::trunc);
70 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);
73 void XRFCStore::reloadCache()
75 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
77 if(!m_updateInProgress)
79 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"ClearDB is not issued yet or Duplicate ClearDBEnd, .. ignoring\n");
82 m_initDone = loadTR181PropertiesIntoCache();
84 m_updateInProgress =
false;
87 for (unordered_map<string, string>::iterator it=m_local_dict.begin(); it!=m_local_dict.end(); ++it)
89 if(m_dict.find(it->first) == m_dict.end())
90 m_dict[it->first] = it->second;
92 ofstream ofs(m_filename, ios::trunc | ios::out);
95 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Failed to open : %s \n", m_filename.c_str());
99 for (unordered_map<string, string>::iterator it=m_dict.begin(); it!=m_dict.end(); ++it)
101 ofs << it->first <<
'=' << it->second << endl;
106 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);
109 string XRFCStore::getRawValue(
const string &key)
111 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
113 if (strstr((
char *)key.c_str(),TR181_RFC_NONPERSISTENT_PREFIX) != NULL)
115 ifstream ifs_rfc(
"/tmp/.rfcSyncDone");
116 if(!ifs_rfc.is_open())
118 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: file /tmp/.rfcSyncDone doesn't exist, use default value.\n", __FUNCTION__);
121 unordered_map<string,string>::const_iterator it = m_nonpersist_dict.find(key);
122 if (it == m_nonpersist_dict.end()) {
125 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s : Value = %s \n", __FUNCTION__, it->second.c_str());
130 unordered_map<string,string>::const_iterator it = m_dict.find(key);
131 if (it == m_dict.end()) {
134 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s : Value = %s \n", __FUNCTION__, it->second.c_str());
139 bool XRFCStore::setRawValue(
const string &key,
const string &value)
141 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
143 if(m_updateInProgress)
145 ofstream ofs(m_filename, ios::out | ios::app);
149 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Failed to open : %s \n", m_filename.c_str());
152 ofs << key <<
'=' << value << endl;
158 return writeHashToFile(key, value, m_dict, m_filename);
161 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);
165 bool XRFCStore::writeHashToFile(
const string &key,
const string &value, unordered_map<string, string> &dict,
const string &filename)
167 ofstream ofs(filename, ios::trunc | ios::out);
171 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Failed to open : %s \n", filename.c_str());
175 if (key.compare(TR181_CLEAR_PARAM))
180 for (unordered_map<string, string>::iterator it=dict.begin(); it!=dict.end(); ++it)
182 ofs << it->first <<
'=' << it->second << endl;
190 faultCode_t XRFCStore::clearValue(
const string &key,
const string &value)
192 bool foundInLocalStore =
false;
194 sem_t *sem_id = sem_open(semName, O_CREAT, 0600, 1);
195 if (sem_id == SEM_FAILED){
196 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_open failed \n", __FUNCTION__);
197 return fcInternalError;
200 if (sem_wait(sem_id) < 0)
202 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_wait failed \n", __FUNCTION__);
205 loadFileToCache(m_local_filename, m_local_dict);
206 unordered_map<string, string> temp_local_dict(m_local_dict);
208 for (unordered_map<string, string>::iterator it=temp_local_dict.begin(); it!=temp_local_dict.end(); ++it)
212 if(!it->first.compare(value) || (value.back() ==
'.' && it->first.find(value) != string::npos) )
214 RDK_LOG(RDK_LOG_INFO, LOG_TR69HOSTIF,
"Clearing param: %s\n", it->first.c_str());
215 m_local_dict.erase(it->first);
216 m_dict.erase(it->first);
217 foundInLocalStore =
true;
221 if (foundInLocalStore)
223 writeHashToFile(key, value, m_local_dict, m_local_filename);
224 writeHashToFile(key, value, m_dict, m_filename);
227 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Parameter to be cleared is not present in tr181localstore.ini\n");
229 if (sem_post(sem_id) < 0)
230 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_post failed \n", __FUNCTION__);
232 if (sem_close(sem_id) != 0){
233 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_close failed \n", __FUNCTION__);
241 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
244 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Init Failed, can't handle the request\n");
245 return fcInternalError;
247 string rawValue = getRawValue(stMsgData->
paramName);
248 if(rawValue.length() > 0)
250 putValue(stMsgData, rawValue.c_str());
255 RDK_LOG(RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"%s : Parameter Not Found in %s\n", stMsgData->
paramName, m_filename.c_str());
256 unordered_map<string,string>::const_iterator it = m_dict_rfcdefaults.find(stMsgData->
paramName);
257 if (it != m_dict_rfcdefaults.end())
259 RDK_LOG(RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"%s : Param found in rfcdefaults\n", stMsgData->
paramName);
260 rawValue = it->second;
261 if(rawValue.length() > 0)
263 putValue(stMsgData, rawValue.c_str());
268 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s : Parameter Found in rfcdefaults is empty\n", stMsgData->
paramName);
274 RDK_LOG(RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"%s : Parameter Not Found in rfcdefaults\n", stMsgData->
paramName);
278 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s\n", __FUNCTION__);
284 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
287 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Init Failed, can't handle the request\n");
288 return fcInternalError;
290 const string &givenValue = getStringValue(stMsgData);
292 if (!strcmp(stMsgData->
paramName,TR181_CLEAR_PARAM))
294 return clearValue(stMsgData->
paramName, givenValue);
297 if (strstr(stMsgData->
paramName,TR181_RFC_NONPERSISTENT_PREFIX) != NULL)
299 if(stMsgData->
requestor == HOSTIF_SRC_RFC)
301 if(!writeHashToFile(stMsgData->
paramName, givenValue, m_nonpersist_dict, TR181_STORE_NONPERSISTENT_FILE))
303 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Failed to write to nonpersistent file \n");
304 return fcInternalError;
313 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Only RFC is allowed to set NonPersistent params.\n");
314 return fcInternalError;
318 if (stMsgData->
requestor == HOSTIF_SRC_WEBPA) {
320 sem_t *sem_id = sem_open(semName, O_CREAT, 0600, 1);
321 if (sem_id == SEM_FAILED){
322 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_open failed \n", __FUNCTION__);
323 return fcInternalError;
326 if (sem_wait(sem_id) < 0)
328 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_wait failed \n", __FUNCTION__);
331 loadFileToCache(m_local_filename, m_local_dict);
332 bool writeStatus = writeHashToFile(stMsgData->
paramName, givenValue, m_local_dict, m_local_filename);
334 if (sem_post(sem_id) < 0)
335 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_post failed \n", __FUNCTION__);
337 if (sem_close(sem_id) != 0){
338 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_close failed \n", __FUNCTION__);
343 return fcInternalError;
346 if(m_updateInProgress)
348 RDK_LOG (RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"Local tr181 set during RFC processing for %s\n", stMsgData->
paramName);
353 if(!m_updateInProgress)
355 const string ¤tValue = getRawValue(stMsgData->
paramName);
356 RDK_LOG (RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"Given Value : %s ---- Current value : %s \n", givenValue.c_str(), currentValue.c_str());
358 if(strlen(currentValue.c_str()) > 0)
360 if(!strcasecmp(currentValue.c_str(), givenValue.c_str()))
362 RDK_LOG (RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"Property value exists, don't have to overwrite\n");
368 if(setRawValue(stMsgData->
paramName, givenValue))
374 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Unable to Set Value for given Param\n");
377 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);
381 void XRFCStore::initTR181PropertiesFileName()
383 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
384 ifstream ifs_rfc(RFC_PROPERTIES_FILE);
385 if(!ifs_rfc.is_open())
387 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: Trying to open a non-existent file [%s] \n", __FUNCTION__, RFC_PROPERTIES_FILE);
392 while (getline(ifs_rfc, line)) {
393 size_t splitterPos = line.find(
'=');
394 if (splitterPos < line.length()) {
395 string key = line.substr(0, splitterPos);
396 string value = line.substr(splitterPos+1, line.length());
397 if(!strcmp(key.c_str(), TR181_RFC_STORE_KEY))
401 m_filename.erase(remove(m_filename.begin(), m_filename.end(),
'\"'), m_filename.end());
402 RDK_LOG(RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"TR181 Properties FileName = %s\n", m_filename.c_str());
404 else if(!strcmp(key.c_str(), TR181_LOCAL_STORE_KEY))
406 m_local_filename = value;
408 m_local_filename.erase(remove(m_local_filename.begin(), m_local_filename.end(),
'\"'), m_local_filename.end());
409 RDK_LOG(RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"TR181 Local FileName = %s\n", m_local_filename.c_str());
415 if(m_filename.empty())
417 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Didn't find %s in %s\n", TR181_RFC_STORE_KEY, RFC_PROPERTIES_FILE);
420 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);
423 bool init_rfcdefaults()
427 if ((dir = opendir ( RFCDEFAULTS_ETC_DIR )) != NULL)
429 std::ofstream combined_file( RFCDEFAULTS_FILE, ios::out | ios::app ) ;
430 while ((ent = readdir (dir)) != NULL )
432 if (strstr(ent->d_name,
".ini"))
434 RDK_LOG (RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"rfcdefaults file: %s\n", ent->d_name);
435 string filepath = RFCDEFAULTS_ETC_DIR;
436 std::ifstream file1( filepath.append(ent->d_name) ) ;
437 combined_file << file1.rdbuf();
438 combined_file <<
"\n";
445 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"Could not open dir %s \n", RFCDEFAULTS_ETC_DIR) ;
451 bool XRFCStore::loadFileToCache(
const string &filename, unordered_map<string, string> &dict)
453 RDK_LOG (RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
456 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s Invalid/empty filename, Unable to load properties\n", __FUNCTION__);
461 RDK_LOG (RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"%s TR181 Properties File : %s \n", __FUNCTION__, filename.c_str());
462 ifstream ifs_tr181(filename);
463 if (!ifs_tr181.is_open()) {
464 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: Trying to open a non-existent file [%s] \n", __FUNCTION__, filename.c_str());
469 while (getline(ifs_tr181, line)) {
470 size_t splitterPos = line.find(
'=');
471 if (splitterPos < line.length()) {
472 string key = line.substr(0, splitterPos);
473 string value = line.substr(splitterPos+1, line.length());
475 RDK_LOG(RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"Key = %s : Value = %s\n", key.c_str(), value.c_str());
483 bool XRFCStore::loadTR181PropertiesIntoCache()
485 loadFileToCache(m_filename, m_dict);
487 sem_t *sem_id = sem_open(semName, O_CREAT, 0600, 1);
488 if (sem_id == SEM_FAILED){
489 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_open failed \n", __FUNCTION__);
490 return fcInternalError;
493 if (sem_wait(sem_id) < 0)
495 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_wait failed \n", __FUNCTION__);
498 loadFileToCache(m_local_filename, m_local_dict);
500 if (sem_post(sem_id) < 0)
501 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_post failed \n", __FUNCTION__);
503 if (sem_close(sem_id) != 0){
504 RDK_LOG(RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: sem_close failed \n", __FUNCTION__);
507 loadFileToCache(TR181_STORE_NONPERSISTENT_FILE, m_nonpersist_dict);
509 ifstream ifs_rfcdef(RFCDEFAULTS_FILE);
510 if (!ifs_rfcdef.is_open()) {
511 RDK_LOG (RDK_LOG_ERROR, LOG_TR69HOSTIF,
"%s: Trying to open a non-existent file [%s] \n", __FUNCTION__, RFCDEFAULTS_FILE);
513 if ( init_rfcdefaults())
515 RDK_LOG(RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"Trying to open %s after newly creating\n", RFCDEFAULTS_FILE);
516 ifs_rfcdef.open(RFCDEFAULTS_FILE, ifstream::in);
517 if (!ifs_rfcdef.is_open())
525 while (getline(ifs_rfcdef, line)) {
526 size_t splitterPos = line.find(
'=');
527 if (splitterPos < line.length()) {
528 string key = line.substr(0, splitterPos);
529 string value = line.substr(splitterPos+1, line.length());
530 m_dict_rfcdefaults[key] = value;
531 RDK_LOG(RDK_LOG_DEBUG, LOG_TR69HOSTIF,
"Key = %s : Value = %s\n", key.c_str(), value.c_str());
536 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);
540 bool XRFCStore::init()
542 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
546 initTR181PropertiesFileName();
548 m_initDone = loadTR181PropertiesIntoCache();
550 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);
554 XRFCStore::XRFCStore()
556 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
559 m_updateInProgress =
false;
563 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);
568 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Entering %s \n", __FUNCTION__);
573 RDK_LOG (RDK_LOG_TRACE1, LOG_TR69HOSTIF,
"Leaving %s \n", __FUNCTION__);