1/*
2 * Copyright (c) 2021 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15#include "init_reboot.h"
16
17#include <string.h>
18#include <unistd.h>
19
20#include "beget_ext.h"
21#include "securec.h"
22#include "init_param.h"
23
24// Refer to parameter limit, value size should not bigger than 96
25#define MAX_REBOOT_OPTION_SIZE PARAM_VALUE_LEN_MAX
26
27#ifndef STARTUP_INIT_TEST
28#define DOREBOOT_PARAM "ohos.startup.powerctrl"
29#else
30#define DOREBOOT_PARAM "reboot.ut"
31#endif
32
33static int DoRebootByInitPlugin(const char *mode, const char *option)
34{
35    char value[MAX_REBOOT_OPTION_SIZE];
36    int ret = 0;
37    if (mode != NULL) {
38        if (option != NULL) {
39            ret = snprintf_s(value, MAX_REBOOT_OPTION_SIZE, MAX_REBOOT_OPTION_SIZE - 1, "reboot,%s:%s", mode, option);
40        } else {
41            ret = snprintf_s(value, MAX_REBOOT_OPTION_SIZE, MAX_REBOOT_OPTION_SIZE - 1, "reboot,%s", mode);
42        }
43    } else {
44        if (option != NULL) {
45            ret = snprintf_s(value, MAX_REBOOT_OPTION_SIZE, MAX_REBOOT_OPTION_SIZE - 1, "reboot,%s", option);
46        } else {
47            ret = snprintf_s(value, MAX_REBOOT_OPTION_SIZE, MAX_REBOOT_OPTION_SIZE - 1, "%s", "reboot");
48        }
49    }
50    BEGET_ERROR_CHECK(ret >= 0, return -1, "Failed to format boot mode ");
51    BEGET_LOGV("Reboot cmd %s", value);
52    ret = SystemSetParameter(STARTUP_DEVICE_CTL, DEVICE_CMD_STOP);
53    BEGET_ERROR_CHECK(ret == 0, return -1, "Failed to set stop param");
54    ret = SystemSetParameter(DOREBOOT_PARAM, value);
55    BEGET_ERROR_CHECK(ret == 0, return -1, "Set parameter to trigger reboot command \" %s \" failed", value);
56    return 0;
57}
58
59static int ExecReboot(const char *mode, const char *option)
60{
61    // check if param set ok
62#ifndef STARTUP_INIT_TEST
63    const int maxCount = 10;
64#else
65    const int maxCount = 1;
66#endif
67    int count = 0;
68    DoRebootByInitPlugin(mode, option);
69    while (count < maxCount) {
70        usleep(100 * 1000); // 100 * 1000 wait 100ms
71        char result[10] = {0}; // 10 stop len
72        uint32_t len = sizeof(result);
73        int ret = SystemGetParameter(STARTUP_DEVICE_CTL, result, &len);
74        if (ret == 0 && strcmp(result, DEVICE_CMD_STOP) == 0) {
75            BEGET_LOGE("Success to reboot system");
76            return 0;
77        }
78        count++;
79        DoRebootByInitPlugin(mode, option);
80    }
81    BEGET_LOGE("Failed to reboot system");
82    return 0;
83}
84
85int DoReboot(const char *option)
86{
87    return ExecReboot(NULL, option);
88}
89
90int DoRebootExt(const char *mode, const char *option)
91{
92    return ExecReboot(mode, option);
93}