Fix tct failure 65/321165/2
authorIlho Kim <ilho159.kim@samsung.com>
Mon, 17 Mar 2025 00:48:15 +0000 (09:48 +0900)
committerIlho Kim <ilho159.kim@samsung.com>
Mon, 17 Mar 2025 01:52:02 +0000 (10:52 +0900)
 - Add lock to shared memory to ensure operation in race condition
 - Fix pkgid, appid management errors in ShmManager

Change-Id: I06353f2a44a09e875e19af616a9203e502c77ccc
Signed-off-by: Ilho Kim <ilho159.kim@samsung.com>
src/pkgmgrinfo_pkginfo.cc
src/server/shared_memory/shm_manager.cc
src/server/shared_memory/shm_writer.cc
src/server/shared_memory/shm_writer.hh

index d33665c3598e37c242d161e23272061b0bc872f2..4bb98405ff25c897b4e5907a5a0a83e765bd0170 100644 (file)
@@ -1614,6 +1614,8 @@ static void __free_depends_on(gpointer data)
   pkgmgrinfo_basic_free_dependency(dep);
 }
 
+extern "C" {
+
 /* This API is not exported at the header file */
 API int pkgmgrinfo_pkginfo_foreach_depends_on_by_pkgid(const char *pkgid,
     pkgmgrinfo_pkg_dependency_list_cb dependency_cb,
@@ -1645,6 +1647,8 @@ API int pkgmgrinfo_pkginfo_foreach_depends_on_by_pkgid(const char *pkgid,
   return PMINFO_R_OK;
 }
 
+}
+
 API int pkgmgrinfo_pkginfo_foreach_depends_on(pkgmgrinfo_pkginfo_h handle,
     pkgmgrinfo_pkg_dependency_list_cb dependency_cb,
     void *user_data)
index 1c0cafb67d7b26d72f284d6dab78140b9c866f84..550511f135562d98e115c451acc44e434845374f 100644 (file)
@@ -146,6 +146,19 @@ int ShmManager::CreateSharedMemory(const tizen_base::Database& db,
   std::sort(pkgs.begin(), pkgs.end());
   std::sort(apps.begin(), apps.end());
 
+  if (!pkg_writer_.Init()) {
+    LOG(ERROR) << "pkg_writer init fail";
+    return PMINFO_R_ERROR;
+  }
+
+  if (!app_writer_.Init()) {
+    LOG(ERROR) << "pkg_writer init fail";
+    return PMINFO_R_ERROR;
+  }
+
+  auto p_lock = pkg_writer_.GetLock();
+  auto a_lock = app_writer_.GetLock();
+
   if (!pkg_writer_.CreateSharedMemory(pkgs)) {
     LOG(ERROR) << "Failed to create pkg shared memory";
     return PMINFO_R_ERROR;
@@ -156,6 +169,13 @@ int ShmManager::CreateSharedMemory(const tizen_base::Database& db,
     return PMINFO_R_ERROR;
   }
 
+  pkg_app_map_.clear();
+  for (const auto& pkg : pkgs)
+    pkg_app_map_[pkg.GetPackage()];
+
+  for (const auto& app : apps)
+    pkg_app_map_[app.GetPackage()].emplace(app.GetAppId());
+
   released_ = false;
 
   return PMINFO_R_OK;
@@ -163,12 +183,14 @@ int ShmManager::CreateSharedMemory(const tizen_base::Database& db,
 
 void ShmManager::InsertWriterPID(pid_t pid) {
   std::unique_lock<std::shared_mutex> u(pid_list_lock_);
+  LOGD("InsertWriterPID %d", pid);
 
   writer_pid_list_.insert(pid);
 }
 
 bool ShmManager::EraseWriterPID(pid_t pid) {
   std::unique_lock<std::shared_mutex> u(pid_list_lock_);
+  LOGD("EraseWriterPID %d", pid);
 
   return writer_pid_list_.erase(pid) == 1;
 }
@@ -177,6 +199,7 @@ void ShmManager::RegisterPendingPackageInfo(
     const tizen_base::Database& db, package_x* info,
     pid_t pid, uid_t uid, const std::string& locale,
     pkgmgr_common::PkgWriteType write_type) {
+  LOGD("register pending package info : %s", info->package);
   if (!info || !info->package)
     return;
 
@@ -212,6 +235,9 @@ void ShmManager::UpdatePendingPackageInfo(const tizen_base::Database& db,
   tmp_filter.cache_flag = true;
   tmp_filter.list = g_slist_append(tmp_filter.list, (gpointer)&node);
 
+  auto p_lock = pkg_writer_.GetLock();
+  auto a_lock = app_writer_.GetLock();
+
   for (const auto& pkgid : pkgids) {
     auto pkg_it = pending_pkg_.find(pkgid);
     if (pkg_it == pending_pkg_.end())
@@ -244,11 +270,13 @@ void ShmManager::UpdatePendingPackageInfo(const tizen_base::Database& db,
 }
 
 void ShmManager::TrimCache() {
+  LOGD("TrimCache");
   if (!released_)
     ReleaseCache();
 }
 
 void ShmManager::ReleaseCache() {
+  LOGD("ReleaseCache");
   pending_pkg_.clear();
 
   released_ = true;
@@ -258,6 +286,7 @@ void ShmManager::UpdateCrashedWriterPackageInfo(
     const tizen_base::Database& db,
     uid_t uid, const std::string& locale,
     const std::unordered_set<pid_t>& pids) {
+  LOGD("UpdateCrashedWriterPackageInfo");
   std::vector<std::string> pkgids;
   for (const auto& [pkgid, pid] : pending_pkg_) {
     if (pids.find(pid) == pids.end())
@@ -281,6 +310,8 @@ bool ShmManager::UpdatePkg(const tizen_base::Database& db, uid_t uid,
   tmp_filter.list = g_slist_append(tmp_filter.list, (gpointer)&node);
   std::vector<pkgmgr_common::PkgInfoHandle> pkgs;
   internal::GetPkgInfo(db, &tmp_filter, uid_, locale, pkgs);
+  auto p_lock = pkg_writer_.GetLock();
+  auto a_lock = app_writer_.GetLock();
   for (const auto& pkg : pkgs) {
     std::string pkgid = pkg.GetPackage();
     if (!pkg_writer_.Erase(pkgid))
@@ -317,11 +348,13 @@ bool ShmManager::UpdateApp(const tizen_base::Database& db, uid_t uid,
   tmp_filter.list = g_slist_append(tmp_filter.list, (gpointer)&node);
 
   std::vector<pkgmgr_common::AppInfoHandle> app_list;
-  if (!app_writer_.Erase(appid))
-    return false;
   internal::GetAppInfo(db, &tmp_filter, uid_, uid, locale, app_list);
   g_slist_free(tmp_filter.list);
 
+  auto a_lock = app_writer_.GetLock();
+  if (!app_writer_.Erase(appid))
+    return false;
+
   for (const auto& app : app_list)
     if (!AddApp(app))
       return false;
@@ -343,6 +376,7 @@ bool ShmManager::UpdateAppByPkgid(const tizen_base::Database& db,
   std::vector<pkgmgr_common::AppInfoHandle> app_list;
   internal::GetAppInfo(db, &tmp_filter, uid_, uid, locale, app_list);
 
+  auto a_lock = app_writer_.GetLock();
   for (const auto& appid : pkg_app_map_[pkgid])
     if (!app_writer_.Erase(appid))
       return false;
index e40027ca238e0fe4f3bb80fba60ada469f28c1e9..16073bc40aace77cef9df9712e3eade7728c3258 100644 (file)
@@ -44,18 +44,17 @@ namespace pc = pkgmgr_common;
 namespace ps = pkgmgr_common::shared_memory;
 
 template<typename T>
-bool ShmWriter<T>::CreateSharedMemory(const std::vector<T>& handles) {
+bool ShmWriter<T>::Init() {
   if (!config_handler_.Create()) {
     LOGE("Failed to create config handler");
     return false;
   }
 
-  int ret = config_handler_.GetWriteLock();
-  if (ret != 0) {
-    LOGE("GetWriteLock fail, %d", ret);
-    return false;
-  }
+  return true;
+}
 
+template<typename T>
+bool ShmWriter<T>::CreateSharedMemory(const std::vector<T>& handles) {
   WriteHandles(handles);
 
   config_handler_.SetMemSize(handle_mapper_.GetSize());
@@ -398,5 +397,10 @@ size_t ShmWriter<T>::GetHandleSize() const {
   return index_mapper_.GetSize() / sizeof(ps::HandleMappingData);
 }
 
+template<typename T>
+LockGuard ShmWriter<T>::GetLock() {
+  return LockGuard(config_handler_);
+}
+
 }  // namespace shared_memory
 }  // namespace pkgmgr_server
index 3d02830f22f3940118a3d6216608aac4519aa6a8..5e2e3a9662de546af2848a093ceac22730e482dc 100644 (file)
@@ -43,6 +43,20 @@ namespace shared_memory {
 namespace pc = pkgmgr_common;
 namespace ps = pkgmgr_common::shared_memory;
 
+class LockGuard {
+ public:
+  LockGuard(ps::ShmConfigHandler& config_handler) : config_handler_(config_handler) {
+    config_handler_.GetWriteLock();
+  }
+
+  ~LockGuard() {
+    config_handler_.Unlock();
+  }
+
+ private:
+  ps::ShmConfigHandler& config_handler_;
+};
+
 template <typename T>
 class ShmWriter {
  public:
@@ -53,9 +67,11 @@ class ShmWriter {
           handle_mapper_(handle_shm_name),
           index_mapper_(index_shm_name),
           key_mapper_(key_shm_name) {}
+  bool Init();
   bool CreateSharedMemory(const std::vector<T>& handles);
   bool Erase(const std::string& key);
   bool Insert(const T& handle);
+  LockGuard GetLock();
 
  private:
   bool WriteHandles(const std::vector<T>& handles);