Add defensive codes for broken AppRegistry file
[platform/framework/native/appfw.git] / src / app / FApp_AppControlRegistry.cpp
index 5413239..2775ba4 100644 (file)
@@ -1,5 +1,4 @@
 //
-// Open Service Platform
 // Copyright (c) 2012 Samsung Electronics Co., Ltd.
 //
 // Licensed under the Apache License, Version 2.0 (the License);
@@ -22,8 +21,9 @@
 
 #include <new>
 #include <unique_ptr.h>
-#include <app.h>
 #include <bundle.h>
+#include <appsvc.h>
+#include <new>
 
 #include <FBaseErrors.h>
 #include <FBaseSysLog.h>
 #include <FBase_StringConverter.h>
 #include <FIo_RegistryImpl.h>
 
-#include "FAppPkg_PackageManagerImpl.h"
 #include "FApp_AppControlImpl.h"
-#include "FApp_Aul.h"
 #include "FApp_AppControlRegistry.h"
 #include "FApp_AppMessageImpl.h"
 #include "FApp_TemplateUtil.h"
-#ifdef _SINGLETON_CLEANUP
-#include "FApp_LongevityManager.h"
-#endif
 
-using namespace Tizen::App::Package;
 using namespace Tizen::Base;
 using namespace Tizen::Base::Collection;
 using namespace Tizen::Io;
@@ -56,18 +50,11 @@ namespace
 
 const wchar_t ACTL_DEFAULT_FILE[] = L"/usr/etc/app-control-info.ini";
 const wchar_t ACTL_LEGACY_FILE[] = L"/usr/etc/app-control-alias.ini";
-const wchar_t ACTL_ALIAS_FILE[] = L"/usr/etc/app-control-appid.ini";
-
-const wchar_t TIZEN_ALIAS_APPID_PREFIX[] = L"tizen.";
+const wchar_t ACTL_DEFAULT_PLUGIN[] = L"libosp-ac-platform.so";
 
-const String ACTL_REGISTRY_OP_NUM = L"OPID_Count";
-const String ACTL_REGISTRY_PUBLIC = L"Public";
 const String ACTL_REGISTRY_PATH = L"Path";
-const String ACTL_REGISTRY_TITLE = L"Title";
 const String ACTL_REGISTRY_ALIAS_PROVIDER = L"PROVIDER_ALIAS";
 
-const int PKG_CATEGORY_LEN = 256;
-const int PKG_APPID_LEN = 256;
 const int REG_VALUE_BUFFER_LEN = 256;
 
 }
@@ -80,19 +67,13 @@ _AppControlRegistry* _AppControlRegistry::__pSelf = null;
 
 _AppControlRegistry::_AppControlRegistry(void)
 {
-       __nativeList.Construct();
+       __tizenList.Construct();
 
        __aliasList.Construct();
-
-       __aliasOperation.Construct();
-
-       __aliasAppId.Construct();
 }
 
 _AppControlRegistry::~_AppControlRegistry(void)
 {
-       _DeleteCollection<AppControl>(__nativeList);
-
        _DeleteCollectionMapValue<String, _AppControlAliasEntry>(__aliasList);
 }
 
@@ -106,44 +87,40 @@ _AppControlRegistry::GetInstance(void)
                SysTryReturn(NID_APP, __pSelf != null, null, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Insufficient memory.");
                SysAssertf(__pSelf != null, "AppControl registry instance creation failure");
 
-               __pSelf->LoadRegistry();
+               __pSelf->LoadTizenAppControlRegistry();
 
                __pSelf->LoadLegacyList();
-
-               __pSelf->LoadAliasList();
-
-#ifdef _SINGLETON_CLEANUP
-               _LongevityManager::GetInstance().RegisterOwnership(*__pSelf);
-#endif
        }
 
        return __pSelf;
 }
 
+
 result
-_AppControlRegistry::LoadRegistry(void)
+_AppControlRegistry::LoadTizenAppControlRegistry(void)
 {
        _RegistryImpl reg;
 
        const String regPath = ACTL_DEFAULT_FILE;
 
        result r = reg.Construct(regPath, REG_OPEN_READ_ONLY, null);
-       SysTryReturn(NID_APP, !IsFailed(r), r, r, "[%s] Propagating.", GetErrorMessage(r));
+       if (IsFailed(r))
+       {
+               SysPropagate(NID_APP, r);
+               return r;
+       }
 
-       const int sec_count = reg.GetAllSectionCount();
-       SysTryReturnResult(NID_APP, !(sec_count <= 0), E_OBJ_NOT_FOUND, "Registry contains no data.");
+       const int secCount = reg.GetAllSectionCount();
+       SysTryReturnResult(NID_APP, !(secCount <= 0), E_OBJ_NOT_FOUND, "Registry contains no data.");
 
-       SysLog(NID_APP, "Loading %d sections from %ls", sec_count, regPath.GetPointer());
+       SysLog(NID_APP, "Loading %d sections from %ls", secCount, regPath.GetPointer());
 
        int index = 0;
        int size = 0;
-       int num = 0;
-       String actl_path;
-       String actl_name;
-
+       //int num = 0;
+       String path;
 
-       // actual parameter manipulation
-       for (int i = 0; i < sec_count; i++)
+       for (int i = 0; i < secCount; i++)
        {
                ///////////////////////////////////////////////////////////////////////
                // appcontrol Id
@@ -155,103 +132,19 @@ _AppControlRegistry::LoadRegistry(void)
                        continue;
                }
 
-               int public_open = 0;
-
-               ///////////////////////////////////////////////////////////////////////
-               // Plubic
-               index = reg.GetEntryIndex(i, ACTL_REGISTRY_PUBLIC);
-               if (index >= 0)
-               {
-                       size = sizeof(size);
-                       num = 0;
-
-                       reg.GetEntryValue(i, index, REG_VALUE_TYPE_INT, &num, &size);
-                       if (num == 1)
-                       {
-                               // public
-                               public_open = 1;
-                       }
-               }
-
                ///////////////////////////////////////////////////////////////////////
                // Path
                index = reg.GetEntryIndex(i, ACTL_REGISTRY_PATH);
                if (index >= 0)
                {
                        size = REG_VALUE_BUFFER_LEN;
-                       reg.GetEntryValue(i, index, REG_VALUE_TYPE_STRING, &actl_path, &size);
-               }
-
-               ///////////////////////////////////////////////////////////////////////
-               // Name
-               // [FIXME] SLP localized name here
-               index = reg.GetEntryIndex(i, ACTL_REGISTRY_TITLE);
-               if (index >= 0)
-               {
-                       size = REG_VALUE_BUFFER_LEN;
-                       reg.GetEntryValue(i, index, REG_VALUE_TYPE_STRING, &actl_name, &size);
-               }
-
-               //SysLog(NID_APP, "%dth iteration : %ls", i, sec_name.GetPointer());
-
-               ///////////////////////////////////////////////////////////////////////
-               // Number of operation Id
-               index = reg.GetEntryIndex(i, ACTL_REGISTRY_OP_NUM);
-               if (index >= 0)
-               {
-                       size = sizeof(size);
-                       reg.GetEntryValue(i, index, REG_VALUE_TYPE_INT, &num, &size);
-
-                       String tagName;
-                       String actl_opId;
-
-                       //SysLog(NID_APP, "number of operation %d for index %d", num, index);
-
-                       for (int j = 0; j < num; j++)
-                       {
-                               size = REG_VALUE_BUFFER_LEN;
-
-                               ///////////////////////////////////////////////////////////////
-                               // operation Id
-                               tagName.Format(10, L"OPID_%d", j);
-
-                               index = reg.GetEntryIndex(i, tagName);
-                               if (index >= 0)
-                               {
-                                       reg.GetEntryValue(i, index, REG_VALUE_TYPE_STRING, &actl_opId, &size);
-                                       actl_opId.Trim();
-                               }
-                               //SysLog(NID_APP, "Operation(%d) %ls", index, actl_opId.GetPointer());
-
-                               ///////////////////////////////////////////////////////////////
-                               // AppControl allocation
-
-                               int prop = 0;
-                               if (public_open == 1)
-                               {
-                                       prop |= _APPCONTROL_PROPERTY_PUBLIC;
-                               }
-
-                               prop |= _APPCONTROL_PROPERTY_SLP;
-
-                               //SysLog(NID_APP, "(%ls, %ls)", sec_name.GetPointer(), actl_opId.GetPointer());
-                               AppControl* pAc = _AppControlImpl::CreateN(actl_path, sec_name, actl_opId, actl_name, prop);
-
-                               if (pAc)
-                               {
-                                       __nativeList.Add(pAc);
-                               }
-                               else
-                               {
-                                       SysLog(NID_APP, "Failed to create AppControl instance (%ls, %ls, %d)",
-                                                               sec_name.GetPointer(), actl_opId.GetPointer(), public_open);
-                               }
-                       }
+                       reg.GetEntryValue(i, index, REG_VALUE_TYPE_STRING, &path, &size);
                }
 
+               __tizenList.Add(sec_name, path);
        }
 
-       SysLog(NID_APP, "Finished loading %d entries", __nativeList.GetCount());
+       SysLog(NID_APP, "Finished loading %d tizen AppControl entries", __tizenList.GetCount());
 
        return E_SUCCESS;
 }
@@ -264,7 +157,11 @@ _AppControlRegistry::LoadLegacyList(void)
        const String& regPath(ACTL_LEGACY_FILE);
 
        result r = reg.Construct(regPath, REG_OPEN_READ_ONLY, null);
-       SysTryReturn(NID_APP, !IsFailed(r), r, r, "[%s] Propagating.", GetErrorMessage(r));
+       if (IsFailed(r))
+       {
+               SysPropagate(NID_APP, r);
+               return r;
+       }
 
        const int sec_count = reg.GetAllSectionCount();
        SysTryReturnResult(NID_APP, !(sec_count <= 0), E_OBJ_NOT_FOUND, "Registry contains no data.");
@@ -313,21 +210,10 @@ _AppControlRegistry::LoadLegacyList(void)
                        r = reg.GetValue(secName, *pStr, value);
                        if (IsFailed(r))
                        {
-                               SysLog(NID_APP, "[%s] Propagating.", GetErrorMessage(r));
+                               SysPropagate(NID_APP, r);
                                continue;
                        }
 
-                       bool b = false;
-                       __aliasOperation.ContainsKey(*pStr, b);
-                       if (b)
-                       {
-                               __aliasOperation.SetValue(*pStr, value);
-                       }
-                       else
-                       {
-                               __aliasOperation.Add(*pStr, value);
-                       }
-
                        // add entry to aliasList
                        _AppControlAliasEntry* pEntry = new (std::nothrow) _AppControlAliasEntry(secName, *pStr, aliasProvider, value);
                        SysTryReturnResult(NID_APP, pEntry != null, E_OUT_OF_MEMORY, "Insufficient memory.");
@@ -343,89 +229,78 @@ _AppControlRegistry::LoadLegacyList(void)
                delete pList;
        }
 
-       SysLog(NID_APP, "Finished loading %d entries with %d operation aliases.", __aliasList.GetCount(), __aliasOperation.GetCount());
+       SysLog(NID_APP, "Finished loading %d entries.", __aliasList.GetCount());
 
        return E_SUCCESS;
 }
 
-result
-_AppControlRegistry::LoadAliasList(void)
-{
-       _RegistryImpl reg;
-
-       const String regPath = ACTL_ALIAS_FILE;
 
-       result r = reg.Construct(regPath, REG_OPEN_READ_ONLY, null);
-       SysTryReturn(NID_APP, !IsFailed(r), r, r, "[%s] Propagating.", GetErrorMessage(r));
+AppControl*
+_AppControlRegistry::GetTizenAppControlN(const String& aId, const String& oId) const
+{
+       int count = 0;
+       const String* pAppId = &aId;
+       const String* pOperation = &oId;
 
-       HashMap* pMap = null;
-       r = reg.GetEntryListN(L"Alias", &pMap);
-       if (r != E_SUCCESS)
+       // legacy check first
+       do
        {
-               SysLog(NID_APP, "[%s] Propagating.", GetErrorMessage(r));
-               delete pMap;
-               return r;
-       }
+               const _AppControlAliasEntry* const pEntry = GetAppControlAliasEntry(*pAppId, *pOperation);
+               // number does not matter
+               if (count >= 5 || pEntry == null)
+               {
+                       break;
+               }
 
-       String* pKey = null;
-       String* pVal = null;
-       std::unique_ptr<IMapEnumerator> pEnum(pMap->GetMapEnumeratorN());
-       SysTryCatch(NID_APP, pEnum.get(), r = E_OUT_OF_MEMORY , E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] Memory error.");
+               pAppId = &pEntry->provider2;
+               pOperation = &pEntry->operation2;
+               count++;
+       }
+       while (true);
 
-       while(pEnum->MoveNext() == E_SUCCESS)
-       {
-               pKey = static_cast<String*>(pEnum->GetKey());
-               pVal = static_cast<String*>(pEnum->GetValue());
 
-               __aliasAppId.Add(*pKey, *pVal);
-               //SysLog(NID_APP, "(%ls, %ls)", pKey->GetPointer(), pVal->GetPointer());
-       }
+       SysAssert(pAppId != null);
+       SysAssert(pOperation != null);
 
-       SysLog(NID_APP, "Loading %d alias sections", __aliasAppId.GetCount());
+       SysLog(NID_APP, "Found matching AppControl (%ls, %ls)", pAppId->GetPointer(), pOperation->GetPointer());
 
-CATCH:
-       delete pMap;
+       const String& soName = GetTizenAppControlProvider(*pAppId, *pOperation);
 
-       return r;
+       return _AppControlImpl::CreateN(soName, *pAppId, *pOperation, _APPCONTROL_PROPERTY_PUBLIC);
 }
 
 
-AppControl*
-_AppControlRegistry::GetNativeAppControlN(const String& aId, const String& oId) const
+String
+_AppControlRegistry::GetTizenAppControlProvider(const String& appId, const String& oId) const
 {
-       std::unique_ptr< IEnumeratorT<AppControl*> > pEnum(__nativeList.GetEnumeratorN());
-
-       while (pEnum->MoveNext() == E_SUCCESS)
+       String val;
+       result r = __tizenList.GetValue(appId, val);
+       if (r == E_SUCCESS)
        {
-               AppControl* pAc = null;
-               pEnum->GetCurrent(pAc);
-
-               if (pAc->GetAppControlProviderId() == aId && pAc->GetOperationId() == oId)
-               {
-                       SysLog(NID_APP, "Found matching AppControl (%ls, %ls)", aId.GetPointer(), oId.GetPointer());
-                       return _AppControlImpl::CreateN(*pAc);
-               }
+               SysLog(NID_APP, "Found TIZEN AppControl stub %ls for %ls.", val.GetPointer(), appId.GetPointer());
+               return val;
        }
 
-       SysLog(NID_APP, "No matching AppControl (%ls, %ls)", aId.GetPointer(), oId.GetPointer());
-
-       return null;
+       SysLog(NID_APP, "Default platform AppControl %ls is used.", ACTL_DEFAULT_PLUGIN);
+       return String(ACTL_DEFAULT_PLUGIN);
 }
 
+
+//
+// data structure for _AppControlRegistry::FindAppControlListN() only
 //
-// data structure for _AppControlRegistry::GetAppControlListN() only
-// 
 struct AppSvcIterData
 {
 public:
-       AppSvcIterData(ArrayList* pArr, const String& op) : pArray(pArr), operation(op) {}
+       AppSvcIterData(const _AppControlRegistry* pRegs, ArrayList* pArr, const String& op) : pThis(pRegs), pArray(pArr), operation(op) {}
 
+       const _AppControlRegistry* pThis;
        ArrayList* pArray;
        const String& operation;
 };
 
 //
-// callback function for _AppControlRegistry::GetAppControlListN()
+// callback function for _AppControlRegistry::FindAppControlListN()
 //
 static int
 AppSvcIterFnCb(const char* pAppId, void* pData)
@@ -435,6 +310,8 @@ AppSvcIterFnCb(const char* pAppId, void* pData)
        AppSvcIterData* pAppSvcIterData = static_cast<AppSvcIterData*>(pData);
        ArrayList* pList = pAppSvcIterData->pArray;
        SysAssert(pList != null);
+       const _AppControlRegistry* pThis = pAppSvcIterData->pThis;
+       SysAssert(pThis != null);
        const String& operation = pAppSvcIterData->operation;
 
        if (pAppId == NULL)
@@ -444,7 +321,7 @@ AppSvcIterFnCb(const char* pAppId, void* pData)
        }
 
        String appId = pAppId;
-       AppControl* pAc = _AppControlImpl::CreateN(appId, operation, false);
+       AppControl* pAc = pThis->GetTizenAppControlN(appId, operation);
        if (pAc == null)
        {
                SysLog(NID_APP, "AppControl allocation failure for %ls.", appId.GetPointer());
@@ -485,7 +362,7 @@ _AppControlRegistry::FindAppControlListN(const String* pOid, const String* pUri,
        SysTryReturn(NID_APP, pList != null, null, E_OUT_OF_MEMORY, "[E_OUT_OF_MEMORY] ArrayList creation failure.");
        pList->Construct();
 
-       AppSvcIterData data(pList, operation);
+       AppSvcIterData data(this, pList, operation);
 
        appsvc_get_list(pBundle.get(), AppSvcIterFnCb, reinterpret_cast<void*>(&data));
 
@@ -500,7 +377,7 @@ _AppControlRegistry::FindAppControlListN(const String* pOid, const String* pUri,
        return pList;
 }
 
-_AppControlRegistry::_AppControlAliasEntry*
+const _AppControlRegistry::_AppControlAliasEntry*
 _AppControlRegistry::GetAppControlAliasEntry(const String& aId, const String& oId) const
 {
        std::unique_ptr< IEnumeratorT<_AppControlAliasEntry*> > pEnum(__aliasList.GetValuesN(aId));
@@ -525,122 +402,27 @@ _AppControlRegistry::GetAppControlAliasEntry(const String& aId, const String& oI
        return null;
 }
 
-_AppControlRegistry::_AppControlAliasEntry*
-_AppControlRegistry::GetReverseAppControlAliasEntry(const String& aId, const String& oId) const
-{
-       std::unique_ptr< IMapEnumeratorT<String, _AppControlAliasEntry*> > pEnum(__aliasList.GetMapEnumeratorN());
-
-       while (pEnum->MoveNext() == E_SUCCESS)
-       {
-               _AppControlAliasEntry* pEntry = null;
-               pEnum->GetValue(pEntry);
-               if (pEntry->provider2 == aId && pEntry->operation2 == oId)
-               {
-                       SysLog(NID_APP, "Found matching AppControl (%ls, %ls)<-(%ls, %ls)", aId.GetPointer(), oId.GetPointer(), pEntry->provider.GetPointer(), pEntry->operation.GetPointer());
 
-                       return pEntry;
-               }
-       }
-
-       return null;
-}
-
-AppControl*
-_AppControlRegistry::GetAliasAppControlN(const String& aId, const String& oId) const
-{
-       _AppControlAliasEntry* pEntry = GetAppControlAliasEntry(aId, oId);
-
-       if (pEntry)
-       {
-               AppControl* pAc = GetNativeAppControlN(pEntry->provider2, pEntry->operation2);
-               if (pAc)
-               {
-                       _AppControlImpl* pImpl = _AppControlImpl::GetInstance(*pAc);
-                       pImpl->SetProperty(_APPCONTROL_PROPERTY_ALIAS);
-               }
-               else
-               {
-                       pAc = GetAppControlN(pEntry->provider2, pEntry->operation2);
-                       if (pAc)
-                       {
-                               _AppControlImpl* pImpl = _AppControlImpl::GetInstance(*pAc);
-                               pImpl->SetProperty(_APPCONTROL_PROPERTY_ALIAS);
-                       }
-                       else
-                       {
-                               SysLog(NID_APP, "No matching AppControl found.");
-                       }
-               }
-
-               return pAc;
-       }
-
-       SysLog(NID_APP, "No matching AppControl found.");
-       return null;
-}
-
-AppControl*
-_AppControlRegistry::GetAppControlN(const String& appId, const String& operationId) const
+AppId
+_AppControlRegistry::GetAliasAppId(const AppId& appId) const
 {
-       bool changeAppId = false;
+       std::unique_ptr<bundle, BundleDeleter> pBundle(bundle_create());
 
-       String actualAppId = appId;
-       if (appId.StartsWith(TIZEN_ALIAS_APPID_PREFIX, 0))
+       if (pBundle.get())
        {
-               String tmp;
-               result r = __aliasAppId.GetValue(appId, tmp);
-               if (r == E_SUCCESS)
-               {
-                       actualAppId = tmp;
-                       SysLog(NID_APP, "Found alias appId (%ls -> %ls).", appId.GetPointer(), tmp.GetPointer());
-
-                       changeAppId = true;
-               }
-       }
-
-       bool b = _Aul::IsInstalled(actualAppId);
-       SysTryReturn(NID_APP, b == true, null, E_APP_NOT_INSTALLED, "[E_APP_NOT_INSTALLED] %ls not installed.", actualAppId.GetPointer());
+               std::unique_ptr<char[]> pAppId(_StringConverter::CopyToCharArrayN(appId));
 
-       return _AppControlImpl::CreateN(actualAppId, operationId, changeAppId);
-}
-
-AppId
-_AppControlRegistry::GetReverseAliasAppId(const AppId& appId) const
-{
-       std::unique_ptr< IMapEnumeratorT<String, String> > pEnum(__aliasAppId.GetMapEnumeratorN());
+               // appsvc_set_appid() lookup for actual app ID internally
+               appsvc_set_appid(pBundle.get(), pAppId.get());
+               const char* pTmp = appsvc_get_appid(pBundle.get());
 
-       String key;
-       String value;
-       while (pEnum->MoveNext() == E_SUCCESS)
-       {
-               pEnum->GetKey(key);
-               pEnum->GetValue(value);
-               if (value == appId)
+               if (pTmp)
                {
-                       return key;
+                       return String(pTmp);
                }
        }
 
-       SysLog(NID_APP, "No entry found for %ls", appId.GetPointer());
-       return L"";
-}
-
-String
-_AppControlRegistry::GetAliasedOperation(const String& operation) const
-{
-       bool b = false;
-       __aliasOperation.ContainsKey(operation, b);
-
-       if (b)
-       {
-               String tmp;
-               __aliasOperation.GetValue(operation, tmp);
-               return tmp;
-       }
-       else
-       {
-               return String();
-       }
+       return String();
 }
 
 } } // Tizen::App