diff --git a/frameworks/concurrent_task_client/include/concurrent_task_type.h b/frameworks/concurrent_task_client/include/concurrent_task_type.h index c9194e0a4ccd0f19408fcf66c872fc89ebdf3abc..0162353e1f15a794fbd2897cf6e7bf68903dee72 100644 --- a/frameworks/concurrent_task_client/include/concurrent_task_type.h +++ b/frameworks/concurrent_task_client/include/concurrent_task_type.h @@ -51,7 +51,8 @@ enum QueryIntervalItem { }; enum DeadlineType { - DDL_RATE = 0 + DDL_RATE = 0, + MSG_GAME = 1, }; struct IntervalReply { @@ -64,6 +65,15 @@ struct IntervalReply { struct DeadlineReply { bool setStatus; }; + +enum GameStatus { + GAME_ENTRY_MSG = 0, + GAME_EXIT_MSG, + GAME_GTX_MSG, + CAMERA_ENTRY_MSG, + CAMERA_EXIT_MSG, + STATUS_MSG_MAX +}; } } #endif // CONCURRENT_TASK_SERVICES_CONCURRENTSEVICE_INCLUDE_CONCURRENT_TASK_TYPE_H diff --git a/frameworks/concurrent_task_client/src/concurrent_task_client.cpp b/frameworks/concurrent_task_client/src/concurrent_task_client.cpp index 858694a60fbf04591da3898dfd9d1466b4f5e719..5c9f91be351b73ac02f0053c403a3217490b8a13 100644 --- a/frameworks/concurrent_task_client/src/concurrent_task_client.cpp +++ b/frameworks/concurrent_task_client/src/concurrent_task_client.cpp @@ -80,6 +80,20 @@ void ConcurrentTaskClient::RequestAuth(const std::unordered_map& mapPayload) +{ + if (TryConnect() != ERR_OK) { + return; + } + Json::Value payload; + for (auto it = mapPayload.begin(); it != mapPayload.end(); ++it) { + payload[it->first] = it->second; + } + clientService_->QueryDeadline(queryItem, ddlReply, payload); + return; +} + ErrCode ConcurrentTaskClient::TryConnect() { std::lock_guard lock(mutex_); diff --git a/interfaces/inner_api/concurrent_task_client.h b/interfaces/inner_api/concurrent_task_client.h index 603667d870e2f5664363c2b01c7cfbe0f25e7d78..a00c3a537312d57642533f7b55fd631abac4e740 100644 --- a/interfaces/inner_api/concurrent_task_client.h +++ b/interfaces/inner_api/concurrent_task_client.h @@ -65,6 +65,16 @@ public: void QueryDeadline(int queryItem, DeadlineReply& ddlReply, const std::unordered_map& mapPayload); + /** + * @brief Receive game scene info provided by rss. + * + * @param queryItem Information of the corresponding query module. + * @param ddlReply Indicates the setStatus. + * @param mapPayload Indicates the context info of game. + */ + void QueryDeadline(int queryItem, DeadlineReply& ddlReply, + const std::unordered_map& mapPayload); + /** * @brief Report auth request data to the concurrent task service. * diff --git a/services/include/concurrent_task_controller.h b/services/include/concurrent_task_controller.h index 97cf3d04a26845bafbd7666a085391a36fd6d279..6a9db9d09610f042ed61dea63e675112550a94b0 100644 --- a/services/include/concurrent_task_controller.h +++ b/services/include/concurrent_task_controller.h @@ -21,6 +21,7 @@ #include #include #include +#include #include "json/json.h" #include "concurrent_task_type.h" #include "qos_policy.h" @@ -69,6 +70,10 @@ private: void PrintInfo(); bool ParsePayload(const Json::Value& payload, int& uid, int& pid); std::string GetProcessNameByToken(); + void ModifyGameState(const Json::Value& payload); + int GetGamePid(const std::string &gameMsg) const; + GameStatus GetGameScene(const std::string &gameMsg) const; + void NewForegroundAppRecord(int pid, int uiTid, bool ddlEnabled); std::mutex appInfoLock_; std::mutex rateInfoLock_; @@ -81,6 +86,7 @@ private: int systemRate_ = 0; bool rtgEnabled_ = false; bool rsAuthed_ = false; + std::atomic curGamePid_ = -1; const std::string RENDER_SERVICE_PROCESS_NAME = "render_service"; const std::string RESOURCE_SCHEDULE_PROCESS_NAME = "resource_schedule_service"; @@ -89,7 +95,7 @@ private: class ForegroundAppRecord { public: - explicit ForegroundAppRecord(int pid, int uiTid); + explicit ForegroundAppRecord(int pid, int uiTid, bool createGrp = true); ~ForegroundAppRecord(); void AddKeyThread(int tid, int prio = PRIO_NORMAL); @@ -101,6 +107,7 @@ public: void SetRate(int appRate); int GetUiTid() const; void SetUiTid(int uiTid); + void SetGrpId(int grpId); bool IsValid(); void PrintKeyThreads(); diff --git a/services/src/concurrent_task_controller.cpp b/services/src/concurrent_task_controller.cpp index 38b0a83d4d25b15877db8db51232e44a2dc70969..49b51a0a9b7c7ba961c40be992fea0848159c167 100644 --- a/services/src/concurrent_task_controller.cpp +++ b/services/src/concurrent_task_controller.cpp @@ -350,23 +350,33 @@ void TaskController::NewForeground(int uid, int pid) for (auto iter = foregroundApp_.begin(); iter != foregroundApp_.end(); iter++) { if (iter->GetPid() == pid) { found = true; - if (ddlEnabled) { + if (ddlEnabled && pid != curGamePid_) { iter->AddKeyThread(uiTid, PRIO_RT); } iter->BeginScene(); } } if (!found) { - ForegroundAppRecord *tempRecord = new ForegroundAppRecord(pid, uiTid); - if (tempRecord->IsValid()) { - foregroundApp_.push_back(*tempRecord); - if (ddlEnabled) { - tempRecord->AddKeyThread(uiTid, PRIO_RT); - } - tempRecord->BeginScene(); - } else { - delete tempRecord; + NewForegroundAppRecord(pid, uiTid, ddlEnabled); + } +} + +void TaskController::NewForegroundAppRecord(int pid, int uiTid, bool ddlEnabled) +{ + ForegroundAppRecord *tempRecord = nullptr; + if (pid == curGamePid_) { + tempRecord = new ForegroundAppRecord(pid, uiTid, false); + } else { + tempRecord = new ForegroundAppRecord(pid, uiTid, true); + } + if (tempRecord->IsValid()) { + foregroundApp_.push_back(*tempRecord); + if (ddlEnabled && pid != curGamePid_) { + tempRecord->AddKeyThread(uiTid, PRIO_RT); } + tempRecord->BeginScene(); + } else { + delete tempRecord; } } @@ -482,8 +492,9 @@ void TaskController::FocusStatusProcess(int uid, int pid, int status) void TaskController::QueryDeadline(int queryItem, DeadlineReply& ddlReply, const Json::Value& payload) { pid_t uid = IPCSkeleton::GetInstance().GetCallingUid(); - if (GetProcessNameByToken() != RENDER_SERVICE_PROCESS_NAME) { - CONCUR_LOGE("Invalid uid %{public}d, only render service can call QueryDeadline", uid); + std::string processName = GetProcessNameByToken(); + if (processName != RENDER_SERVICE_PROCESS_NAME && processName != RESOURCE_SCHEDULE_PROCESS_NAME) { + CONCUR_LOGE("Invalid uid %{public}d, only RS or RSS can call QueryDeadline", uid); return; } switch (queryItem) { @@ -491,12 +502,87 @@ void TaskController::QueryDeadline(int queryItem, DeadlineReply& ddlReply, const ModifySystemRate(payload); break; } + case MSG_GAME: { + ModifyGameState(payload); + break; + } default: { break; } } } +void TaskController::ModifyGameState(const Json::Value& payload) +{ + if (!CheckJsonValid(payload)) { + CONCUR_LOGE("[MSG_GAME]receive json invalid"); + return; + } + if (payload["gameMsg"].isNull()) { + CONCUR_LOGE("[MSG_GAME]message is null"); + return; + } + std::string gameMsg = payload["gameMsg"].asString(); + int oldGamePid = curGamePid_; + int newGamePid = GetGamePid(gameMsg); + curGamePid_ = newGamePid; + CONCUR_LOGI("[MSG_GAME]current game pid is %{public}d, old game pid is %{public}d", + newGamePid, oldGamePid); + if (curGamePid_ == -1) { + return; + } + for (auto iter = foregroundApp_.begin(); iter != foregroundApp_.end(); iter++) { + if (iter->GetPid() == curGamePid_ && iter->GetGrpId() >= 0) { + CONCUR_LOGI("[MSG_GAME]destroy rtg grp, pid is %{public}d grpId is %{public}d", + iter->GetPid(), iter->GetGrpId()); + DestroyRtgGrp(iter->GetGrpId()); + iter->SetGrpId(-1); + break; + } + } + return; +} + +int TaskController::GetGamePid(const std::string &gameMsg) const +{ + GameStatus status = GetGameScene(gameMsg); + CONCUR_LOGI("[MSG_GAME]gamescene status %{public}d", status); + int gamePid = -1; + if (status == GAME_ENTRY_MSG) { + size_t pos = gameMsg.find(","); + if (pos == string::npos) { + return -1; + } + int ret = sscanf_s(gameMsg.substr(0, pos).c_str(), "{\"gamePid\":\"%d\"", &gamePid); + if (ret == -1) { + CONCUR_LOGE("[MSG_GAME]message parsing failed, ret is %{public}d", ret); + } else { + CONCUR_LOGI("[MSG_GAME]message parsing success"); + } + } + return gamePid; +} + +GameStatus TaskController::GetGameScene(const std::string &gameMsg) const +{ + if (gameMsg.find("gameScene\":\"1") != std::string::npos) { + return GAME_ENTRY_MSG; + } + if (gameMsg.find("gameScene\":\"0") != std::string::npos) { + return GAME_EXIT_MSG; + } + if (gameMsg.find("cameraScene\":\"1") != std::string::npos) { + return CAMERA_ENTRY_MSG; + } + if (gameMsg.find("cameraScene\":\"0") != std::string::npos) { + return CAMERA_EXIT_MSG; + } + if (gameMsg.find("GTXGamePid\":") != std::string::npos) { + return GAME_GTX_MSG; + } + return STATUS_MSG_MAX; +} + bool TaskController::ModifySystemRate(const Json::Value& payload) { if (!CheckJsonValid(payload)) { @@ -632,11 +718,11 @@ int TaskController::CreateNewRtgGrp(int prioType, int rtNum) return ret; } -ForegroundAppRecord::ForegroundAppRecord(int pid, int uiTid) +ForegroundAppRecord::ForegroundAppRecord(int pid, int uiTid, bool createGrp) { pid_ = pid; uiTid_ = uiTid; - if (OHOS::system::GetBoolParameter(INTERVAL_DDL, false)) { + if (OHOS::system::GetBoolParameter(INTERVAL_DDL, false) && createGrp) { grpId_ = TaskController::GetInstance().CreateNewRtgGrp(PRIO_RT, MAX_KEY_THREADS); } else { grpId_ = -1; @@ -657,7 +743,7 @@ void ForegroundAppRecord::AddKeyThread(int tid, int prio) return; } if (grpId_ <= 0) { - CONCUR_LOGI("Add key thread fail: Grp id not been created success."); + CONCUR_LOGI("Add key thread fail: Grp id not been created success, tid is %{public}d", tid); return; } if (keyThreads_.size() >= MAX_KEY_THREADS) { @@ -708,6 +794,11 @@ int ForegroundAppRecord::GetGrpId() const return grpId_; } +void ForegroundAppRecord::SetGrpId(int grpId) +{ + grpId_ = grpId; +} + void ForegroundAppRecord::SetRate(int appRate) { rate_ = appRate; diff --git a/test/unittest/phone/concurrent_task_controller_test.cpp b/test/unittest/phone/concurrent_task_controller_test.cpp index 75b7d0a821eb0fdf383b67419b9f42022cc49e28..416e9ce1ac61986d02efcd7ce54d093390a8740c 100644 --- a/test/unittest/phone/concurrent_task_controller_test.cpp +++ b/test/unittest/phone/concurrent_task_controller_test.cpp @@ -452,5 +452,92 @@ HWTEST_F(ConcurrentTaskControllerTest, SetUiTidTest, TestSize.Level1) foreApp.SetUiTid(755); EXPECT_EQ(foreApp.GetUiTid(), 755); } + +/** + * @tc.name: SetGrpId + * @tc.desc: Test whether the SetGrpId interface are normal. + * @tc.type: FUNC + */ +HWTEST_F(ConcurrentTaskControllerTest, SetGrpId, TestSize.Level1) +{ + ForegroundAppRecord foreApp = ForegroundAppRecord(758, 758); + foreApp.SetGrpId(-1); + EXPECT_EQ(foreApp.GetGrpId(), -1); +} + +/** + * @tc.name: GetGameScene + * @tc.desc: Test whether the GetGameScene interface are normal. + * @tc.type: FUNC + */ +HWTEST_F(ConcurrentTaskControllerTest, GetGameScene, TestSize.Level1) +{ + std::string testMsg = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\"," + "\"gameScene\":\"1\",\"renderThread\":\"5579\"}"; + GameStatus status = TaskController::GetInstance().GetGameScene(testMsg); + EXPECT_EQ(status, GAME_ENTRY_MSG); + testMsg = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\",\"gameScene\":\"0\"}"; + status = TaskController::GetInstance().GetGameScene(testMsg); + EXPECT_EQ(status, GAME_EXIT_MSG); + testMsg = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\",\"gameScene\":\"2\"}"; + status = TaskController::GetInstance().GetGameScene(testMsg); + EXPECT_EQ(status, STATUS_MSG_MAX); + testMsg = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\",\"cameraScene\":\"1\"}"; + status = TaskController::GetInstance().GetGameScene(testMsg); + EXPECT_EQ(status, CAMERA_ENTRY_MSG); + testMsg = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\",\"cameraScene\":\"0\"}"; + status = TaskController::GetInstance().GetGameScene(testMsg); + EXPECT_EQ(status, CAMERA_EXIT_MSG); +} + +/** + * @tc.name: GetGamePid + * @tc.desc: Test whether the GetGamePid interface are normal. + * @tc.type: FUNC + */ +HWTEST_F(ConcurrentTaskControllerTest, GetGamePid, TestSize.Level1) +{ + std::string testMsg = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\"," + "\"gameScene\":\"1\",\"renderThread\":\"5579\"}"; + int gamePid = TaskController::GetInstance().GetGamePid(testMsg); + EXPECT_EQ(gamePid, 5578); + testMsg = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\",\"gameScene\":\"0\"}"; + gamePid = TaskController::GetInstance().GetGamePid(testMsg); + EXPECT_EQ(gamePid, -1); + testMsg = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\",\"gameScene\":\"2\"}"; + gamePid = TaskController::GetInstance().GetGamePid(testMsg); + EXPECT_EQ(gamePid, -1); +} + +/** + * @tc.name: NewForegroundAppRecord + * @tc.desc: Test whether the NewForegroundAppRecord interface are normal. + * @tc.type: FUNC + */ +HWTEST_F(ConcurrentTaskControllerTest, NewForegroundAppRecord, TestSize.Level1) +{ + TaskController::GetInstance().curGamePid_ = 756; + TaskController::GetInstance().NewForegroundAppRecord(756, 756, true); + TaskController::GetInstance().NewForegroundAppRecord(757, 757, true); + TaskController::GetInstance().NewForegroundAppRecord(757, 757, false); +} + +/** + * @tc.name: ModifyGameState + * @tc.desc: Test whether the ModifyGameState interface are normal. + * @tc.type: FUNC + */ +HWTEST_F(ConcurrentTaskControllerTest, ModifyGameState, TestSize.Level1) +{ + Json::Value payload; + payload["gameMsg"] = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\"," + "\"gameScene\":\"1\",\"renderThread\":\"5579\"}"; + TaskController::GetInstance().ModifyGameState(payload); + EXPECT_EQ(TaskController::GetInstance().curGamePid_, 5578); + payload["gameMsg"] = "{\"gamePid\":\"5578\",\"packageName\":\"com.happyelements.OhosAnimal\"," + "\"gameScene\":\"0\"}"; + TaskController::GetInstance().ModifyGameState(payload); + EXPECT_EQ(TaskController::GetInstance().curGamePid_, -1); +} } }