1 /******************************************************************
3 * Copyright 2014 Samsung Electronics All Rights Reserved.
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
11 * http://www.apache.org/licenses/LICENSE-2.0
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
19 ******************************************************************/
20 #include "ContextExecutor.h"
22 SSMRESULT CContextExecutor::finalConstruct()
24 SSMRESULT res = SSM_E_FAIL;
28 SSM_CLEANUP_ASSERT(CreateGlobalInstance(OID_ITasker, (IBase **)&m_pTasker));
29 SSM_CLEANUP_ASSERT(CreateGlobalInstance(OID_IContextRepository, (IBase **)&m_pContextRepository));
30 SSM_CLEANUP_ASSERT(CreateGlobalInstance(OID_IContextDataReader, (IBase **)&m_pContextDataReader));
32 SSM_CLEANUP_ASSERT(m_pContextRepository->registerResourceFinderEvent(this));
34 SSM_CLEANUP_ASSERT(m_pContextRepository->startResourceFinder());
40 void CContextExecutor::finalRelease()
44 void CContextExecutor::registerCallback(ICtxEvent *pEvent)
49 //Data from soft sensors
50 void CContextExecutor::addOutput(std::vector<ContextData> contextData)
53 std::map<std::string, CallbackData>::iterator itor;
54 std::string type = contextData[0].rootName;
56 //TODO: name must be a this soft sensors identifier
57 //m_mtxRequestedContextCallback.Lock();
58 itor = m_requestedContextCallback.find(type);
59 if (itor != m_requestedContextCallback.end())
61 TypeofEvent callType = itor->second.m_callType;
62 itor->second.m_pCallbackEvent->onEvent(type, callType, contextData);
63 if (callType == SSM_ONCE)
65 unregisterContext(callType, m_registeredResources[type], this);
69 //m_mtxRequestedContextCallback.Unlock();
72 void CContextExecutor::getDataFromDatabase(std::string modelName, int startIndex, int count,
73 std::vector<ContextData> *data, int *pLastIndex)
75 m_pContextDataReader->getContextData(modelName, startIndex, count, data, pLastIndex);
78 void CContextExecutor::registerContext(TypeofEvent callType, ISSMResource *pSSMResource,
81 //will make check routine for One resource has callbacks.
82 std::vector<ISSMResource *> baseList;
84 CallbackData callbackData(callType, pSSMResource->name, pEvent);
86 //m_mtxRequestedContextCallback.Lock();
87 m_registeredResources[pSSMResource->type] = pSSMResource;
88 m_requestedContextCallback[pSSMResource->type] = callbackData;
89 //m_mtxRequestedContextCallback.Unlock();
91 //This is stand-alone sensor
92 if (pSSMResource->inputList.size() == 0)
95 std::vector<ContextData> inputData;
96 switch (pSSMResource->location)
98 case SENSOR_LOCATION_LOCAL:
99 runLogic(inputData, pSSMResource->type);
102 case SENSOR_LOCATION_REMOTE:
104 m_pContextRepository->startObserveResource(pSSMResource, this);
109 m_pContextRepository->getPrimitiveSensorList(&baseList);
110 m_pContextRepository->getSoftSensorList(&baseList);
112 for (unsigned int i = 0; i < pSSMResource->inputList.size(); ++i)
114 ISSMResource *pKeyResource = NULL;
115 if (findString(&baseList, pSSMResource->inputList[i],
116 &pKeyResource) != SSM_E_FAIL) //if element of inputList is in the primitive resources.
118 if (m_relatedSoftSensor.find(pKeyResource->type) != m_relatedSoftSensor.end()) //already exists
121 //check related Context needs insert or not. if softSensor resource is not a member of related context then insert.
122 std::vector<std::string> softSensorList = m_relatedSoftSensor[pKeyResource->type];
124 for (unsigned int j = 0; j < softSensorList.size(); ++j)
126 if (softSensorList[j].compare(pSSMResource->type) != 0)
128 m_relatedSoftSensor[pKeyResource->type].push_back(pSSMResource->type);
133 else // If first time
136 //insert resource in the all map and vector
137 m_relatedSoftSensor[pKeyResource->type].push_back(pSSMResource->type);
140 registerContext(callType, pKeyResource, this);
143 else //unable to find installed sensors. take it to keep list
145 m_mapResourceLookup[pSSMResource->inputList[i]].push_back(CallbackData(callType, pSSMResource->type,
151 void CContextExecutor::onExecute(IN void *pArg)
153 intptr_t *pMessage = (intptr_t *)pArg;
155 RESOURCE_EVENT_TYPE eventType = (RESOURCE_EVENT_TYPE)pMessage[0];
156 ISSMResource *pResource = (ISSMResource *)pMessage[1];
160 case SSM_EVENT_NORMAL:
163 case SSM_EVENT_ADDED:
164 if (m_mapResourceLookup.find(pResource->type) != m_mapResourceLookup.end())
166 CallbackData *callBack = NULL;
168 for (size_t i = 0; i < m_mapResourceLookup[pResource->type].size(); i++)
170 callBack = &m_mapResourceLookup[pResource->type][i];
172 m_relatedSoftSensor[pResource->type].push_back(callBack->m_name);
174 registerContext(callBack->m_callType, pResource, callBack->m_pCallbackEvent);
177 m_mapResourceLookup.erase(m_mapResourceLookup.find(pResource->type));
192 void CContextExecutor::onTerminate(IN void *pArg)
194 intptr_t *pMessage = (intptr_t *)pArg;
199 int CContextExecutor::onResourceEvent(RESOURCE_EVENT_TYPE eventType, ISSMResource *pSSMResource,
202 intptr_t *pMessage = new intptr_t [2];
204 pMessage[0] = eventType;
205 pMessage[1] = reinterpret_cast<intptr_t>(pSSMResource);
206 return (int)m_pTasker->addTask(this, (void *)pMessage);
209 SSMRESULT CContextExecutor::findString(std::vector<ISSMResource *> *sList, const std::string str,
210 ISSMResource **ppResource)
212 SSMRESULT ret = SSM_E_FAIL;
213 for (unsigned int i = 0 ; i < sList->size() ; ++i)
215 if ((*sList)[i]->type == str)
217 *ppResource = (*sList)[i];
225 std::map<std::string, std::vector<ContextData> > CContextExecutor::getPreparedContextList(
226 std::string primitiveSensor)
228 //check m_relatedSoftSensor / apply timestamp
230 SSMRESULT ret = SSM_E_FAIL;
232 std::map<std::string, std::vector<ContextData> > returnData;
233 std::vector<ContextData> contextDataList;
235 for (unsigned int i = 0; i < m_relatedSoftSensor[primitiveSensor].size(); ++i)
237 std::string softSensorName = m_relatedSoftSensor[primitiveSensor][i];
238 if (m_registeredResources.find(softSensorName) != m_registeredResources.end())
241 std::vector<std::string> inputList = m_registeredResources[softSensorName]->inputList;
242 for (unsigned int j = 0; j < inputList.size(); j++) //check all "inputlist" arrived or not
244 if (m_storedPrimitiveSensorData.find(inputList[j]) == m_storedPrimitiveSensorData.end())
246 //Still we have partial data
252 //Copy all properties of current primitiveSensor data to outputs
253 for (std::vector<ContextData>::iterator itor = m_storedPrimitiveSensorData[inputList[j]].begin();
254 itor != m_storedPrimitiveSensorData[inputList[j]].end(); ++itor)
256 contextDataList.push_back(*itor);
264 returnData.insert(std::make_pair(softSensorName, contextDataList));
266 contextDataList.clear();
273 //Data from every primitive sensors
274 int CContextExecutor::onEvent(std::string type, TypeofEvent callType,
275 std::vector<ContextData> ctxData)
277 //std::string root_name = ctxData.at(0).root_name; //-> deviceId+ctxData.root_name
279 if (m_relatedSoftSensor.find(type) != m_relatedSoftSensor.end()) //already registered?
281 //update recent values(overwrite)
282 m_storedPrimitiveSensorData[type] = ctxData;
285 std::map<std::string, std::vector<ContextData> > readyContextList = getPreparedContextList(type);
287 //Run SoftSensor! readyContextList has all data for run
288 std::map<std::string, std::vector<ContextData> >::iterator iter;
289 for (iter = readyContextList.begin(); iter != readyContextList.end(); ++iter)
291 std::string softSensorName = iter->first;
292 std::vector<ContextData> inputData = iter->second;
294 runLogic(inputData, softSensorName);
297 else //This data is primitive
299 //TODO: Temporally added for primitive data testing
306 void CContextExecutor::unregisterContext(TypeofEvent callType, ISSMResource *pSSMResource,
309 std::vector<ISSMResource *> baseList;
311 //This is primitive sensor
312 if (pSSMResource->inputList.size() == 0)
315 std::vector<ContextData> inputData;
316 switch (pSSMResource->location)
318 case SENSOR_LOCATION_LOCAL:
319 //TODO: Must free soft sensor
320 if (m_libraryList.find(pSSMResource->type) != m_libraryList.end() && callType != SSM_ONCE)
322 m_pContextRepository->unloadSoftSensor(m_libraryList[pSSMResource->type]);
323 m_libraryList.erase(m_libraryList.find(pSSMResource->type));
326 if (m_ctxEventList.find(pSSMResource->type) != m_ctxEventList.end())
328 m_ctxEventList.erase(m_ctxEventList.find(pSSMResource->type));
332 case SENSOR_LOCATION_REMOTE:
333 //Let observer stop work!
334 m_pContextRepository->stopObserveResource(pSSMResource);
339 //m_mtxRequestedContextCallback.Lock();
340 if (m_requestedContextCallback.find(pSSMResource->type) != m_requestedContextCallback.end())
342 m_requestedContextCallback.erase(m_requestedContextCallback.find(pSSMResource->type));
344 if (m_registeredResources.find(pSSMResource->type) != m_registeredResources.end())
346 m_registeredResources.erase(m_registeredResources.find(pSSMResource->type));
348 //m_mtxRequestedContextCallback.Unlock();
350 //TODO: support multiple concurrent query reference
351 m_pContextRepository->getPrimitiveSensorList(&baseList);
352 m_pContextRepository->getSoftSensorList(&baseList);
354 for (unsigned int i = 0 ; i < pSSMResource->inputList.size() ; ++i)
356 ISSMResource *pPrimitiveSensor = NULL;
357 if (findString(&baseList, pSSMResource->inputList[i], &pPrimitiveSensor) != SSM_E_FAIL)
359 std::vector<std::string> *softSensorList = &m_relatedSoftSensor[pPrimitiveSensor->type];
360 for (unsigned int j = 0; j < softSensorList->size(); ++j)
362 if (!(*softSensorList)[j].compare(pSSMResource->type))
364 softSensorList->erase(softSensorList->begin() + j);
366 if (softSensorList->size() == 0) //no more related context.
368 m_relatedSoftSensor.erase(m_relatedSoftSensor.find(pPrimitiveSensor->type));
371 unregisterContext(callType, pPrimitiveSensor, this);
380 //Called when soft sensor try to work
381 void CContextExecutor::runLogic(std::vector<ContextData> inputData, std::string softSensor)
383 m_mtxLibraryIO.lock();
384 if (m_ctxEventList.find(softSensor) == m_ctxEventList.end())
386 void *hSoftSensor = NULL;
387 if (m_pContextRepository->loadSoftSensor(softSensor, this, &hSoftSensor) == SSM_S_OK)
389 m_libraryList[softSensor] = hSoftSensor;
390 m_ctxEventList[softSensor] = ctxEvent;
391 m_ctxEventList[softSensor]->onCtxEvent(SPF_START, inputData);
396 m_ctxEventList[softSensor]->onCtxEvent(SPF_START, inputData);
398 m_mtxLibraryIO.unlock();