From 98078c429b33c62c1e87d52b3c17f43c9a088d5a Mon Sep 17 00:00:00 2001 From: xlei1030 Date: Mon, 28 Feb 2022 18:02:21 +0800 Subject: [PATCH 1/6] APP cold start --- BUILD.gn | 17 ++++++ bundle.json | 4 +- src/appspawn_server.cpp | 107 ++++++++++++++++++++++++++++++++-- src/include/appspawn_server.h | 1 + tools/appspawn_start_app.cpp | 28 +++++++++ 5 files changed, 151 insertions(+), 6 deletions(-) create mode 100644 tools/appspawn_start_app.cpp diff --git a/BUILD.gn b/BUILD.gn index 9f0e9b9b..a6343e9b 100755 --- a/BUILD.gn +++ b/BUILD.gn @@ -85,6 +85,7 @@ ohos_static_library("appspawn_server") { "ipc:ipc_core", "safwk:system_ability_fwk", "samgr_standard:samgr_proxy", + "os_account_standard:os_account_innerkits" ] if (build_selinux) { @@ -95,6 +96,22 @@ ohos_static_library("appspawn_server") { part_name = "${part_name}" } +ohos_executable("appspawntools") { + sources = [ "${appspawn_path}/tools/appspawn_start_app.cpp" ] + configs = [ ":appspawn_config" ] + deps = [ + "${appspawn_path}:appspawn_server", + "//base/security/access_token/interfaces/innerkits/token_setproc:libtoken_setproc", + ] + external_deps = [ + "hiviewdfx_hilog_native:libhilog", + ] + + install_enable = true + subsystem_name = "${subsystem_name}" + part_name = "${part_name}" +} + ohos_prebuilt_etc("appspawn.rc") { source = "appspawn.cfg" relative_install_dir = "init" diff --git a/bundle.json b/bundle.json index 502b4725..c0f8b74e 100644 --- a/bundle.json +++ b/bundle.json @@ -29,7 +29,8 @@ "ipc", "safwk", "samgr_standard", - "utils_base" + "utils_base", + "bundle_framework" ] }, "build": { @@ -38,6 +39,7 @@ "//base/startup/appspawn_standard:appspawn.rc", "//base/startup/appspawn_standard:appspawn_server", "//base/startup/appspawn_standard:webview", + "//base/startup/appspawn_standard:appspawntools", "//base/startup/appspawn_standard/interfaces/innerkits:appspawn_socket_client" ], "inner_kits": [ diff --git a/src/appspawn_server.cpp b/src/appspawn_server.cpp index e5679e6a..d3ff363e 100644 --- a/src/appspawn_server.cpp +++ b/src/appspawn_server.cpp @@ -41,6 +41,7 @@ #include "token_setproc.h" #include "parameter.h" #include "beget_ext.h" +#include "os_account_manager.h" #ifdef WITH_SELINUX #include "hap_restorecon.h" #endif @@ -80,6 +81,49 @@ static constexpr HiLogLabel LABEL = {LOG_CORE, 0, "AppSpawnServer"}; extern "C" { #endif +static sptr GetBundleMgrProxy() +{ + sptr systemAbilityManager = + SystemAbilityManagerClient::GetInstance().GetSystemAbilityManager(); + if (!systemAbilityManager) { + APPSPAWN_LOGI("Failed to get for systemAbilityManager"); + return nullptr; + } + + sptr remoteObject = systemAbilityManager->GetSystemAbility(BUNDLE_MGR_SERVICE_SYS_ABILITY_ID); + if (!remoteObject) { + APPSPAWN_LOGI("Failed to get for remoteObject"); + return nullptr; + } + sptr bundleMgr = iface_cast(remoteObject); + if (!bundleMgr) { + APPSPAWN_LOGI("Failed to get for bundleMgr"); + return nullptr; + } + return bundleMgr; +} + +static int GetApplicationInfo(const std::string &bundleName, int applicationFlag, int userId, AppExecFwk::ApplicationInfo &appInfo) +{ + sptr bundleMgr = GetBundleMgrProxy(); + if (!bundleMgr) { + APPSPAWN_LOGI("appInfo can not get bundleMgr for %s", bundleName.c_str()); + HiLog::Error(LABEL, "can not get bundleMgr for %{public}s", bundleName.c_str()); + return -1; + } + + APPSPAWN_LOGI("GetApplicationInfo userId %d", userId); + if (!bundleMgr->GetApplicationInfo(bundleName, applicationFlag, userId, appInfo)) { + APPSPAWN_LOGI("Failed to cold start %s", bundleName.c_str()); + HiLog::Error(LABEL, "Failed to cold start %{public}s", bundleName.c_str()); + return -1; + } + APPSPAWN_LOGI("GetApplicationInfo bundleName %s", appInfo.bundleName.c_str()); + APPSPAWN_LOGI("GetApplicationInfo accessTokenId %d", appInfo.accessTokenId); + APPSPAWN_LOGI("GetApplicationInfo appPrivilegeLevel %s", appInfo.appPrivilegeLevel.c_str()); + return 0; +} + static void SignalHandler([[maybe_unused]] int sig) { pid_t pid; @@ -327,7 +371,8 @@ bool AppSpawnServer::ServerMain(char *longProcName, int64_t longProcNameLen) appMap_[pid] = appProperty->processName; } socket_->CloseConnection(connectFd); // close socket connection - APPSPAWN_LOGI("AppSpawnServer::parent process create app finish, pid = %d %s", pid, appProperty->processName); + APPSPAWN_LOGI("AppSpawnServer::parent process create app finish, pid = %d uid %d %s %s", + pid, appProperty->uid, appProperty->processName, appProperty->bundleName); } while (appMap_.size() > 0) { @@ -794,15 +839,17 @@ int32_t AppSpawnServer::SetAppSandboxProperty(const ClientSocket::AppProperty *a void AppSpawnServer::SetAppAccessToken(const ClientSocket::AppProperty *appProperty) { int32_t ret = SetSelfTokenID(appProperty->accessTokenId); - if (ret != 0) { - HiLog::Error(LABEL, "AppSpawnServer::Failed to set access token id, errno = %{public}d", errno); - } + HiLog::Info(LABEL, "AppSpawnServer::set access token id = %{public}d, ret = %{public}d", + appProperty->accessTokenId, ret); + #ifdef WITH_SELINUX HapContext hapContext; ret = hapContext.HapDomainSetcontext(appProperty->apl, appProperty->processName); if (ret != 0) { HiLog::Error(LABEL, "AppSpawnServer::Failed to hap domain set context, errno = %{public}d", errno); - } + } else { + HiLog::Info(LABEL, "AppSpawnServer::Success to hap domain set context, ret = %{public}d", ret); + } #endif } @@ -927,5 +974,55 @@ bool AppSpawnServer::CheckAppProperty(const ClientSocket::AppProperty *appProper return true; } + +int AppSpawnServer::AppColdStart(char *longProcName, + int64_t longProcNameLen, const std::string &appName, const std::string uidStr) +{ + APPSPAWN_LOGI("AppColdStart appName %s uid %s", appName.c_str(), uidStr.c_str()); + LoadAceLib(); + AppExecFwk::ApplicationInfo appInfo = {}; + int ret = -1; + if (uidStr.empty()) { + std::vector activeUserIds = {}; + OHOS::AccountSA::OsAccountManager::QueryActiveOsAccountIds(activeUserIds); + APPSPAWN_LOGI("AppColdStart activeUserIds %d", activeUserIds.size()); + for (int userId : activeUserIds) { + APPSPAWN_LOGI("AppColdStart appName %s uid %d", appName.c_str(), userId); + ret = GetApplicationInfo(appName, OHOS::AppExecFwk::GET_BASIC_APPLICATION_INFO, userId, appInfo); + if (ret == 0) { + break; + } + } + } else { + uint32_t uid = atoi(uidStr.c_str()); + int32_t userId = uid / 200000; // 200000 uid to userId + ret = GetApplicationInfo(appName, OHOS::AppExecFwk::GET_BASIC_APPLICATION_INFO, userId, appInfo); + } + if (ret != 0) { + return ret; + } + auto appProperty = std::make_unique(); + if (appProperty == nullptr) { + return -1; + } + appProperty->uid = appInfo.uid; + appProperty->accessTokenId = appInfo.accessTokenId; + (void)strcpy_s(appProperty->processName, sizeof(appProperty->processName), appInfo.name.c_str()); + (void)strcpy_s(appProperty->bundleName, sizeof(appProperty->bundleName), appInfo.bundleName.c_str()); + (void)strcpy_s(appProperty->apl, sizeof(appProperty->apl), appInfo.appPrivilegeLevel.c_str()); + + int32_t fd[FDLEN2] = {FD_INIT_VALUE, FD_INIT_VALUE}; + SpecialHandle(appProperty.get()); + SetAppProcProperty(appProperty.get(), longProcName, longProcNameLen, fd); + if (ret != 0) { + return ret; + } + while (1) { + pause(); + } + printf("Clod start %s success. \n", appName.c_str()); + return 0; +} + } // namespace AppSpawn } // namespace OHOS diff --git a/src/include/appspawn_server.h b/src/include/appspawn_server.h index 6e2192a8..2d4701b4 100644 --- a/src/include/appspawn_server.h +++ b/src/include/appspawn_server.h @@ -70,6 +70,7 @@ public: */ void SetServerSocket(const std::shared_ptr &serverSocket); + int AppColdStart(char *longProcName, int64_t longProcNameLen, const std::string &appName, const std::string uid); private: static constexpr uint8_t BITLEN32 = 32; static constexpr uint8_t FDLEN2 = 2; diff --git a/tools/appspawn_start_app.cpp b/tools/appspawn_start_app.cpp new file mode 100644 index 00000000..85bf307d --- /dev/null +++ b/tools/appspawn_start_app.cpp @@ -0,0 +1,28 @@ +#include + +#include "appspawn_server.h" +#include "hilog/log.h" + +int main(int argc, char *const argv[]) +{ + if (argc <= 1) { + printf("appspawntools xxxx \n"); + return 0; + } + + // calculate child process long name size + uintptr_t start = reinterpret_cast(argv[0]); + uintptr_t end = reinterpret_cast(strchr(argv[argc - 1], 0)); + uintptr_t argvSize = end - start; + + std::string appName(argv[1]); + std::string uid ((argc > 2) ? argv[2] : ""); // 2 uid index + auto appspawnServer = std::make_shared("AppSpawn"); + if (appspawnServer != nullptr) { + int ret = appspawnServer->AppColdStart(argv[0], argvSize, appName, uid); + if (ret != 0) { + printf("Cold start %s fail \n", appName.c_str()); + } + } + return 0; +} -- Gitee From 072304a201febf4a52b1e6df1ce57375f4a5a7ad Mon Sep 17 00:00:00 2001 From: xlei1030 Date: Mon, 28 Feb 2022 18:54:07 +0800 Subject: [PATCH 2/6] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E7=BC=96=E7=A0=81?= =?UTF-8?q?=E8=A7=84=E8=8C=83?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/appspawn_server.cpp | 6 +++--- test/unittest/app_spawn_server_test/BUILD.gn | 2 ++ tools/appspawn_start_app.cpp | 18 ++++++++++++++++++ 3 files changed, 23 insertions(+), 3 deletions(-) diff --git a/src/appspawn_server.cpp b/src/appspawn_server.cpp index d3ff363e..0b018e1a 100644 --- a/src/appspawn_server.cpp +++ b/src/appspawn_server.cpp @@ -103,7 +103,8 @@ static sptr GetBundleMgrProxy() return bundleMgr; } -static int GetApplicationInfo(const std::string &bundleName, int applicationFlag, int userId, AppExecFwk::ApplicationInfo &appInfo) +static int GetApplicationInfo(const std::string &bundleName, int applicationFlag, int userId, + AppExecFwk::ApplicationInfo &appInfo) { sptr bundleMgr = GetBundleMgrProxy(); if (!bundleMgr) { @@ -849,7 +850,7 @@ void AppSpawnServer::SetAppAccessToken(const ClientSocket::AppProperty *appPrope HiLog::Error(LABEL, "AppSpawnServer::Failed to hap domain set context, errno = %{public}d", errno); } else { HiLog::Info(LABEL, "AppSpawnServer::Success to hap domain set context, ret = %{public}d", ret); - } + } #endif } @@ -1023,6 +1024,5 @@ int AppSpawnServer::AppColdStart(char *longProcName, printf("Clod start %s success. \n", appName.c_str()); return 0; } - } // namespace AppSpawn } // namespace OHOS diff --git a/test/unittest/app_spawn_server_test/BUILD.gn b/test/unittest/app_spawn_server_test/BUILD.gn index 83a07f4e..8168179c 100755 --- a/test/unittest/app_spawn_server_test/BUILD.gn +++ b/test/unittest/app_spawn_server_test/BUILD.gn @@ -53,6 +53,7 @@ ohos_unittest("AppSpawnServerOverrideTest") { "ipc:ipc_core", "safwk:system_ability_fwk", "samgr_standard:samgr_proxy", + "os_account_standard:os_account_innerkits" ] if (build_selinux) { @@ -101,6 +102,7 @@ ohos_unittest("AppSpawnServerMockTest") { "ipc:ipc_core", "safwk:system_ability_fwk", "samgr_standard:samgr_proxy", + "os_account_standard:os_account_innerkits" ] if (build_selinux) { diff --git a/tools/appspawn_start_app.cpp b/tools/appspawn_start_app.cpp index 85bf307d..e0ab0dc2 100644 --- a/tools/appspawn_start_app.cpp +++ b/tools/appspawn_start_app.cpp @@ -1,3 +1,17 @@ +/* + * Copyright (c) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ #include #include "appspawn_server.h" @@ -13,6 +27,10 @@ int main(int argc, char *const argv[]) // calculate child process long name size uintptr_t start = reinterpret_cast(argv[0]); uintptr_t end = reinterpret_cast(strchr(argv[argc - 1], 0)); + if (end == nullptr) { + printf("end result is error!!"); + return 0; + } uintptr_t argvSize = end - start; std::string appName(argv[1]); -- Gitee From 07145b85798a5da8ccfd37b999742cb735809273 Mon Sep 17 00:00:00 2001 From: xlei1030 Date: Mon, 28 Feb 2022 19:06:54 +0800 Subject: [PATCH 3/6] =?UTF-8?q?=E4=BF=AE=E6=94=B9BUILD.gn=20=E6=A0=BC?= =?UTF-8?q?=E5=BC=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- BUILD.gn | 2 +- test/unittest/app_spawn_server_test/BUILD.gn | 4 ++-- tools/appspawn_start_app.cpp | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/BUILD.gn b/BUILD.gn index a6343e9b..15e9bde2 100755 --- a/BUILD.gn +++ b/BUILD.gn @@ -83,9 +83,9 @@ ohos_static_library("appspawn_server") { "hilog_native:libhilog", "hiviewdfx_hilog_native:libhilog", "ipc:ipc_core", + "os_account_standard:os_account_innerkits", "safwk:system_ability_fwk", "samgr_standard:samgr_proxy", - "os_account_standard:os_account_innerkits" ] if (build_selinux) { diff --git a/test/unittest/app_spawn_server_test/BUILD.gn b/test/unittest/app_spawn_server_test/BUILD.gn index 8168179c..17deadc3 100755 --- a/test/unittest/app_spawn_server_test/BUILD.gn +++ b/test/unittest/app_spawn_server_test/BUILD.gn @@ -51,9 +51,9 @@ ohos_unittest("AppSpawnServerOverrideTest") { "hilog_native:libhilog", "hiviewdfx_hilog_native:libhilog", "ipc:ipc_core", + "os_account_standard:os_account_innerkits", "safwk:system_ability_fwk", "samgr_standard:samgr_proxy", - "os_account_standard:os_account_innerkits" ] if (build_selinux) { @@ -100,9 +100,9 @@ ohos_unittest("AppSpawnServerMockTest") { "hilog_native:libhilog", "hiviewdfx_hilog_native:libhilog", "ipc:ipc_core", + "os_account_standard:os_account_innerkits", "safwk:system_ability_fwk", "samgr_standard:samgr_proxy", - "os_account_standard:os_account_innerkits" ] if (build_selinux) { diff --git a/tools/appspawn_start_app.cpp b/tools/appspawn_start_app.cpp index e0ab0dc2..a52709bb 100644 --- a/tools/appspawn_start_app.cpp +++ b/tools/appspawn_start_app.cpp @@ -28,7 +28,7 @@ int main(int argc, char *const argv[]) uintptr_t start = reinterpret_cast(argv[0]); uintptr_t end = reinterpret_cast(strchr(argv[argc - 1], 0)); if (end == nullptr) { - printf("end result is error!!"); + printf("end result is error!!\n"); return 0; } uintptr_t argvSize = end - start; -- Gitee From 4ee363aa165632f65b9876ea6de66dc410aa3469 Mon Sep 17 00:00:00 2001 From: xlei1030 Date: Mon, 28 Feb 2022 19:29:00 +0800 Subject: [PATCH 4/6] =?UTF-8?q?=E4=BF=AE=E6=94=B9=E7=BC=96=E8=AF=91?= =?UTF-8?q?=E9=94=99=E8=AF=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- tools/appspawn_start_app.cpp | 4 ---- 1 file changed, 4 deletions(-) diff --git a/tools/appspawn_start_app.cpp b/tools/appspawn_start_app.cpp index a52709bb..50c2d160 100644 --- a/tools/appspawn_start_app.cpp +++ b/tools/appspawn_start_app.cpp @@ -27,10 +27,6 @@ int main(int argc, char *const argv[]) // calculate child process long name size uintptr_t start = reinterpret_cast(argv[0]); uintptr_t end = reinterpret_cast(strchr(argv[argc - 1], 0)); - if (end == nullptr) { - printf("end result is error!!\n"); - return 0; - } uintptr_t argvSize = end - start; std::string appName(argv[1]); -- Gitee From 5fb873d121e7c81fb11cc617c667e74d2c53e62d Mon Sep 17 00:00:00 2001 From: xlei1030 Date: Mon, 28 Feb 2022 19:47:16 +0800 Subject: [PATCH 5/6] =?UTF-8?q?fix:=20=E4=BF=AE=E6=94=B9Build.gn=E7=BC=96?= =?UTF-8?q?=E8=AF=91=E6=8A=A5=E9=94=99?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- BUILD.gn | 1 + 1 file changed, 1 insertion(+) diff --git a/BUILD.gn b/BUILD.gn index 15e9bde2..905de92a 100755 --- a/BUILD.gn +++ b/BUILD.gn @@ -163,6 +163,7 @@ ohos_static_library("webviewspawn_server") { "hilog_native:libhilog", "hiviewdfx_hilog_native:libhilog", "ipc:ipc_core", + "os_account_standard:os_account_innerkits", "safwk:system_ability_fwk", "samgr_standard:samgr_proxy", ] -- Gitee From f4491109059ca4033f5c801302c51724787ba40c Mon Sep 17 00:00:00 2001 From: xlei1030 Date: Mon, 28 Feb 2022 21:10:17 +0800 Subject: [PATCH 6/6] =?UTF-8?q?NotifyResToParentProc=20=E6=B7=BB=E5=8A=A0i?= =?UTF-8?q?f=E6=9D=A1=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- BUILD.gn | 4 +--- src/appspawn_server.cpp | 6 ++++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/BUILD.gn b/BUILD.gn index 905de92a..193a2c26 100755 --- a/BUILD.gn +++ b/BUILD.gn @@ -103,9 +103,7 @@ ohos_executable("appspawntools") { "${appspawn_path}:appspawn_server", "//base/security/access_token/interfaces/innerkits/token_setproc:libtoken_setproc", ] - external_deps = [ - "hiviewdfx_hilog_native:libhilog", - ] + external_deps = [ "hiviewdfx_hilog_native:libhilog" ] install_enable = true subsystem_name = "${subsystem_name}" diff --git a/src/appspawn_server.cpp b/src/appspawn_server.cpp index 0b018e1a..fefae587 100644 --- a/src/appspawn_server.cpp +++ b/src/appspawn_server.cpp @@ -921,8 +921,10 @@ bool AppSpawnServer::SetAppProcProperty(const ClientSocket::AppProperty *appProp void AppSpawnServer::NotifyResToParentProc(const int32_t fd, const int32_t value) { - write(fd, &value, sizeof(value)); - close(fd); + if (fd != FD_INIT_VALUE) { + write(fd, &value, sizeof(value)); + close(fd); + } } void AppSpawnServer::SpecialHandle(ClientSocket::AppProperty *appProperty) -- Gitee