169570cc8Sopenharmony_ci/*
269570cc8Sopenharmony_ci * Copyright (c) 2024 Huawei Device Co., Ltd.
369570cc8Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
469570cc8Sopenharmony_ci * you may not use this file except in compliance with the License.
569570cc8Sopenharmony_ci * You may obtain a copy of the License at
669570cc8Sopenharmony_ci *
769570cc8Sopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
869570cc8Sopenharmony_ci *
969570cc8Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
1069570cc8Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
1169570cc8Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
1269570cc8Sopenharmony_ci * See the License for the specific language governing permissions and
1369570cc8Sopenharmony_ci * limitations under the License.
1469570cc8Sopenharmony_ci */
1569570cc8Sopenharmony_ci
1669570cc8Sopenharmony_ci#ifndef APPSPAWN_TEST_HELPER_H
1769570cc8Sopenharmony_ci#define APPSPAWN_TEST_HELPER_H
1869570cc8Sopenharmony_ci
1969570cc8Sopenharmony_ci#include <atomic>
2069570cc8Sopenharmony_ci#include <cstdint>
2169570cc8Sopenharmony_ci#include <cstdio>
2269570cc8Sopenharmony_ci#include <cstdlib>
2369570cc8Sopenharmony_ci#include <cstring>
2469570cc8Sopenharmony_ci#include <functional>
2569570cc8Sopenharmony_ci#include <mutex>
2669570cc8Sopenharmony_ci#include <pthread.h>
2769570cc8Sopenharmony_ci#include <string>
2869570cc8Sopenharmony_ci#include <unistd.h>
2969570cc8Sopenharmony_ci#include <vector>
3069570cc8Sopenharmony_ci
3169570cc8Sopenharmony_ci#include "appspawn.h"
3269570cc8Sopenharmony_ci#include "appspawn_client.h"
3369570cc8Sopenharmony_ci#include "appspawn_hook.h"
3469570cc8Sopenharmony_ci#include "appspawn_server.h"
3569570cc8Sopenharmony_ci#include "appspawn_service.h"
3669570cc8Sopenharmony_ci#include "appspawn_utils.h"
3769570cc8Sopenharmony_ci#include "list.h"
3869570cc8Sopenharmony_ci#include "loop_event.h"
3969570cc8Sopenharmony_ci
4069570cc8Sopenharmony_ci#include "app_spawn_stub.h"
4169570cc8Sopenharmony_ci
4269570cc8Sopenharmony_cinamespace OHOS {
4369570cc8Sopenharmony_citypedef struct {
4469570cc8Sopenharmony_ci    int argc;
4569570cc8Sopenharmony_ci    char *argv[0];
4669570cc8Sopenharmony_ci} CmdArgs;
4769570cc8Sopenharmony_ci
4869570cc8Sopenharmony_citypedef struct AppSpawnClient AppSpawnClient;
4969570cc8Sopenharmony_cistruct TestConnection;
5069570cc8Sopenharmony_ciclass LocalTestServer;
5169570cc8Sopenharmony_ciusing RecvMsgProcess = std::function<void(struct TestConnection *connection, const uint8_t *buffer, uint32_t buffLen)>;
5269570cc8Sopenharmony_ciusing AddTlvFunction = std::function<int(uint8_t *buffer, uint32_t bufferLen, uint32_t &realLen, uint32_t &tlvCount)>;
5369570cc8Sopenharmony_ci
5469570cc8Sopenharmony_ciclass AppSpawnTestHelper {
5569570cc8Sopenharmony_cipublic:
5669570cc8Sopenharmony_ci    AppSpawnTestHelper()
5769570cc8Sopenharmony_ci    {
5869570cc8Sopenharmony_ci        SetDefaultTestData();
5969570cc8Sopenharmony_ci    }
6069570cc8Sopenharmony_ci    ~AppSpawnTestHelper()
6169570cc8Sopenharmony_ci    {
6269570cc8Sopenharmony_ci        if (fdArg >= 0) {
6369570cc8Sopenharmony_ci            APPSPAWN_LOGE("destory test helper close fd %d", fdArg);
6469570cc8Sopenharmony_ci            close(fdArg);
6569570cc8Sopenharmony_ci        }
6669570cc8Sopenharmony_ci    }
6769570cc8Sopenharmony_ci
6869570cc8Sopenharmony_ci    void SetDefaultTestData();
6969570cc8Sopenharmony_ci    const char *GetDefaultTestAppBundleName()
7069570cc8Sopenharmony_ci    {
7169570cc8Sopenharmony_ci        return processName_.c_str();
7269570cc8Sopenharmony_ci    }
7369570cc8Sopenharmony_ci    uid_t GetTestUid()
7469570cc8Sopenharmony_ci    {
7569570cc8Sopenharmony_ci        return defaultTestUid_;
7669570cc8Sopenharmony_ci    }
7769570cc8Sopenharmony_ci    gid_t GetTestGid()
7869570cc8Sopenharmony_ci    {
7969570cc8Sopenharmony_ci        return defaultTestGid_;
8069570cc8Sopenharmony_ci    }
8169570cc8Sopenharmony_ci    gid_t GetTestGidGroup()
8269570cc8Sopenharmony_ci    {
8369570cc8Sopenharmony_ci        return defaultTestGidGroup_;
8469570cc8Sopenharmony_ci    }
8569570cc8Sopenharmony_ci    int32_t GetTestBundleIndex()
8669570cc8Sopenharmony_ci    {
8769570cc8Sopenharmony_ci        return defaultTestBundleIndex_;
8869570cc8Sopenharmony_ci    }
8969570cc8Sopenharmony_ci
9069570cc8Sopenharmony_ci    void SetTestMsgFlags(uint32_t flags)
9169570cc8Sopenharmony_ci    {
9269570cc8Sopenharmony_ci        defaultMsgFlags_ = flags;
9369570cc8Sopenharmony_ci    }
9469570cc8Sopenharmony_ci    void SetTestApl(const char *apl)
9569570cc8Sopenharmony_ci    {
9669570cc8Sopenharmony_ci        defaultApl_ = std::string(apl);
9769570cc8Sopenharmony_ci    }
9869570cc8Sopenharmony_ci    void SetTestUid(uid_t uid)
9969570cc8Sopenharmony_ci    {
10069570cc8Sopenharmony_ci        defaultTestUid_ = uid;
10169570cc8Sopenharmony_ci    }
10269570cc8Sopenharmony_ci    void SetTestGid(gid_t gid)
10369570cc8Sopenharmony_ci    {
10469570cc8Sopenharmony_ci        defaultTestGid_ = gid;
10569570cc8Sopenharmony_ci    }
10669570cc8Sopenharmony_ci    void SetProcessName(const char *name)
10769570cc8Sopenharmony_ci    {
10869570cc8Sopenharmony_ci        processName_ = std::string(name);
10969570cc8Sopenharmony_ci    }
11069570cc8Sopenharmony_ci
11169570cc8Sopenharmony_ci    AppSpawnReqMsgHandle CreateMsg(AppSpawnClientHandle handle, uint32_t msgType = MSG_APP_SPAWN, int base = 0);
11269570cc8Sopenharmony_ci    AppSpawningCtx *GetAppProperty(AppSpawnClientHandle handle, AppSpawnReqMsgHandle reqHandle);
11369570cc8Sopenharmony_ci    int AddDacInfo(AppSpawnReqMsgHandle &reqHandle);
11469570cc8Sopenharmony_ci    int AddFdInfo(AppSpawnReqMsgHandle &reqHandle);
11569570cc8Sopenharmony_ci    int CreateSocket(int type = 0);
11669570cc8Sopenharmony_ci    int CreateSendMsg(std::vector<uint8_t> &buffer, uint32_t msgType, uint32_t &msgLen,
11769570cc8Sopenharmony_ci        const std::vector<AddTlvFunction> &addTlvFuncs);
11869570cc8Sopenharmony_ci    const std::vector<const char *> &GetPermissions()
11969570cc8Sopenharmony_ci    {
12069570cc8Sopenharmony_ci        return permissions_;
12169570cc8Sopenharmony_ci    }
12269570cc8Sopenharmony_ci
12369570cc8Sopenharmony_ci    static int AddBaseTlv(uint8_t *buffer, uint32_t bufferLen, uint32_t &realLen, uint32_t &tlvCount);
12469570cc8Sopenharmony_ci    static uint32_t GenRandom(void);
12569570cc8Sopenharmony_ci    static CmdArgs *ToCmdList(const char *cmd);
12669570cc8Sopenharmony_ci    static AppSpawnContent *StartSpawnServer(std::string &cmd, CmdArgs *&args);
12769570cc8Sopenharmony_ci
12869570cc8Sopenharmony_ci    int AppSpawnReqMsgSetFlags(AppSpawnReqMsgHandle reqHandle, uint32_t tlv, uint32_t flags)
12969570cc8Sopenharmony_ci    {
13069570cc8Sopenharmony_ci        AppSpawnReqMsgNode *reqNode = (AppSpawnReqMsgNode *)reqHandle;
13169570cc8Sopenharmony_ci        APPSPAWN_CHECK_ONLY_EXPER(reqNode != nullptr, return APPSPAWN_ARG_INVALID);
13269570cc8Sopenharmony_ci        if (tlv == TLV_MSG_FLAGS) {
13369570cc8Sopenharmony_ci            *(uint32_t *)reqNode->msgFlags->flags = flags;
13469570cc8Sopenharmony_ci        } else if (tlv == TLV_PERMISSION) {
13569570cc8Sopenharmony_ci            *(uint32_t *)reqNode->permissionFlags->flags = flags;
13669570cc8Sopenharmony_ci        }
13769570cc8Sopenharmony_ci        return 0;
13869570cc8Sopenharmony_ci    }
13969570cc8Sopenharmony_ciprivate:
14069570cc8Sopenharmony_ci    AppSpawnMsgNode *CreateAppSpawnMsg(AppSpawnMsg *msg);
14169570cc8Sopenharmony_ci
14269570cc8Sopenharmony_ci    std::string processName_ = {};
14369570cc8Sopenharmony_ci    std::string defaultApl_ = "system_core";
14469570cc8Sopenharmony_ci    uid_t defaultTestUid_;
14569570cc8Sopenharmony_ci    gid_t defaultTestGid_;
14669570cc8Sopenharmony_ci    gid_t defaultTestGidGroup_;
14769570cc8Sopenharmony_ci    int32_t defaultTestBundleIndex_;
14869570cc8Sopenharmony_ci    uint32_t defaultMsgFlags_ = 0;
14969570cc8Sopenharmony_ci    int fdArg = -1;
15069570cc8Sopenharmony_ci    std::vector<const char *> permissions_ = {
15169570cc8Sopenharmony_ci        const_cast<char *>("ohos.permission.READ_IMAGEVIDEO"),
15269570cc8Sopenharmony_ci        const_cast<char *>("ohos.permission.FILE_CROSS_APP"),
15369570cc8Sopenharmony_ci        const_cast<char *>("ohos.permission.ACTIVATE_THEME_PACKAGE"),
15469570cc8Sopenharmony_ci        const_cast<char *>("ohos.permission.GET_WALLPAPER"),
15569570cc8Sopenharmony_ci        const_cast<char *>("ohos.permission.ACCESS_DATA"),
15669570cc8Sopenharmony_ci        const_cast<char *>("ohos.permission.ACCESS_DEV_FUSE"),
15769570cc8Sopenharmony_ci        const_cast<char *>("ohos.permission.FILE_ACCESS_MANAGER")
15869570cc8Sopenharmony_ci    };
15969570cc8Sopenharmony_ci};
16069570cc8Sopenharmony_ci
16169570cc8Sopenharmony_ciclass AppSpawnTestServer : public AppSpawnTestHelper {
16269570cc8Sopenharmony_cipublic:
16369570cc8Sopenharmony_ci    explicit AppSpawnTestServer(const char *cmd, bool testServer)
16469570cc8Sopenharmony_ci        : AppSpawnTestHelper(), serviceCmd_(cmd), testServer_(testServer), protectTime_(defaultProtectTime)
16569570cc8Sopenharmony_ci    {
16669570cc8Sopenharmony_ci        serverId_ = AppSpawnTestServer::serverId;
16769570cc8Sopenharmony_ci        AppSpawnTestServer::serverId++;
16869570cc8Sopenharmony_ci    }
16969570cc8Sopenharmony_ci
17069570cc8Sopenharmony_ci    explicit AppSpawnTestServer(const char *cmd)
17169570cc8Sopenharmony_ci        : AppSpawnTestHelper(), serviceCmd_(cmd), testServer_(true), protectTime_(defaultProtectTime)
17269570cc8Sopenharmony_ci    {
17369570cc8Sopenharmony_ci        serverId_ = AppSpawnTestServer::serverId;
17469570cc8Sopenharmony_ci        AppSpawnTestServer::serverId++;
17569570cc8Sopenharmony_ci    }
17669570cc8Sopenharmony_ci    ~AppSpawnTestServer();
17769570cc8Sopenharmony_ci
17869570cc8Sopenharmony_ci    void Start(void);
17969570cc8Sopenharmony_ci    void Start(RecvMsgProcess process, uint32_t time = defaultProtectTime);
18069570cc8Sopenharmony_ci    void Stop();
18169570cc8Sopenharmony_ci    void ServiceThread();
18269570cc8Sopenharmony_ci    void KillNWebSpawnServer();
18369570cc8Sopenharmony_ci
18469570cc8Sopenharmony_ci    static const uint32_t defaultProtectTime;
18569570cc8Sopenharmony_ciprivate:
18669570cc8Sopenharmony_ci    void CloseCheckHandler(void);
18769570cc8Sopenharmony_ci    void StartCheckHandler(void);
18869570cc8Sopenharmony_ci    void StopSpawnService(void);
18969570cc8Sopenharmony_ci
19069570cc8Sopenharmony_ci    static uint32_t serverId;
19169570cc8Sopenharmony_ci#ifdef USER_TIMER_TO_CHECK
19269570cc8Sopenharmony_ci    static void ProcessIdle(const TimerHandle taskHandle, void *context);
19369570cc8Sopenharmony_ci#else
19469570cc8Sopenharmony_ci    static void ProcessIdle(const IdleHandle taskHandle, void *context);
19569570cc8Sopenharmony_ci#endif
19669570cc8Sopenharmony_ci
19769570cc8Sopenharmony_ci    AppSpawnContent *content_ = nullptr;
19869570cc8Sopenharmony_ci    std::atomic<long> appPid_{-1};
19969570cc8Sopenharmony_ci    std::string serviceCmd_{};
20069570cc8Sopenharmony_ci    bool running_{false};
20169570cc8Sopenharmony_ci#ifdef USER_TIMER_TO_CHECK
20269570cc8Sopenharmony_ci    TimerHandle timer_;
20369570cc8Sopenharmony_ci#else
20469570cc8Sopenharmony_ci    IdleHandle idle_ = nullptr;
20569570cc8Sopenharmony_ci#endif
20669570cc8Sopenharmony_ci    pthread_t threadId_ = 0;
20769570cc8Sopenharmony_ci    std::atomic<bool> stop_{false};
20869570cc8Sopenharmony_ci    RecvMsgProcess recvMsgProcess_ = nullptr;
20969570cc8Sopenharmony_ci    bool testServer_ = false;
21069570cc8Sopenharmony_ci    bool serverStoped = false;
21169570cc8Sopenharmony_ci    struct timespec startTime_ {};
21269570cc8Sopenharmony_ci    uint32_t protectTime_;
21369570cc8Sopenharmony_ci    uint32_t serverId_ = 0;
21469570cc8Sopenharmony_ci    LocalTestServer *localServer_ = nullptr;
21569570cc8Sopenharmony_ci};
21669570cc8Sopenharmony_ci
21769570cc8Sopenharmony_cistruct TestConnection {
21869570cc8Sopenharmony_ci    uint32_t connectionId;
21969570cc8Sopenharmony_ci    TaskHandle stream;
22069570cc8Sopenharmony_ci    uint32_t msgRecvLen;  // 已经接收的长度
22169570cc8Sopenharmony_ci    AppSpawnMsg msg;      // 保存不完整的消息,额外保存消息头信息
22269570cc8Sopenharmony_ci    uint8_t *buffer = nullptr;
22369570cc8Sopenharmony_ci    RecvMsgProcess recvMsgProcess = nullptr;
22469570cc8Sopenharmony_ci    int SendResponse(const AppSpawnMsg *msg, int result, pid_t pid);
22569570cc8Sopenharmony_ci};
22669570cc8Sopenharmony_ci
22769570cc8Sopenharmony_ci/**
22869570cc8Sopenharmony_ci * @brief 用于client端测试,构建服务程序
22969570cc8Sopenharmony_ci *
23069570cc8Sopenharmony_ci */
23169570cc8Sopenharmony_ciclass LocalTestServer {
23269570cc8Sopenharmony_cipublic:
23369570cc8Sopenharmony_ci    LocalTestServer() {}
23469570cc8Sopenharmony_ci    ~LocalTestServer() {}
23569570cc8Sopenharmony_ci
23669570cc8Sopenharmony_ci    int Run(const char *serverName, RecvMsgProcess recvMsg);
23769570cc8Sopenharmony_ci    void Stop();
23869570cc8Sopenharmony_ci
23969570cc8Sopenharmony_ciprivate:
24069570cc8Sopenharmony_ci    using ServerInfo = struct ServerInfo_ {
24169570cc8Sopenharmony_ci        LocalTestServer *local = nullptr;
24269570cc8Sopenharmony_ci        RecvMsgProcess recvMsgProcess = nullptr;
24369570cc8Sopenharmony_ci    };
24469570cc8Sopenharmony_ci
24569570cc8Sopenharmony_ci    static int OnConnection(const LoopHandle loopHandle, const TaskHandle server);
24669570cc8Sopenharmony_ci    static void SendMessageComplete(const TaskHandle taskHandle, BufferHandle handle);
24769570cc8Sopenharmony_ci    static void OnClose(const TaskHandle taskHandle);
24869570cc8Sopenharmony_ci    static void OnReceiveRequest(const TaskHandle taskHandle, const uint8_t *buffer, uint32_t buffLen);
24969570cc8Sopenharmony_ci    TaskHandle serverHandle_ = 0;
25069570cc8Sopenharmony_ci};
25169570cc8Sopenharmony_ci}  // namespace OHOS
25269570cc8Sopenharmony_ci#endif  // APPSPAWN_TEST_HELPER_H
253