From f604db775ee7695e5c7ce8f41fc3d4aff30eda7a Mon Sep 17 00:00:00 2001 From: Ilho Kim Date: Mon, 27 Jun 2022 13:39:43 +0900 Subject: [PATCH 1/1] Apply cpu priority inheritance If a process with a high cpu priority attempts IPC with a non cpu boosting process the high cpu priority of the process becomes useless To improve the priority inversion problem apply cpu priority inheritance to pkginfo-server Change-Id: I05414234f147d360ce63820b53edbbabda872aad Signed-off-by: Ilho Kim --- CMakeLists.txt | 2 ++ packaging/pkgmgr-info.spec | 1 + src/client/pkginfo_client.cc | 35 +++++++++++++++++++++++++++++++++++ src/client/pkginfo_client.hh | 12 ++++++++++++ src/server/runner.cc | 16 +++++++++++++++- src/server/runner.hh | 1 + 6 files changed, 66 insertions(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index a7b24f6..ab7f4e3 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -45,6 +45,7 @@ pkg_check_modules(libpkgs REQUIRED cynara-client-async cynara-session cynara-creds-socket + capi-system-resource ) FOREACH(flag ${libpkgs_CFLAGS}) @@ -68,6 +69,7 @@ pkg_check_modules(libpkgs_server REQUIRED cynara-client-async cynara-session cynara-creds-socket + capi-system-resource ) FOREACH(flag ${libpkgs_server_CFLAGS}) diff --git a/packaging/pkgmgr-info.spec b/packaging/pkgmgr-info.spec index bb4b445..b988ab9 100755 --- a/packaging/pkgmgr-info.spec +++ b/packaging/pkgmgr-info.spec @@ -27,6 +27,7 @@ BuildRequires: pkgconfig(parcel) BuildRequires: pkgconfig(cynara-client-async) BuildRequires: pkgconfig(cynara-session) BuildRequires: pkgconfig(cynara-creds-socket) +BuildRequires: pkgconfig(capi-system-resource) %if 0%{?gcov:1} BuildRequires: lcov diff --git a/src/client/pkginfo_client.cc b/src/client/pkginfo_client.cc index dd1bcbd..922bbf0 100644 --- a/src/client/pkginfo_client.cc +++ b/src/client/pkginfo_client.cc @@ -4,6 +4,7 @@ #include "pkginfo_client.hh" +#include #include #include @@ -26,6 +27,37 @@ namespace pkgmgr_client { constexpr const char SOCK_PATH[] = "/run/pkgmgr-info-server"; constexpr const char SERVER_READY[] = "/run/.pkginfo_server_ready"; +constexpr const char DEST_PROCESS_NAME[] = "pkgmgr-info"; + +PkgInfoClient::CPUInheritanceInvoker::CPUInheritanceInvoker() + : set_complete_(false) {} + +PkgInfoClient::CPUInheritanceInvoker::~CPUInheritanceInvoker() { + ClearCPUInheritance(); +} + +void PkgInfoClient::CPUInheritanceInvoker::SetCPUInheritance() { + int ret = resource_set_cpu_inheritance(gettid(), DEST_PROCESS_NAME, -1); + if (ret != 0) { + LOG(ERROR) << "set cpu inheritance fail ret : " << ret; + return; + } + + set_complete_ = true; +} + +void PkgInfoClient::CPUInheritanceInvoker::ClearCPUInheritance() { + if (!set_complete_) + return; + + int ret = resource_clear_cpu_inheritance(gettid(), DEST_PROCESS_NAME); + if (ret != 0) { + LOG(ERROR) << "clear cpu inheritance fail ret : " << ret; + return; + } + + set_complete_ = false; +} PkgInfoClient::PkgInfoClient( std::shared_ptr parcel, @@ -65,6 +97,7 @@ bool PkgInfoClient::SendRequest() { LOG(WARNING) << "Try to send request, Request type: " << pkgmgr_common::ReqTypeToString(req_type_); + cpu_inheritance_invoker_.SetCPUInheritance(); if (!socket_->Connect(req_type_)) { LOG(ERROR) << "Failed to connect client socket, try to direct access"; is_offline_ = true; @@ -117,6 +150,8 @@ PkgInfoClient::GetResultParcel() { return nullptr; } + cpu_inheritance_invoker_.ClearCPUInheritance(); + auto res = pkgmgr_common::parcel::ParcelableFactory::GetInst().CreateParcel( raw, len); delete[] raw; diff --git a/src/client/pkginfo_client.hh b/src/client/pkginfo_client.hh index e0634ba..67d50d0 100644 --- a/src/client/pkginfo_client.hh +++ b/src/client/pkginfo_client.hh @@ -15,6 +15,17 @@ namespace pkgmgr_client { class PkgInfoClient { public: + class CPUInheritanceInvoker { + public: + CPUInheritanceInvoker(); + ~CPUInheritanceInvoker(); + void SetCPUInheritance(); + void ClearCPUInheritance(); + + private: + bool set_complete_; + }; + PkgInfoClient( std::shared_ptr parcel, uid_t uid, pkgmgr_common::ReqType req_type); @@ -31,6 +42,7 @@ class PkgInfoClient { uid_t uid_; pkgmgr_common::ReqType req_type_; bool is_offline_; + CPUInheritanceInvoker cpu_inheritance_invoker_; }; } // namespace pkgmgr_client diff --git a/src/server/runner.cc b/src/server/runner.cc index 4e4589b..f1092d4 100644 --- a/src/server/runner.cc +++ b/src/server/runner.cc @@ -14,6 +14,7 @@ * limitations under the License. */ +#include #include #include #include @@ -41,8 +42,9 @@ namespace pkgmgr_server { namespace { static const std::string SOCK_PATH = "/run/pkgmgr-info-server"; -const char PRIVILEGE_PACKAGE_MANAGER_ADMIN[] = +constexpr const char PRIVILEGE_PACKAGE_MANAGER_ADMIN[] = "http://tizen.org/privilege/packagemanager.admin"; +constexpr const char DEST_PROCESS_NAME[] = "pkgmgr-info"; } // namespace @@ -52,6 +54,7 @@ Runner::Runner(unsigned int thread_num) { CynaraChecker::GetInst().Init(); server_ = std::make_unique(SOCK_PATH); thread_pool_ = std::make_unique(thread_num_); + SetCPUInheritance(); auto condition = static_cast(G_IO_IN); sid_ = g_unix_fd_add(server_->GetFd(), condition, OnReceiveRequest, this); pkgmgr_common::SystemLocale::GetInst().RegisterEvent(this); @@ -99,4 +102,15 @@ bool Runner::QueueRequest(std::shared_ptr req) { return true; } +void Runner::SetCPUInheritance() { + int ret; + resource_pid_t resource_st = { 0, }; + resource_st.pid = getpid(); + + ret = resource_register_cpu_inheritance_destination( + DEST_PROCESS_NAME, resource_st); + if (ret != 0) + LOG(ERROR) << "Fail to register cpu inheritance destination ret : " << ret; +} + } // namespace pkgmgr_server diff --git a/src/server/runner.hh b/src/server/runner.hh index 0a256c7..76f67cc 100644 --- a/src/server/runner.hh +++ b/src/server/runner.hh @@ -46,6 +46,7 @@ class EXPORT_API Runner private: static int OnReceiveRequest(int fd, GIOCondition cond, void* user_data); bool QueueRequest(int client_fd); + void SetCPUInheritance(); private: int sid_; -- 2.7.4