提交 924b03da 编写于 作者: Z zhong_ning

modify l2 init

Signed-off-by: Nzhong_ning <zhong_ning@hoperun.com>
上级 cde94033
......@@ -18,21 +18,32 @@ lite_component("initsync") {
}
shared_library("libinitsync_shared") {
sources = [ "src/init_sync.c" ]
sources = [
"src/init_sync.c",
]
cflags = [ "-Wall" ]
include_dirs = [
"//base/startup/init_lite/initsync/include",
"//base/startup/init_lite/interfaces/kits",
"//base/startup/init_lite/services/log",
]
public_deps = [
"//base/startup/init_lite/services/log:init_log",
"//third_party/bounds_checking_function:libsec_shared",
]
public_deps = [ "//third_party/bounds_checking_function:libsec_shared" ]
}
static_library("libinitsync_static") {
sources = [ "src/init_sync.c" ]
sources = [
"src/init_sync.c",
]
cflags = [ "-Wall" ]
include_dirs = [
"//base/startup/init_lite/initsync/include",
"//base/startup/init_lite/interfaces/kits",
"//base/startup/init_lite/services/log",
]
public_deps = [
"//third_party/bounds_checking_function:libsec_static",
]
public_deps = [ "//third_party/bounds_checking_function:libsec_static" ]
}
......@@ -24,19 +24,19 @@
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
#include "init_log.h"
static int SendCmd(int cmd, unsigned long arg)
{
int fd = open(QUICKSTART_NODE, O_RDONLY);
if (fd != -1) {
int ret = ioctl(fd, cmd, arg);
if (ret == -1) {
printf("[ERR][%s,%d] %s!\n", __FUNCTION__, __LINE__, strerror(errno));
INIT_LOGE("[Init] [ERR] %s!\n", strerror(errno));
}
close(fd);
return ret;
}
printf("[ERR][%s,%d] %s!\n", __FUNCTION__, __LINE__, strerror(errno));
INIT_LOGE("[Init] [ERR] %s!\n", strerror(errno));
return fd;
}
......@@ -56,7 +56,7 @@ int NotifyInit(unsigned long event)
int SystemInitStage(QuickstartStage stage)
{
if (stage >= QS_STAGE_LIMIT || stage < QS_STAGE1) {
printf("[ERR][%s,%d] the stage(%d) is not expected!\n", __FUNCTION__, __LINE__, stage);
INIT_LOGE("[Init] the stage(%d) is not expected!\n", stage);
return -1;
}
return SendCmd(QUICKSTART_STAGE(stage), 0);
......
/*
* 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.
*/
#ifndef INIT_REBOOT_API_H
#define INIT_REBOOT_API_H
int DoRebootApi(const char *cmdContent);
#endif
文件模式从 100755 更改为 100644
# Copyright (c) 2020 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.
import("//build/ohos.gni")
ohos_static_library("triggerservice") {
sources = [
"trigger_manager.c",
"trigger_processor.c",
"trigger_checker.c",
"//base/startup/init_lite/services/src/init_utils.c",
]
include_dirs = [
".",
"//base/startup/init_lite/services/include/property",
"//base/startup/init_lite/services/include/trigger",
"//base/startup/init_lite/services/include",
"//base/startup/init_lite/services/property/include",
"//third_party/libuv/include",
"//third_party/cJSON",
]
deps = [
"//third_party/libuv:uv_static",
"//third_party/bounds_checking_function:libsec_static",
]
part_name = "startup"
subsystem_name = "startup"
}
\ No newline at end of file
# 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.
import("//build/ohos.gni")
ohos_static_library("libreboot") {
sources = [
"//base/startup/init_lite/interfaces/innerkits/reboot/init_reboot_api.c",
]
include_dirs = [
"//base/startup/init_lite/interfaces/innerkits/include",
"//base/startup/init_lite/services/include/param",
"//third_party/bounds_checking_function/include",
"//base/startup/init_lite/services/log",
]
deps = [
"//third_party/bounds_checking_function:libsec_static",
"//base/startup/init_lite/services/param:paramclient",
"//base/startup/init_lite/services/log:init_log",
]
}
/*
* 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 "init_reboot_api.h"
#include <stdio.h>
#include <string.h>
#include "sys_param.h"
#include "securec.h"
#include "init_log.h"
#define SYS_POWER_CTRL "sys.powerctrl."
#define MAX_REBOOT_NAME_SIZE 100
#define MAX_REBOOT_VAUE_SIZE 500
int DoRebootApi(const char *cmdContent)
{
char name[MAX_REBOOT_VAUE_SIZE];
if (cmdContent == NULL) {
INIT_LOGE("DoReboot api error, cmdContent is NULL.\n");
return -1;
}
int length = strlen(cmdContent);
if (length == 0 || length > MAX_REBOOT_VAUE_SIZE) {
INIT_LOGE("DoReboot api error, cmdContent = %s, length = %d.\n", cmdContent, length);
return -1;
}
if (snprintf_s(name, MAX_REBOOT_NAME_SIZE, MAX_REBOOT_NAME_SIZE - 1, "%s%s", SYS_POWER_CTRL, "reboot") < 0) {
INIT_LOGE("DoReboot api error, MAX_REBOOT_NAME_SIZE is not enough\n");
return -1;
}
if (SystemSetParameter(name, cmdContent) != 0) {
INIT_LOGE("DoRebootApi SystemSetParameter error\n");
return -1;
}
return 0;
}
文件模式从 100755 更改为 100644
......@@ -37,10 +37,10 @@ static int GetControlFromEnv(char *path)
if (path == NULL) {
return -1;
}
printf("GetControlFromEnv path is %s \n", path);
INIT_LOGI("GetControlFromEnv path is %s \n", path);
const char *val = getenv(path);
if (val == NULL) {
printf("test GetControlFromEnv val is null %d\n", errno);
INIT_LOGE("GetControlFromEnv val is null %d\n", errno);
return -1;
}
errno = 0;
......@@ -48,9 +48,9 @@ static int GetControlFromEnv(char *path)
if (errno) {
return -1;
}
printf("test GetControlFromEnv fd is %d \n", fd);
INIT_LOGI("GetControlFromEnv fd is %d \n", fd);
if (fcntl(fd, F_GETFD) < 0) {
printf("test GetControlFromEnv errno %d \n", errno);
INIT_LOGE("GetControlFromEnv errno %d \n", errno);
return -1;
}
return fd;
......@@ -63,23 +63,23 @@ int GetControlSocket(const char *name)
}
char path[MAX_SOCKET_ENV_PREFIX_LEN] = {0};
snprintf(path, sizeof(path), OHOS_SOCKET_ENV_PREFIX"%s", name);
printf("test GetControlSocket path is %s \n", path);
INIT_LOGI("GetControlSocket path is %s \n", path);
int fd = GetControlFromEnv(path);
if (fd < 0) {
printf("GetControlFromEnv fail \n");
INIT_LOGE("GetControlFromEnv fail \n");
return -1;
}
struct sockaddr_un addr;
socklen_t addrlen = sizeof(addr);
int ret = getsockname(fd, (struct sockaddr*)&addr, &addrlen);
if (ret < 0) {
printf("test GetControlSocket errno %d \n", errno);
INIT_LOGE("GetControlSocket errno %d \n", errno);
return -1;
}
char sockDir[MAX_SOCKET_DIR_LEN] = {0};
snprintf(sockDir, sizeof(sockDir), OHOS_SOCKET_DIR"/%s", name);
printf("test sockDir %s \n", sockDir);
printf("addr.sun_path %s \n", addr.sun_path);
INIT_LOGI("sockDir %s \n", sockDir);
INIT_LOGI("addr.sun_path %s \n", addr.sun_path);
if (strncmp(sockDir, addr.sun_path, strlen(sockDir)) == 0) {
return fd;
}
......
文件模式从 100755 更改为 100644
......@@ -20,22 +20,24 @@ if (defined(ohos_lite)) {
]
sources = [
"src/init_adapter.c",
"src/init_capability.c",
"src/init_cmds.c",
"src/init_import.c",
"src/init_jobs.c",
"src/init_read_cfg.c",
"src/init_service.c",
"src/init_service_manager.c",
"src/init_import.c",
"src/init_service_socket.c",
"src/init_signal_handler.c",
"src/init_utils.c",
"src/init_service_socket.c",
"src/main.c",
"src/init_capability.c",
"src/init_reboot.c",
]
include_dirs = [
"//base/startup/init_lite/services/include",
"//base/startup/init_lite/services/property/include",
"//base/startup/init_lite/services/param/include",
"//base/startup/init_lite/services/log",
"//third_party/cJSON",
"//third_party/bounds_checking_function/include",
"//base/startup/syspara_lite/interfaces/kits",
......@@ -44,8 +46,9 @@ if (defined(ohos_lite)) {
cflags = [ "-Wall" ]
deps = [
"//base/startup/syspara_lite/frameworks/parameter:parameter",
"//base/startup/init_lite/initsync:initsync",
"//base/startup/init_lite/services/log:init_log",
"//base/startup/syspara_lite/frameworks/parameter:parameter",
"//build/lite/config/component/cJSON:cjson_shared",
"//third_party/bounds_checking_function:libsec_shared",
]
......@@ -73,8 +76,9 @@ if (defined(ohos_lite)) {
if (ohos_build_type == "debug") {
group("unittest") {
deps =
[ "//base/startup/init_lite/services/test/unittest/common:unittest" ]
deps = [
"//base/startup/init_lite/services/test/unittest/common:unittest",
]
}
}
} else {
......@@ -87,8 +91,12 @@ if (defined(ohos_lite)) {
include_dirs = [
"include",
"//third_party/bounds_checking_function/include",
"//base/startup/init_lite/services/log",
]
deps = [
"//third_party/bounds_checking_function:libsec_static",
"//base/startup/init_lite/services/log:init_log",
]
deps = [ "//third_party/bounds_checking_function:libsec_static" ]
install_enable = true
part_name = "init"
}
......@@ -97,38 +105,37 @@ if (defined(ohos_lite)) {
sources = [
"src/device.c",
"src/init_adapter.c",
"src/init_capability.c",
"src/init_cmds.c",
"src/init_import.c",
"src/init_jobs.c",
"src/init_log.c",
"src/init_read_cfg.c",
"src/init_service.c",
"src/init_service_manager.c",
"src/init_import.c",
"src/init_service_socket.c",
"src/init_signal_handler.c",
"src/init_utils.c",
"src/init_service_socket.c",
"src/main.c",
"src/init_capability.c",
"src/init_reboot.c",
]
include_dirs = [
"//base/startup/init_lite/services/include/property",
"//base/startup/init_lite/services/include/trigger",
"//base/startup/init_lite/services/include/param",
"//base/startup/init_lite/services/include",
"//base/startup/init_lite/services/property/include",
"//base/startup/init_lite/services/log",
"//third_party/cJSON",
"//third_party/bounds_checking_function/include",
"//third_party/libuv/include",
]
deps = [
"//base/startup/init_lite/services/property:propertyserver",
"//base/startup/init_lite/services/property:propertyclient",
"//base/startup/init_lite/services/trigger:triggerservice",
"//base/startup/init_lite/services/param:paramservice",
"//base/startup/init_lite/services/log:init_log",
"//third_party/bounds_checking_function:libsec_static",
"//third_party/cJSON:cjson_static",
]
if (use_musl) {
deps += [
"//third_party/mksh:sh",
"//third_party/toybox:toybox"
"//third_party/toybox:toybox",
]
}
install_enable = true
......@@ -142,14 +149,14 @@ if (defined(ohos_lite)) {
group("startup_init") {
deps = [
":init.cfg",
":init",
":init.cfg",
":updaterueventd",
"//base/startup/init_lite/services/trigger:triggerservice",
"//base/startup/init_lite/services/property:propertyserver",
"//base/startup/init_lite/services/property:propertyclient",
"//base/startup/init_lite/services/property:setparam",
"//base/startup/init_lite/services/property:getparam"
"//base/startup/init_lite/services/param:paramservice",
"//base/startup/init_lite/services/param:setparam",
"//base/startup/init_lite/services/param:getparam",
"//base/startup/init_lite/services/param:paramclient",
"//base/startup/init_lite/services/reboot:reboot",
]
}
}
文件模式从 100755 更改为 100644
文件模式从 100755 更改为 100644
文件模式从 100755 更改为 100644
文件模式从 100755 更改为 100644
文件模式从 100755 更改为 100644
/*
* Copyright (c) 2020 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.
*/
#ifndef INIT_REBOOT_H
#define INIT_REBOOT_H
void DoReboot(const char *value);
#endif
文件模式从 100755 更改为 100644
......@@ -39,6 +39,7 @@ void RegisterServices(Service* services, int servicesCnt);
void StartServiceByName(const char* serviceName);
void StopServiceByName(const char* serviceName);
void StopAllServices();
void StopAllServicesBeforeReboot();
void ReapServiceByPID(int pid);
void ParseAllServices(const cJSON* fileRoot);
void DumpAllServices();
......
文件模式从 100755 更改为 100644
文件模式从 100755 更改为 100644
文件模式从 100755 更改为 100644
......@@ -13,71 +13,120 @@
* limitations under the License.
*/
#ifndef BASE_STARTUP_PROPERTY_SERVICE_H
#define BASE_STARTUP_PROPERTY_SERVICE_H
#ifndef BASE_STARTUP_INIT_PARAM_H
#define BASE_STARTUP_INIT_PARAM_H
#include <stdio.h>
#include "property.h"
#include "cJSON.h"
#include "sys_param.h"
#ifdef __cplusplus
#if __cplusplus
extern "C" {
#endif
#endif
typedef enum {
EVENT_PROPERTY, // 参数修改事件
EVENT_BOOT
} EventType;
/**
* Init 接口
* 初始化属性服务
* 初始化参数服务
*
*/
void InitPropertyService();
void InitParamService();
/**
* 对Init接口
* 启动trigger服务。
*
*/
void StartTriggerService();
/**
* Init 接口
* 加载默认的属性值
* 启动参数服务,在main启动的最后调用,阻赛当前线程
*
*/
int LoadDefaultProperty(const char *fileName);
int StartParamService();
/**
* Init 接口
* 安全使用,加载属性的信息,包括selinux label 等
* 停止参数服务
*
*/
int LoadPropertyInfo(const char *fileName);
void StopParamService();
/**
* Init 接口
* 启动属性服务,在main启动的最后调用,阻赛当前线程
* 加载默认的参数值
*
*/
int StartPropertyService();
int LoadDefaultParams(const char *fileName);
/**
* Init 接口
* 设置属性,主要用于其他进程使用,通过管道修改属性
* 安全使用,加载参数的信息,包括selinux label 等
*
*/
int SystemWriteParameter(const char *name, const char *value);
int LoadParamInfos(const char *fileName);
/**
* Init 接口
* 查询属性
* 加载默认参数
*
*/
int SystemReadParameter(const char *name, char *value, unsigned int *len);
int LoadPersistParams();
/**
* Init 接口
* 遍历属性。
* 设置参数,主要用于其他进程使用,通过管道修改参数
*
*/
int SystemTraversalParameters(void (*traversalParameter)(PropertyHandle handle, void* cookie), void* cookie);
int SystemWriteParam(const char *name, const char *value);
/**
* Init 接口
* 加载默认属性。
* 查询参数。
*
*/
int SystemReadParam(const char *name, char *value, unsigned int *len);
/**
* 对Init接口
* 触发一个trigger操作。
*
*/
void PostTrigger(EventType type, void *content, u_int32_t contentLen);
/**
* 对Init接口
* 触发一个参数trigger操作。
*
*/
void PostParamTrigger(const char *name, const char *value);
/**
* 对Init接口
* 解析trigger文件。
*
*/
int ParseTriggerConfig(cJSON *fileRoot);
/**
* 对Init接口
* 按名字执行对应的trigger。
*
*/
void DoTriggerExec(const char *content);
/**
* 对Init接口
* 按名字执行对应的trigger。
*
*/
int LoadPersistProperties();
int SystemTraversalParam(void (*traversalParameter)(ParamHandle handle, void* cookie), void* cookie);
#ifdef __cplusplus
#if __cplusplus
......
......@@ -13,8 +13,8 @@
* limitations under the License.
*/
#ifndef BASE_STARTUP_PROPERTY_H
#define BASE_STARTUP_PROPERTY_H
#ifndef BASE_STARTUP_SYS_PARAM_H
#define BASE_STARTUP_SYS_PARAM_H
#include <pthread.h>
#include <stdio.h>
#include <sys/types.h>
......@@ -25,35 +25,35 @@ extern "C" {
#endif
#endif
#define PROPERTY_VALUE_LEN_MAX 96
typedef u_int32_t PropertyHandle;
#define PARAM_VALUE_LEN_MAX 96
typedef u_int32_t ParamHandle;
typedef struct {
u_int32_t serial;
PropertyHandle handle;
char value[PROPERTY_VALUE_LEN_MAX];
} PropertyCacheNode;
ParamHandle handle;
char value[PARAM_VALUE_LEN_MAX];
} ParamCacheNode;
typedef const char *(*PropertyEvaluatePtr)(u_int32_t cacheCount, PropertyCacheNode *node);
typedef const char *(*ParamEvaluatePtr)(u_int32_t cacheCount, ParamCacheNode *node);
typedef struct {
pthread_mutex_t lock;
u_int32_t serial;
u_int32_t cacheCount;
PropertyEvaluatePtr evaluate;
PropertyCacheNode *cacheNode;
} PropertyCache;
ParamEvaluatePtr evaluate;
ParamCacheNode *cacheNode;
} ParamCache;
/**
* 对外接口
* 设置属性,主要用于其他进程使用,通过管道修改属性
* 设置参数,主要用于其他进程使用,通过管道修改参数
*
*/
int SystemSetParameter(const char *name, const char *value);
/**
* 对外接口
* 查询属性,主要用于其他进程使用,需要给定足够的内存保存属性
* 查询参数,主要用于其他进程使用,需要给定足够的内存保存参数
* 如果 value == null,获取value的长度
* 否则value的大小认为是len
*
......@@ -61,28 +61,27 @@ int SystemSetParameter(const char *name, const char *value);
int SystemGetParameter(const char *name, char *value, unsigned int *len);
/**
* 对外接口
* 查询属性,主要用于其他进程使用,需要给定足够的内存保存属性。
* 如果 value == null,获取value的长度
* 否则value的大小认为是len
* 外部接口
* 遍历参数。
*
*/
int SystemGetParameterName(PropertyHandle handle, char *name, unsigned int len);
int SystemTraversalParameter(void (*traversalParameter)(ParamHandle handle, void* cookie), void* cookie);
/**
* 对外接口
* 遍历所有属性。
* 外部接口
* 查询参数,主要用于其他进程使用,需要给定足够的内存保存参数。
* 如果 value == null,获取value的长度
* 否则value的大小认为是len
*
*/
int SystemTraversalParameter(void (*traversalParameter)(PropertyHandle handle, void* cookie), void* cookie);
int SystemGetParameterName(ParamHandle handle, char *name, unsigned int len);
/**
* 对外接口
* 获取属性值。
* 外部接口
* 获取参数值。
*
*/
int SystemGetParameterValue(PropertyHandle handle, char *value, unsigned int *len);
int SystemGetParameterValue(ParamHandle handle, char *value, unsigned int *len);
#ifdef __cplusplus
#if __cplusplus
}
......
# 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.
if (defined(ohos_lite)) {
static_library("init_log") {
sources = [
"init_log.c",
]
public_deps = [
"//third_party/bounds_checking_function:libsec_static",
]
}
} else {
import("//build/ohos.gni")
ohos_static_library("init_log") {
sources = [
"init_log.c",
]
deps = [
"//third_party/bounds_checking_function:libsec_static",
]
part_name = "startup"
subsystem_name = "startup"
}
}
......@@ -28,9 +28,20 @@
#define MAX_LOG_SIZE 2048
#define BASE_YEAR 1900
void InitLog(int logLevel, const char *fileName, int line, const char *fmt, ...)
static InitLogLevel g_logLevel = INIT_INFO;
static const char *LOG_LEVEL_STR[] = { "DEBUG", "INFO", "WARNING", "ERROR", "FATAL" };
void SetLogLevel(InitLogLevel logLevel)
{
g_logLevel = logLevel;
}
void InitLog(const char *tag, InitLogLevel logLevel, const char *fileName, int line, const char *fmt, ...)
{
UNUSED(logLevel);
if (logLevel < g_logLevel) {
return;
}
va_list vargs;
va_start(vargs, fmt);
......@@ -42,11 +53,13 @@ void InitLog(int logLevel, const char *fileName, int line, const char *fmt, ...)
time(&logTime);
struct tm *t = gmtime(&logTime);
char logInfo[MAX_LOG_SIZE];
if (snprintf_s(logInfo, MAX_LOG_SIZE, MAX_LOG_SIZE, "%d-%d-%d %d:%d %s %d : %s", (t->tm_year + BASE_YEAR),
(t->tm_mon + 1), t->tm_mday, t->tm_hour, t->tm_min, fileName, line, tmpFmt) == -1) {
if (snprintf_s(logInfo, MAX_LOG_SIZE, MAX_LOG_SIZE, "%s %d-%d-%d %d:%d %s:%d [%s] [pid=%d] %s", tag,
(t->tm_year + BASE_YEAR), (t->tm_mon + 1), t->tm_mday, t->tm_hour, t->tm_min, fileName, line,
LOG_LEVEL_STR[logLevel], getpid(), tmpFmt) == -1) {
return;
}
printf("%s", logInfo );
#if 0
int fd = open("/dev/kmsg", O_WRONLY | O_CLOEXEC | O_APPEND );
if (fd < 1) {
printf("xxxxxxxxxxxxxxx open failed. %d\n", errno);
......@@ -54,8 +67,11 @@ void InitLog(int logLevel, const char *fileName, int line, const char *fmt, ...)
}
if (write(fd, logInfo, strlen(logInfo)) < -1) {
printf("xxxxxxxxxxxxxxx write failed.%d\n", errno);
close(fd);
return;
}
close(fd);
#endif
va_end(vargs);
}
......@@ -18,6 +18,7 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#ifdef __cplusplus
#if __cplusplus
......@@ -25,13 +26,13 @@ extern "C" {
#endif
#endif
typedef enum StatupLogLevel {
STARTUP_DEBUG = 0,
STARTUP_INFO,
STARTUP_WARN,
STARTUP_ERROR,
STARTUP_FATAL
} StatupLogLevel;
typedef enum InitLogLevel {
INIT_DEBUG = 0,
INIT_INFO,
INIT_WARN,
INIT_ERROR,
INIT_FATAL
} InitLogLevel;
#define __FILE_NAME__ (strrchr((__FILE__), '/') ? strrchr((__FILE__), '/') + 1 : (__FILE__))
......@@ -41,14 +42,17 @@ typedef enum StatupLogLevel {
#define INIT_LOGI(format, ...) printf("%s %d: "format, __FILE_NAME__, __LINE__, ##__VA_ARGS__)
#define INIT_LOGD(format, ...) printf("%s %d: "format, __FILE_NAME__, __LINE__, ##__VA_ARGS__)
#else
#define INIT_LOGE(format, ...) printf("%s %d: "format, __FILE_NAME__, __LINE__, ##__VA_ARGS__)
#define INIT_LOGW(format, ...) printf("%s %d: "format, __FILE_NAME__, __LINE__, ##__VA_ARGS__)
#define INIT_LOGI(format, ...) printf("%s %d: "format, __FILE_NAME__, __LINE__, ##__VA_ARGS__)
#define INIT_LOGD(format, ...) printf("%s %d: "format, __FILE_NAME__, __LINE__, ##__VA_ARGS__)
void InitLog(int logLevel, const char *fileName, int line, const char *fmt, ...);
void Logger(StatupLogLevel level, const char *format, ...);
#endif
#define INIT_LOGD(format, ...) InitLog("[Init]", INIT_DEBUG, (__FILE_NAME__), (__LINE__), format, ##__VA_ARGS__)
#define INIT_LOGI(format, ...) InitLog("[Init]", INIT_INFO, (__FILE_NAME__), (__LINE__), format, ##__VA_ARGS__)
#define INIT_LOGW(format, ...) InitLog("[Init]", INIT_WARN, (__FILE_NAME__), (__LINE__), format, ##__VA_ARGS__)
#define INIT_LOGE(format, ...) InitLog("[Init]", INIT_ERROR, (__FILE_NAME__), (__LINE__), format, ##__VA_ARGS__)
#define INIT_LOGF(format, ...) InitLog("[Init]", INIT_FATAL, (__FILE_NAME__), (__LINE__), format, ##__VA_ARGS__)
void InitLog(const char *tag, InitLogLevel logLevel, const char *fileName, int line, const char *fmt, ...);
void SetLogLevel(InitLogLevel logLevel);
void Logger(InitLogLevel level, const char *format, ...);
#endif
#define INIT_ERROR_CHECK(ret, statement, format, ...) \
if (!(ret)) { \
......@@ -66,21 +70,21 @@ void Logger(StatupLogLevel level, const char *format, ...);
static constexpr OHOS::HiviewDFX::HiLogLabel STARTUP_LABEL = {LOG_CORE, 0, "STARTUP"};
StatupLogLevel level_;
int JudgeLevel(const StatupLogLevel level) { return return; }
InitLogLevel level_;
int JudgeLevel(const InitLogLevel level) { return return; }
#define STARTUP_LOG(LEVEL, LABEL, Level, fmt, ...) \
Logger(__FILE_NAME__, (__LINE__), fmt, ##__VA_ARGS__); \
if (JudgeLevel(StatupLogLevel::LEVEL)) \
InitLog("[Init]", LEVEL, __FILE_NAME__, (__LINE__), fmt, ##__VA_ARGS__); \
if (JudgeLevel(InitLogLevel::LEVEL)) \
OHOS::HiviewDFX::HiLog::Level(STARTUP_LABEL, "[%{public}s(%{public}d)] " fmt, \
__FILE_NAME__, __LINE__, ##__VA_ARGS__)
#else
#define STARTUP_LOG(LEVEL, LABEL, Level, fmt, ...) \
printf("[%s][%s:%d] " fmt "\n", LABEL, __FILE_NAME__, __LINE__, ##__VA_ARGS__);
printf("[%s:%d][%s:%d] " fmt "\n", LABEL, getpid(), __FILE_NAME__, __LINE__, ##__VA_ARGS__);
#endif
#define STARTUP_LOGI(LABEL, fmt, ...) STARTUP_LOG(STARTUP_INFO, LABEL, Info, fmt, ##__VA_ARGS__)
#define STARTUP_LOGE(LABEL, fmt, ...) STARTUP_LOG(STARTUP_ERROR, LABEL, Error, fmt, ##__VA_ARGS__)
#define STARTUP_LOGI(LABEL, fmt, ...) STARTUP_LOG(INIT_INFO, LABEL, Info, fmt, ##__VA_ARGS__)
#define STARTUP_LOGE(LABEL, fmt, ...) STARTUP_LOG(INIT_ERROR, LABEL, Error, fmt, ##__VA_ARGS__)
#ifdef __cplusplus
#if __cplusplus
......
# Copyright (c) 2020 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.
import("//build/ohos.gni")
ohos_static_library("propertyserver") {
sources = [
"manager/property_manager.c",
"manager/property_trie.c",
"manager/property_cache.c",
"service/property_service.c",
"service/property_persist.c",
"//base/startup/init_lite/services/src/init_utils.c",
]
include_dirs = [
"include",
"//base/startup/init_lite/services/include/property",
"//base/startup/init_lite/services/include/trigger",
"//base/startup/init_lite/services/include",
"//third_party/libuv/include",
"//third_party/cJSON",
]
deps = [
"//third_party/libuv:uv_static",
"//base/startup/init_lite/services/trigger:triggerservice",
"//third_party/bounds_checking_function:libsec_static",
]
part_name = "init"
subsystem_name = "startup"
}
ohos_static_library("propertyclient") {
sources = [
"manager/property_manager.c",
"client/property_request.c",
"manager/property_trie.c",
"manager/property_cache.c",
"//base/startup/init_lite/services/src/init_utils.c",
]
include_dirs = [
"include",
"//base/startup/init_lite/services/include/property",
"//base/startup/init_lite/services/include/trigger",
"//base/startup/init_lite/services/include",
"//third_party/libuv/include",
"//third_party/cJSON",
]
deps = [
"//third_party/libuv:uv_static",
"//third_party/bounds_checking_function:libsec_static",
]
part_name = "init"
subsystem_name = "startup"
}
ohos_executable("getparam") {
sources = [
"cmd/property_get.c",
]
include_dirs = [
"include",
"//base/startup/init_lite/services/include/property",
"//base/startup/init_lite/services/include/trigger",
"//base/startup/init_lite/services/include",
]
deps = [
"//base/startup/init_lite/services/property:propertyclient",
"//third_party/bounds_checking_function:libsec_static",
"//third_party/cJSON:cjson_static",
]
install_enable = true
part_name = "init"
}
ohos_executable("setparam") {
sources = [
"cmd/property_set.c",
]
include_dirs = [
"include",
"//base/startup/init_lite/services/include/property",
"//base/startup/init_lite/services/include/trigger",
"//base/startup/init_lite/services/include",
]
deps = [
"//base/startup/init_lite/services/property:propertyclient",
"//third_party/bounds_checking_function:libsec_static",
"//third_party/cJSON:cjson_static",
]
install_enable = true
part_name = "init"
}
# Copyright (c) 2020 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.
import("//build/ohos.gni")
ohos_static_library("paramservice") {
sources = [
"//base/startup/init_lite/services/src/init_utils.c",
"manager/param_cache.c",
"manager/param_manager.c",
"manager/param_trie.c",
"service/param_persist.c",
"service/param_service.c",
"trigger/trigger_checker.c",
"trigger/trigger_manager.c",
"trigger/trigger_processor.c",
]
include_dirs = [
"include",
"//base/startup/init_lite/services/include/param",
"//base/startup/init_lite/services/include",
"//base/startup/init_lite/services/log",
"//third_party/libuv/include",
"//third_party/cJSON",
]
deps = [
"//third_party/bounds_checking_function:libsec_static",
"//third_party/libuv:uv_static",
]
part_name = "init"
subsystem_name = "startup"
}
ohos_static_library("paramclient") {
sources = [
"//base/startup/init_lite/services/src/init_utils.c",
"client/param_request.c",
"manager/param_cache.c",
"manager/param_manager.c",
"manager/param_trie.c",
]
include_dirs = [
"include",
"//base/startup/init_lite/services/include/param",
"//base/startup/init_lite/services/include",
"//base/startup/init_lite/services/log",
"//third_party/libuv/include",
"//third_party/cJSON",
]
deps = [
"//third_party/bounds_checking_function:libsec_static",
"//third_party/libuv:uv_static",
"//base/startup/init_lite/services/log:init_log"
]
part_name = "init"
subsystem_name = "startup"
}
ohos_executable("getparam") {
sources = [
"cmd/param_get.c",
]
include_dirs = [
"include",
"//base/startup/init_lite/services/include/param",
"//base/startup/init_lite/services/include",
"//base/startup/init_lite/services/log",
]
deps = [
"//base/startup/init_lite/services/param:paramclient",
"//third_party/bounds_checking_function:libsec_static",
"//third_party/cJSON:cjson_static",
]
install_enable = true
part_name = "init"
}
ohos_executable("setparam") {
sources = [
"cmd/param_set.c",
]
include_dirs = [
"include",
"//base/startup/init_lite/services/include/param",
"//base/startup/init_lite/services/include",
"//base/startup/init_lite/services/log",
]
deps = [
"//base/startup/init_lite/services/param:paramclient",
"//third_party/bounds_checking_function:libsec_static",
"//third_party/cJSON:cjson_static",
]
install_enable = true
part_name = "init"
}
......@@ -13,57 +13,60 @@
* limitations under the License.
*/
#include "property_request.h"
#include "param_request.h"
#include <string.h>
#include <unistd.h>
#include <time.h>
#include "property_manager.h"
#include "param_manager.h"
#include "uv.h"
#define LABEL "Client"
#define BUFFER_SIZE 200
#define PropertyEntry(ptr, type, member) (type *)((char *)(ptr) - offsetof(type, member))
#define ParamEntry(ptr, type, member) (type *)((char *)(ptr) - offsetof(type, member))
static PropertyWorkSpace g_propertyWorkSpaceReadOnly = {ATOMIC_VAR_INIT(0), {}, {}, {}};
static ParamWorkSpace g_paramWorkSpaceReadOnly = {ATOMIC_VAR_INIT(0), {}, {}, {}};
static void OnWrite(uv_write_t* req, int status)
static void OnWrite(uv_write_t *req, int status)
{
PROPERTY_LOGI("OnWrite status %d", status);
PARAM_LOGI("OnWrite status %d", status);
}
static void OnReceiveAlloc(uv_handle_t* handle, size_t suggestedSize, uv_buf_t* buf)
{
// 这里需要按实际回复大小申请内存,不需要大内存
buf->base = (char *)malloc(sizeof(ResponseMsg));
buf->len = suggestedSize;
PROPERTY_LOGI("OnReceiveAlloc handle %p %zu", handle, suggestedSize);
buf->len = sizeof(ResponseMsg);
PARAM_LOGI("OnReceiveAlloc handle %p %zu", handle, suggestedSize);
}
static void OnReceiveResponse(uv_stream_t *handle, ssize_t nread, const uv_buf_t *buf)
{
RequestNode *req = PropertyEntry(handle, RequestNode, handle);
PROPERTY_LOGI("OnReceiveResponse %p", handle);
if (nread <= 0 || buf == NULL || buf->base == NULL) {
free(buf->base);
uv_close((uv_handle_t*)handle, NULL);
uv_stop(req->loop);
RequestNode *req = ParamEntry(handle, RequestNode, handle);
PARAM_LOGI("OnReceiveResponse %p", handle);
if (nread <= 0 || buf == NULL || handle == NULL || buf->base == NULL) {
if (buf != NULL && buf->base != NULL) {
free(buf->base);
}
if (handle != NULL) {
uv_close((uv_handle_t*)handle, NULL);
uv_stop(req->loop);
}
return;
}
ResponseMsg *response = (ResponseMsg *)(buf->base);
PROPERTY_CHECK(response != NULL, return, "The response is null");
PROPERTY_LOGI("OnReceiveResponse %p cmd %d result: %d", handle, response->type, response->result);
PARAM_CHECK(response != NULL, return, "The response is null");
PARAM_LOGI("OnReceiveResponse %p cmd %d result: %d", handle, response->type, response->result);
switch (response->type) {
case SET_PROPERTY:
case SET_PARAM:
req->result = response->result;
break;
default:
PROPERTY_LOGE("not supported the command: %d", response->type);
PARAM_LOGE("not supported the command: %d", response->type);
break;
}
PROPERTY_LOGE("Close handle %p", handle);
PARAM_LOGE("Close handle %p", handle);
free(buf->base);
uv_close((uv_handle_t*)handle, NULL);
uv_stop(req->loop);
......@@ -71,28 +74,28 @@ static void OnReceiveResponse(uv_stream_t *handle, ssize_t nread, const uv_buf_t
static void OnConnection(uv_connect_t *connect, int status)
{
PROPERTY_CHECK(status >= 0, return, "Failed to conntect status %s", uv_strerror(status));
uv_write_t wr;
RequestNode *request = PropertyEntry(connect, RequestNode, connect);
PROPERTY_LOGI("Connect to server handle %p", &(request->handle));
PARAM_CHECK(status >= 0, return, "Failed to conntect status %s", uv_strerror(status));
RequestNode *request = ParamEntry(connect, RequestNode, connect);
PARAM_LOGI("Connect to server handle %p", &(request->handle));
uv_buf_t buf = uv_buf_init((char*)&request->msg, request->msg.contentSize + sizeof(request->msg));
int ret = uv_write2(&wr, (uv_stream_t*)&(request->handle), &buf, 1, (uv_stream_t*)&(request->handle), OnWrite);
PROPERTY_CHECK(ret >= 0, return, "Failed to uv_write2 porperty");
int ret = uv_write2(&request->wr, (uv_stream_t*)&(request->handle), &buf, 1, (uv_stream_t*)&(request->handle), OnWrite);
PARAM_CHECK(ret >= 0, return, "Failed to uv_write2 porperty");
// read result
ret = uv_read_start((uv_stream_t*)&(request->handle), OnReceiveAlloc, OnReceiveResponse);
PROPERTY_CHECK(ret >= 0, return, "Failed to uv_read_start response");
PARAM_CHECK(ret >= 0, return, "Failed to uv_read_start response");
}
static int StartRequest(int cmd, RequestNode *request)
{
PROPERTY_CHECK(request != NULL, return -1, "Invalid request");
PARAM_CHECK(request != NULL, return -1, "Invalid request");
request->result = -1;
request->msg.type = cmd;
request->loop = uv_loop_new();
uv_pipe_init(request->loop, &request->handle, 1);
uv_pipe_connect(&request->connect, &request->handle, PIPE_NAME, OnConnection);
uv_run(request->loop, UV_RUN_DEFAULT);
uv_loop_delete(request->loop);
int result = request->result;
free(request);
return result;
......@@ -100,57 +103,58 @@ static int StartRequest(int cmd, RequestNode *request)
int SystemSetParameter(const char *name, const char *value)
{
PROPERTY_CHECK(name != NULL && value != NULL, return -1, "Invalid param");
int ret = CheckPropertyName(name, 0);
PROPERTY_CHECK(ret == 0, return ret, "Illegal property name");
PARAM_CHECK(name != NULL && value != NULL, return -1, "Invalid param");
int ret = CheckParamName(name, 0);
PARAM_CHECK(ret == 0, return ret, "Illegal param name");
PROPERTY_LOGI("StartRequest %s", name);
PARAM_LOGI("StartRequest %s", name);
u_int32_t msgSize = sizeof(RequestMsg) + strlen(name) + strlen(value) + 2;
RequestNode *request = (RequestNode *)malloc(sizeof(RequestNode) + msgSize);
PROPERTY_CHECK(request != NULL, return -1, "Failed to malloc for connect");
PARAM_CHECK(request != NULL, return -1, "Failed to malloc for connect");
memset_s(request, sizeof(RequestNode), 0, sizeof(RequestNode));
// 带字符串结束符
int contentSize = BuildPropertyContent(request->msg.content, msgSize - sizeof(RequestMsg), name, value);
PROPERTY_CHECK(contentSize > 0, return -1, "Failed to copy porperty");
int contentSize = BuildParamContent(request->msg.content, msgSize - sizeof(RequestMsg), name, value);
PARAM_CHECK(contentSize > 0, free(request); return -1, "Failed to copy porperty");
request->msg.contentSize = contentSize;
return StartRequest(SET_PROPERTY, request);
return StartRequest(SET_PARAM, request);
}
int SystemGetParameter(const char *name, char *value, unsigned int *len)
{
PROPERTY_CHECK(name != NULL && len != NULL, return -1, "The name or value is null");
InitPropertyWorkSpace(&g_propertyWorkSpaceReadOnly, 1, NULL);
PARAM_CHECK(name != NULL && len != NULL, return -1, "The name or value is null");
InitParamWorkSpace(&g_paramWorkSpaceReadOnly, 1, NULL);
PropertyHandle handle = 0;
int ret = ReadPropertyWithCheck(&g_propertyWorkSpaceReadOnly, name, &handle);
PROPERTY_CHECK(ret == 0, return ret, "Can not get param for %s", name);
return ReadPropertyValue(&g_propertyWorkSpaceReadOnly, handle, value, len);
ParamHandle handle = 0;
int ret = ReadParamWithCheck(&g_paramWorkSpaceReadOnly, name, &handle);
PARAM_CHECK(ret == 0, return ret, "Can not get param for %s", name);
return ReadParamValue(&g_paramWorkSpaceReadOnly, handle, value, len);
}
int SystemGetParameterName(PropertyHandle handle, char *name, unsigned int len)
int SystemGetParameterName(ParamHandle handle, char *name, unsigned int len)
{
PROPERTY_CHECK(name != NULL && handle != 0, return -1, "The name is null");
InitPropertyWorkSpace(&g_propertyWorkSpaceReadOnly, 1, NULL);
return ReadPropertyName(&g_propertyWorkSpaceReadOnly, handle, name, len);
PARAM_CHECK(name != NULL && handle != 0, return -1, "The name is null");
InitParamWorkSpace(&g_paramWorkSpaceReadOnly, 1, NULL);
return ReadParamName(&g_paramWorkSpaceReadOnly, handle, name, len);
}
int SystemGetParameterValue(PropertyHandle handle, char *value, unsigned int *len)
int SystemGetParameterValue(ParamHandle handle, char *value, unsigned int *len)
{
PROPERTY_CHECK(len != NULL && handle != 0, return -1, "The value is null");
InitPropertyWorkSpace(&g_propertyWorkSpaceReadOnly, 1, NULL);
return ReadPropertyValue(&g_propertyWorkSpaceReadOnly, handle, value, len);
PARAM_CHECK(len != NULL && handle != 0, return -1, "The value is null");
InitParamWorkSpace(&g_paramWorkSpaceReadOnly, 1, NULL);
return ReadParamValue(&g_paramWorkSpaceReadOnly, handle, value, len);
}
int SystemTraversalParameter(void (*traversalParameter)(PropertyHandle handle, void* cookie), void* cookie)
int SystemTraversalParameter(void (*traversalParameter)(ParamHandle handle, void* cookie), void* cookie)
{
PROPERTY_CHECK(traversalParameter != NULL, return -1, "The param is null");
InitPropertyWorkSpace(&g_propertyWorkSpaceReadOnly, 1, NULL);
return TraversalProperty(&g_propertyWorkSpaceReadOnly, traversalParameter, cookie);
PARAM_CHECK(traversalParameter != NULL, return -1, "The param is null");
InitParamWorkSpace(&g_paramWorkSpaceReadOnly, 1, NULL);
return TraversalParam(&g_paramWorkSpaceReadOnly, traversalParameter, cookie);
}
const char *SystemDetectPropertyChange(PropertyCache *cache,
PropertyEvaluatePtr evaluate, u_int32_t count, const char *properties[][2])
const char *SystemDetectParamChange(ParamCache *cache,
ParamEvaluatePtr evaluate, u_int32_t count, const char *parameters[][2])
{
PROPERTY_CHECK(cache != NULL && evaluate != NULL && properties != NULL, return NULL, "The param is null");
return DetectPropertyChange(&g_propertyWorkSpaceReadOnly, cache, evaluate, count, properties);
PARAM_CHECK(cache != NULL && evaluate != NULL && parameters != NULL, return NULL, "The param is null");
return DetectParamChange(&g_paramWorkSpaceReadOnly, cache, evaluate, count, parameters);
}
......@@ -15,17 +15,17 @@
#include <string.h>
#include <stdio.h>
#include "property.h"
#include "sys_param.h"
#define HELP_PARAM "--help"
#define BUFFER_SIZE 256
static void ProcessParam(PropertyHandle handle, void* cookie)
static void ProcessParam(ParamHandle handle, void* cookie)
{
SystemGetParameterName(handle, (char*)cookie, BUFFER_SIZE);
u_int32_t size = BUFFER_SIZE;
SystemGetParameterValue(handle, ((char*)cookie) + BUFFER_SIZE, &size);
printf("\t%s=%s \n", (char*)cookie, ((char*)cookie) + BUFFER_SIZE);
printf("\t%s = %s \n", (char*)cookie, ((char*)cookie) + BUFFER_SIZE);
}
int main(int argc, char* argv[])
......@@ -36,19 +36,20 @@ int main(int argc, char* argv[])
return 0;
}
if (argc == 2 && strncmp(argv[1], HELP_PARAM, strlen(HELP_PARAM)) == 0) { // 显示帮助
printf("usage: getprop NAME VALUE\n");
printf("usage: getparam NAME VALUE\n");
return 0;
}
if (argc != 2) {
printf("usage: getprop NAME VALUE\n");
printf("usage: getparam NAME VALUE\n");
return 0;
}
char value[BUFFER_SIZE] = {0};
u_int32_t size = BUFFER_SIZE;
int ret = SystemGetParameter(argv[1], value, &size);
if (ret == 0) {
printf("getparm %s %s \n", argv[1], value);
printf("getparam %s %s \n", argv[1], value);
} else {
printf("getparm %s %s fail\n", argv[1], value);
printf("getparam %s %s fail\n", argv[1], value);
}
}
......@@ -16,24 +16,24 @@
#include <string.h>
#include <stdio.h>
#include "property.h"
#include "sys_param.h"
#define HELP_PARAM "--help"
int main(int argc, char* argv[])
{
if (argc == 1 || argc > 3) {
printf("setparm: Need 2 arguments (see \"setparm --help\")\n");
printf("setparam: Need 2 arguments (see \"setparam --help\")\n");
return 0;
}
if (argc == 2 && strncmp(argv[1], HELP_PARAM, strlen(HELP_PARAM)) == 0) {
printf("usage: setprop NAME VALUE\n");
printf("usage: setparam NAME VALUE\n");
return 0;
}
int ret = SystemSetParameter(argv[1], argv[2]);
if (ret == 0) {
printf("setparm %s %s success\n", argv[1], argv[2]);
printf("setparam %s %s success\n", argv[1], argv[2]);
} else {
printf("setparm %s %s fail\n", argv[1], argv[2]);
printf("setparam %s %s fail\n", argv[1], argv[2]);
}
}
......@@ -13,16 +13,15 @@
* limitations under the License.
*/
#ifndef BASE_STARTUP_PROPERTY_MANAGER_H
#define BASE_STARTUP_PROPERTY_MANAGER_H
#ifndef BASE_STARTUP_PARAM_MANAGER_H
#define BASE_STARTUP_PARAM_MANAGER_H
#include <stdio.h>
#include <string.h>
#include "init_log.h"
#include "property.h"
#include "property_trie.h"
#include "sys_param.h"
#include "param_trie.h"
#include "securec.h"
#ifdef __cplusplus
#if __cplusplus
extern "C" {
......@@ -30,31 +29,31 @@ extern "C" {
#endif
typedef enum {
PROPERTY_CODE_INVALID_PARAM = 100,
PROPERTY_CODE_INVALID_NAME,
PROPERTY_CODE_INVALID_VALUE,
PROPERTY_CODE_REACHED_MAX,
PROPERTY_CODE_PERMISSION_DENIED,
PROPERTY_CODE_READ_ONLY_PROPERTY,
PROPERTY_CODE_NOT_SUPPORT,
PROPERTY_CODE_ERROR_MAP_FILE,
PROPERTY_CODE_NOT_FOUND_PROP,
PROPERTY_CODE_NOT_INIT
} PROPERTY_CODE;
PARAM_CODE_INVALID_PARAM = 100,
PARAM_CODE_INVALID_NAME,
PARAM_CODE_INVALID_VALUE,
PARAM_CODE_REACHED_MAX,
PARAM_CODE_PERMISSION_DENIED,
PARAM_CODE_READ_ONLY_PROPERTY,
PARAM_CODE_NOT_SUPPORT,
PARAM_CODE_ERROR_MAP_FILE,
PARAM_CODE_NOT_FOUND_PROP,
PARAM_CODE_NOT_INIT
} PARAM_CODE;
#define IS_READY_ONLY(name) strncmp((name), "ro.", strlen("ro.")) == 0
#define LABEL_STRING_LEN 128
#ifdef STARTUP_LOCAL
#define PIPE_NAME "/tmp/propertyservice.sock"
#define PROPERTY_STORAGE_PATH "/media/sf_ubuntu/test/__properties__/property_storage"
#define PROPERTY_PERSIST_PATH "/media/sf_ubuntu/test/property/persist_properties.property"
#define PROPERTY_INFO_PATH "/media/sf_ubuntu/test/__properties__/property_info"
#define PIPE_NAME "/tmp/paramservice"
#define PARAM_STORAGE_PATH "/media/sf_ubuntu/test/__parameters__/param_storage"
#define PARAM_PERSIST_PATH "/media/sf_ubuntu/test/param/persist_parameters"
#define PARAM_INFO_PATH "/media/sf_ubuntu/test/__parameters__/param_info"
#else
#define PIPE_NAME "/dev/unix/socket/PropertyService"
#define PROPERTY_STORAGE_PATH "/dev/__properties__/property_storage"
#define PROPERTY_PERSIST_PATH "/data/property/persist_properties.property"
#define PROPERTY_INFO_PATH "/dev/__properties__/property_info"
#define PIPE_NAME "/dev/unix/socket/paramservice"
#define PARAM_STORAGE_PATH "/dev/__parameters__/param_storage"
#define PARAM_PERSIST_PATH "/data/param/persist_parameters"
#define PARAM_INFO_PATH "/dev/__parameters__/param_info"
#endif
#define SUBSTR_INFO_NAME 0
......@@ -65,12 +64,12 @@ typedef enum {
#define WORKSPACE_FLAGS_INIT 0x01
#define WORKSPACE_FLAGS_LOADED 0x02
#define PROPERTY_LOGI(fmt, ...) STARTUP_LOGI(LABEL, fmt, ##__VA_ARGS__)
#define PROPERTY_LOGE(fmt, ...) STARTUP_LOGE(LABEL, fmt, ##__VA_ARGS__)
#define PARAM_LOGI(fmt, ...) STARTUP_LOGI(LABEL, fmt, ##__VA_ARGS__)
#define PARAM_LOGE(fmt, ...) STARTUP_LOGE(LABEL, fmt, ##__VA_ARGS__)
#define PROPERTY_CHECK(retCode, exper, ...) \
#define PARAM_CHECK(retCode, exper, ...) \
if (!(retCode)) { \
PROPERTY_LOGE(__VA_ARGS__); \
PARAM_LOGE(__VA_ARGS__); \
exper; \
}
......@@ -90,72 +89,67 @@ typedef struct UserCred {
typedef struct {
char label[LABEL_STRING_LEN];
UserCred cred;
} PropertySecurityLabel;
} ParamSecurityLabel;
typedef struct PropertyAuditData {
typedef struct ParamAuditData {
const UserCred *cr;
const char *name;
} PropertyAuditData;
} ParamAuditData;
typedef struct {
atomic_uint_least32_t flags;
WorkSpace propertyLabelSpace;
WorkSpace propertySpace;
PropertySecurityLabel label;
} PropertyWorkSpace;
WorkSpace paramLabelSpace;
WorkSpace paramSpace;
ParamSecurityLabel label;
} ParamWorkSpace;
typedef struct {
atomic_uint_least32_t flags;
WorkSpace persistWorkSpace;
} PropertyPersistWorkSpace;
} ParamPersistWorkSpace;
typedef struct {
char value[128];
} SubStringInfo;
int InitPropertyWorkSpace(PropertyWorkSpace *workSpace, int onlyRead, const char *context);
void ClosePropertyWorkSpace(PropertyWorkSpace *workSpace);
int InitParamWorkSpace(ParamWorkSpace *workSpace, int onlyRead, const char *context);
void CloseParamWorkSpace(ParamWorkSpace *workSpace);
int ReadPropertyWithCheck(PropertyWorkSpace *workSpace, const char *name, PropertyHandle *handle);
int ReadPropertyValue(PropertyWorkSpace *workSpace, PropertyHandle handle, char *value, u_int32_t *len);
int ReadPropertyName(PropertyWorkSpace *workSpace, PropertyHandle handle, char *name, u_int32_t len);
u_int32_t ReadPropertySerial(PropertyWorkSpace *workSpace, PropertyHandle handle);
int ReadParamWithCheck(ParamWorkSpace *workSpace, const char *name, ParamHandle *handle);
int ReadParamValue(ParamWorkSpace *workSpace, ParamHandle handle, char *value, u_int32_t *len);
int ReadParamName(ParamWorkSpace *workSpace, ParamHandle handle, char *name, u_int32_t len);
u_int32_t ReadParamSerial(ParamWorkSpace *workSpace, ParamHandle handle);
int AddProperty(WorkSpace *workSpace, const char *name, const char *value);
int WriteProperty(WorkSpace *workSpace, const char *name, const char *value);
int WritePropertyWithCheck(PropertyWorkSpace *workSpace,
const PropertySecurityLabel *srcLabel, const char *name, const char *value);
int WritePropertyInfo(PropertyWorkSpace *workSpace, SubStringInfo *info, int subStrNumber);
int AddParam(WorkSpace *workSpace, const char *name, const char *value);
int WriteParam(WorkSpace *workSpace, const char *name, const char *value);
int WriteParamWithCheck(ParamWorkSpace *workSpace,
const ParamSecurityLabel *srcLabel, const char *name, const char *value);
int WriteParamInfo(ParamWorkSpace *workSpace, SubStringInfo *info, int subStrNumber);
int CheckPropertyValue(WorkSpace *workSpace, const TrieDataNode *node, const char *name, const char *value);
int CheckPropertyName(const char *name, int propInfo);
int CanReadProperty(PropertyWorkSpace *workSpace, u_int32_t labelIndex, const char *name);
int CanWriteProperty(PropertyWorkSpace *workSpace,
const PropertySecurityLabel *srcLabel, const TrieDataNode *node, const char *name, const char *value);
int CheckParamValue(WorkSpace *workSpace, const TrieDataNode *node, const char *name, const char *value);
int CheckParamName(const char *name, int paramInfo);
int CanReadParam(ParamWorkSpace *workSpace, u_int32_t labelIndex, const char *name);
int CanWriteParam(ParamWorkSpace *workSpace,
const ParamSecurityLabel *srcLabel, const TrieDataNode *node, const char *name, const char *value);
int CheckMacPerms(PropertyWorkSpace *workSpace,
const PropertySecurityLabel *srcLabel, const char *name, u_int32_t labelIndex);
int CheckControlPropertyPerms(PropertyWorkSpace *workSpace,
const PropertySecurityLabel *srcLabel, const char *name, const char *value);
int CheckMacPerms(ParamWorkSpace *workSpace,
const ParamSecurityLabel *srcLabel, const char *name, u_int32_t labelIndex);
int CheckControlParamPerms(ParamWorkSpace *workSpace,
const ParamSecurityLabel *srcLabel, const char *name, const char *value);
int GetSubStringInfo(const char *buff, u_int32_t buffLen, char delimiter, SubStringInfo *info, int subStrNumber);
int BuildPropertyContent(char *content, u_int32_t contentSize, const char *name, const char *value);
PropertyWorkSpace *GetPropertyWorkSpace();
int BuildParamContent(char *content, u_int32_t contentSize, const char *name, const char *value);
ParamWorkSpace *GetParamWorkSpace();
typedef void (*TraversalParamPtr)(PropertyHandle handle, void* context);
typedef void (*TraversalParamPtr)(ParamHandle handle, void* context);
typedef struct {
TraversalParamPtr traversalParamPtr;
void *context;
} PropertyTraversalContext;
int TraversalProperty(PropertyWorkSpace *workSpace, TraversalParamPtr walkFunc, void *cookie);
int InitPersistPropertyWorkSpace(const char *context);
int RefreshPersistProperties(PropertyWorkSpace *workSpace, const char *context);
void ClosePersistPropertyWorkSpace();
int WritePersistProperty(const char *name, const char *value);
} ParamTraversalContext;
int TraversalParam(ParamWorkSpace *workSpace, TraversalParamPtr walkFunc, void *cookie);
const char *DetectPropertyChange(PropertyWorkSpace *workSpace, PropertyCache *cache,
PropertyEvaluatePtr evaluate, u_int32_t count, const char *properties[][2]);
const char *DetectParamChange(ParamWorkSpace *workSpace, ParamCache *cache,
ParamEvaluatePtr evaluate, u_int32_t count, const char *parameters[][2]);
#ifdef __cplusplus
#if __cplusplus
......
......@@ -13,12 +13,12 @@
* limitations under the License.
*/
#ifndef BASE_STARTUP_PROPERTY_REQUEST_H
#define BASE_STARTUP_PROPERTY_REQUEST_H
#ifndef BASE_STARTUP_PARAM_REQUEST_H
#define BASE_STARTUP_PARAM_REQUEST_H
#include <stdio.h>
#include "property.h"
#include "property_manager.h"
#include "sys_param.h"
#include "param_manager.h"
#include "uv.h"
#ifdef __cplusplus
......@@ -28,12 +28,12 @@ extern "C" {
#endif
typedef enum RequestType {
SET_PROPERTY,
GET_PROPERTY,
SET_PARAM,
GET_PARAM,
} RequestType;
typedef struct {
PropertySecurityLabel securitylabel;
ParamSecurityLabel securitylabel;
RequestType type;
int contentSize;
char content[0];
......@@ -50,6 +50,7 @@ typedef struct {
uv_loop_t *loop;
uv_connect_t connect;
uv_pipe_t handle;
uv_write_t wr;
int result;
RequestMsg msg;
} RequestNode;
......
......@@ -13,31 +13,21 @@
* limitations under the License.
*/
#ifndef BASE_STARTUP_TRIGER_H
#define BASE_STARTUP_TRIGER_H
#ifndef BASE_STARTUP_PARAM_SERVICE_H
#define BASE_STARTUP_PARAM_SERVICE_H
#include <stdio.h>
#include "cJSON.h"
#include "sys_param.h"
#include "param_manager.h"
#ifdef __cplusplus
#if __cplusplus
extern "C" {
#endif
#endif
typedef enum {
EVENT_PROPERTY, // 属性修改事件
EVENT_BOOT
} EventType;
void PostTrigger(EventType type, void *content, u_int32_t contentLen);
void PostPropertyTrigger(const char *name, const char *value);
void StartTriggerService();
int ParseTriggerConfig(cJSON *fileRoot);
void DoTriggerExec(const char *content);
int InitPersistParamWorkSpace(const char *context);
int RefreshPersistParams(ParamWorkSpace *workSpace, const char *context);
void ClosePersistParamWorkSpace();
int WritePersistParam(const char *name, const char *value);
#ifdef __cplusplus
#if __cplusplus
......
......@@ -13,8 +13,8 @@
* limitations under the License.
*/
#ifndef BASE_STARTUP_PROPERTY_TRIE_H
#define BASE_STARTUP_PROPERTY_TRIE_H
#ifndef BASE_STARTUP_PARAM_TRIE_H
#define BASE_STARTUP_PARAM_TRIE_H
#include <linux/futex.h>
#include <stdatomic.h>
#include <stdio.h>
......@@ -22,7 +22,7 @@
#include <sys/syscall.h>
#include "init_log.h"
#include "property.h"
#include "sys_param.h"
#include "securec.h"
#ifdef __cplusplus
......@@ -31,8 +31,7 @@ extern "C" {
#endif
#endif
#define PROPERTY_WORKSPACE_MAX 64*1024
#define PARAM_WORKSPACE_MAX 64*1024
#define TRIE_SERIAL_DIRTY_OFFSET 1
#define TRIE_SERIAL_KEY_LEN_OFFSET 24
#define TRIE_SERIAL_DATA_LEN_OFFSET 16
......@@ -136,4 +135,4 @@ u_int32_t GetDataSerial(const DataEntry *entry);
}
#endif
#endif
#endif // BASE_STARTUP_PROPERTY_TRIE_H
\ No newline at end of file
#endif // BASE_STARTUP_PARAM_TRIE_H
\ No newline at end of file
......@@ -15,7 +15,6 @@
#ifndef STARTUP_TRIGER_MANAGER_H
#define STARTUP_TRIGER_MANAGER_H
#include <pthread.h>
#include <stdatomic.h>
#include <stdio.h>
......@@ -23,8 +22,7 @@
#include "cJSON.h"
#include "init_log.h"
#include "list.h"
#include "property_service.h"
#include "param_manager.h"
#include "securec.h"
#ifdef __cplusplus
......@@ -33,30 +31,21 @@ extern "C" {
#endif
#endif
#define TRIGGER_LOGI(fmt, ...) STARTUP_LOGI("Trigger", fmt, ##__VA_ARGS__)
#define TRIGGER_LOGE(fmt, ...) STARTUP_LOGE("Trigger", fmt, ##__VA_ARGS__)
#define TRIGGER_CHECK(retCode, exper, ...) \
if (!(retCode)) { \
TRIGGER_LOGE(__VA_ARGS__); \
exper; \
}
#define COND_STACK_SIZE 20
#define TRIGGER_CMD "trigger "
#define TRIGGER_ARR_NAME_IN_JSON "jobs"
#define CMDS_ARR_NAME_IN_JSON "cmds"
typedef struct {
char data[COND_STACK_SIZE];
int top;
} CONDITION_STACK;
#define MAX_TRIGGER_CMD_NAME_LEN 32
#define MAX_TRIGGER_NAME_LEN 64
#define MAX_TRIGGER_TYPE_LEN 16
#define TRIGGER_NODE_IN_QUEUE(trigger) \
(atomic_load_explicit(&(trigger)->serial, memory_order_relaxed) & 0x01)
#define TRIGGER_NODE_SET_QUEUE_FLAG(trigger) \
atomic_store_explicit(&(trigger)->serial, (trigger)->serial | 0x01, memory_order_relaxed)
#define TRIGGER_NODE_CLEAR_QUEUE_FLAG(trigger) \
atomic_store_explicit(&(trigger)->serial, (trigger)->serial & ~0x01, memory_order_relaxed)
/*
on boot
exec /system/bin/sleep 4
start telephony_sa
*/
typedef enum {
TRIGGER_BOOT = 0,
TRIGGER_PROPERTY,
......@@ -64,10 +53,6 @@ typedef enum {
TRIGGER_MAX
}TriggerType;
#define MAX_TRIGGER_CMD_NAME_LEN 16
#define MAX_TRIGGER_NAME_LEN 64
#define MAX_TRIGGER_TYPE_LEN 16
// Command对象列表,主要存储每个triger需要执行那些Command操作。
typedef struct CommandNode {
atomic_uint_least32_t next;
......@@ -116,27 +101,20 @@ int InitTriggerWorkSpace(TriggerWorkSpace *workSpace);
int ParseTrigger(TriggerWorkSpace *workSpace, cJSON *triggerItem);
typedef int (*TRIGGER_MATCH)(TriggerNode *trigger, void *content, u_int32_t contentSize);
typedef int (*TRIGGER_CHECK_DONE) (TriggerNode *trigger, u_int32_t index);
typedef int (*PARAM_CHECK_DONE) (TriggerNode *trigger, u_int32_t index);
typedef int (*CMD_EXECUTE) (TriggerNode *trigger, const char *cmdName, const char *command);
TriggerNode *GetTriggerByName(TriggerWorkSpace *workSpace, const char *triggerName, u_int32_t *triggerIndex);
int ExecuteTrigger(TriggerWorkSpace *workSpace, TriggerNode *trigger, CMD_EXECUTE cmdExecuter);
int CheckTrigger(TriggerWorkSpace *workSpace,
int type, void *content, u_int32_t contentSize, TRIGGER_CHECK_DONE triggerExecuter);
int CheckPropertyTrigger(TriggerWorkSpace *workSpace,
const char *content, u_int32_t contentSize, TRIGGER_CHECK_DONE triggerExecuter);
int type, void *content, u_int32_t contentSize, PARAM_CHECK_DONE triggerExecuter);
int CheckParamTrigger(TriggerWorkSpace *workSpace,
const char *content, u_int32_t contentSize, PARAM_CHECK_DONE triggerExecuter);
TriggerNode *ExecuteQueuePop(TriggerWorkSpace *workSpace);
int ExecuteQueuePush(TriggerWorkSpace *workSpace, TriggerNode *trigger, u_int32_t index);
int ExecuteQueueSize(TriggerWorkSpace *workSpace);
#define TRIGGER_NODE_IN_QUEUE(trigger) \
(atomic_load_explicit(&(trigger)->serial, memory_order_relaxed) & 0x01)
#define TRIGGER_NODE_SET_QUEUE_FLAG(trigger) \
atomic_store_explicit(&(trigger)->serial, (trigger)->serial | 0x01, memory_order_relaxed)
#define TRIGGER_NODE_CLEAR_QUEUE_FLAG(trigger) \
atomic_store_explicit(&(trigger)->serial, (trigger)->serial & ~0x01, memory_order_relaxed)
TriggerWorkSpace *GetTriggerWorkSpace();
#ifdef __cplusplus
......
......@@ -18,8 +18,8 @@
#include <stdio.h>
#include "property.h"
#include "trigger.h"
#include "sys_param.h"
#include "init_param.h"
#include "trigger_manager.h"
#include "uv.h"
......
......@@ -12,7 +12,7 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "property.h"
#include "sys_param.h"
#include <ctype.h>
#include <errno.h>
......@@ -26,94 +26,94 @@
#include <sys/types.h>
#include <unistd.h>
#include "property_manager.h"
#include "param_manager.h"
#define LABEL "Manager"
#define MAX_PROPERT_IN_WATCH 5
#define NORMAL_MEMORY_FOR_PROPERTY_CACHE 4 * 1024
#define NORMAL_MEMORY_FOR_PARAM_CACHE 4 * 1024
static WorkSpace g_workSpace;
static pthread_mutex_t cacheLock = PTHREAD_MUTEX_INITIALIZER;
static int InitNormalMemory(WorkSpace *workSpace, u_int32_t spaceSize)
{
PROPERTY_CHECK(workSpace != NULL, return -1, "Invalid param");
PARAM_CHECK(workSpace != NULL, return -1, "Invalid param");
if (workSpace->area != NULL) {
return 0;
}
void *areaAddr = (void *)mmap(NULL, spaceSize, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_POPULATE | MAP_ANON, -1, 0);
PROPERTY_CHECK(areaAddr != MAP_FAILED, return -1, "Failed to map memory error %s", strerror(errno));
PARAM_CHECK(areaAddr != MAP_FAILED, return -1, "Failed to map memory error %s", strerror(errno));
workSpace->area = (WorkArea*)areaAddr;
atomic_init(&workSpace->area->serial, 0);
workSpace->area->dataSize = spaceSize;
workSpace->area->currOffset = sizeof(WorkArea);
PROPERTY_LOGI("InitNormalMemory success, currOffset %u firstNode %u dataSize %u",
PARAM_LOGI("InitNormalMemory success, currOffset %u firstNode %u dataSize %u",
workSpace->area->currOffset, workSpace->area->firstNode, workSpace->area->dataSize);
return 0;
}
static PropertyCacheNode *AllocPropertyCacheNode(WorkSpace *workSpace, u_int32_t size)
static ParamCacheNode *AllocParamCacheNode(WorkSpace *workSpace, u_int32_t size)
{
PROPERTY_CHECK(workSpace != NULL, return 0, "Invalid param");
PROPERTY_CHECK((workSpace->area->currOffset + size) < workSpace->area->dataSize, return 0,
PARAM_CHECK(workSpace != NULL, return 0, "Invalid param");
PARAM_CHECK((workSpace->area->currOffset + size) < workSpace->area->dataSize, return 0,
"Failed to allocate currOffset %d, dataSize %d", workSpace->area->currOffset, workSpace->area->dataSize);
PropertyCacheNode *cache = (PropertyCacheNode *)(workSpace->area->data + workSpace->area->currOffset);
ParamCacheNode *cache = (ParamCacheNode *)(workSpace->area->data + workSpace->area->currOffset);
workSpace->area->currOffset += size;
return cache;
}
static int CreatePropertyCache(PropertyCache *cache, PropertyWorkSpace *workSpace, PropertyEvaluatePtr evaluate)
static int CreateParamCache(ParamCache *cache, ParamWorkSpace *workSpace, ParamEvaluatePtr evaluate)
{
PROPERTY_CHECK(cache != NULL && evaluate != NULL, return -1, "Invalid param");
PARAM_CHECK(cache != NULL && evaluate != NULL, return -1, "Invalid param");
if (cache->cacheNode != NULL) {
return 0;
}
int ret = InitNormalMemory(&g_workSpace, NORMAL_MEMORY_FOR_PROPERTY_CACHE);
PROPERTY_CHECK(ret == 0, return -1, "Failed to init normal memory");
int ret = InitNormalMemory(&g_workSpace, NORMAL_MEMORY_FOR_PARAM_CACHE);
PARAM_CHECK(ret == 0, return -1, "Failed to init normal memory");
pthread_mutex_init(&cache->lock, NULL);
cache->serial = GetWorkSpaceSerial(&workSpace->propertySpace);
cache->serial = GetWorkSpaceSerial(&workSpace->paramSpace);
cache->cacheCount = 0;
cache->evaluate = evaluate;
cache->cacheNode = (PropertyCacheNode *)AllocPropertyCacheNode(&g_workSpace,
sizeof(PropertyCache) * MAX_PROPERT_IN_WATCH);
PROPERTY_CHECK(cache->cacheNode != NULL, return -1, "Failed to malloc memory");
cache->cacheNode = (ParamCacheNode *)AllocParamCacheNode(&g_workSpace,
sizeof(ParamCache) * MAX_PROPERT_IN_WATCH);
PARAM_CHECK(cache->cacheNode != NULL, return -1, "Failed to malloc memory");
return 0;
}
static int AddPropertyNode(PropertyCache *cache, PropertyWorkSpace *workSpace, const char *name, const char *defValue)
static int AddParamNode(ParamCache *cache, ParamWorkSpace *workSpace, const char *name, const char *defValue)
{
PROPERTY_CHECK(cache != NULL && name != NULL, return -1, "Invalid param");
PROPERTY_CHECK(cache->cacheCount < MAX_PROPERT_IN_WATCH, return -1, "Full property in cache");
PARAM_CHECK(cache != NULL && name != NULL, return -1, "Invalid param");
PARAM_CHECK(cache->cacheCount < MAX_PROPERT_IN_WATCH, return -1, "Full param in cache");
PropertyCacheNode *cacheNode = &cache->cacheNode[cache->cacheCount++];
ParamCacheNode *cacheNode = &cache->cacheNode[cache->cacheCount++];
int ret = memcpy_s(cacheNode->value, sizeof(cacheNode->value), defValue, strlen(defValue));
PROPERTY_CHECK(ret == 0, return -1, "Failed to copy default value");
PARAM_CHECK(ret == 0, return -1, "Failed to copy default value");
ret = ReadPropertyWithCheck(workSpace, name, &cacheNode->handle);
PROPERTY_CHECK(ret == 0, return -1, "Failed to read property");
cacheNode->serial = ReadPropertySerial(workSpace, cacheNode->handle);
ret = ReadParamWithCheck(workSpace, name, &cacheNode->handle);
PARAM_CHECK(ret == 0, return -1, "Failed to read param");
cacheNode->serial = ReadParamSerial(workSpace, cacheNode->handle);
return ret;
}
static int CheckCacheNode(PropertyWorkSpace *workSpace, PropertyCacheNode *cacheNode)
static int CheckCacheNode(ParamWorkSpace *workSpace, ParamCacheNode *cacheNode)
{
return cacheNode && ReadPropertySerial(workSpace, cacheNode->handle) != cacheNode->serial;
return cacheNode && ReadParamSerial(workSpace, cacheNode->handle) != cacheNode->serial;
}
static void RefreshCacheNode(PropertyWorkSpace *workSpace, PropertyCacheNode *cacheNode)
static void RefreshCacheNode(ParamWorkSpace *workSpace, ParamCacheNode *cacheNode)
{
cacheNode->serial = ReadPropertySerial(workSpace, cacheNode->handle);
cacheNode->serial = ReadParamSerial(workSpace, cacheNode->handle);
u_int32_t len = sizeof(cacheNode->value);
ReadPropertyValue(workSpace, cacheNode->handle, cacheNode->value, &len);
ReadParamValue(workSpace, cacheNode->handle, cacheNode->value, &len);
}
static const char *TestPropertyCache(PropertyCache *cache, PropertyWorkSpace *workSpace)
static const char *TestParamCache(ParamCache *cache, ParamWorkSpace *workSpace)
{
int changeDetected;
int changeDetected = 0;
if (pthread_mutex_trylock(&cache->lock)) {
return cache->evaluate(cache->cacheCount, cache->cacheNode);
}
if (GetWorkSpaceSerial(&workSpace->propertySpace) != cache->serial) {
if (GetWorkSpaceSerial(&workSpace->paramSpace) != cache->serial) {
changeDetected = 1;
}
for (u_int32_t i = 0; (i < cache->cacheCount) && changeDetected == 0; i++) {
......@@ -123,26 +123,26 @@ static const char *TestPropertyCache(PropertyCache *cache, PropertyWorkSpace *wo
for (u_int32_t i = 0; i < cache->cacheCount; i++) {
RefreshCacheNode(workSpace, &cache->cacheNode[i]);
}
cache->serial = GetWorkSpaceSerial(&workSpace->propertySpace);
cache->serial = GetWorkSpaceSerial(&workSpace->paramSpace);
}
pthread_mutex_unlock(&cache->lock);
return cache->evaluate(cache->cacheCount, cache->cacheNode);
}
const char *DetectPropertyChange(PropertyWorkSpace *workSpace, PropertyCache *cache,
PropertyEvaluatePtr evaluate, u_int32_t count, const char *properties[][2])
const char *DetectParamChange(ParamWorkSpace *workSpace, ParamCache *cache,
ParamEvaluatePtr evaluate, u_int32_t count, const char *parameters[][2])
{
pthread_mutex_lock(&cacheLock);
while (cache->cacheCount == 0) {
int ret = CreatePropertyCache(cache, workSpace, evaluate);
PROPERTY_CHECK(ret == 0, break, "Failed to create cache");
int ret = CreateParamCache(cache, workSpace, evaluate);
PARAM_CHECK(ret == 0, break, "Failed to create cache");
for (u_int32_t i = 0; i < count; i++) {
ret = AddPropertyNode(cache, workSpace, properties[i][0], properties[i][1]);
PROPERTY_CHECK(ret == 0, break, "Failed to add property cache");
ret = AddParamNode(cache, workSpace, parameters[i][0], parameters[i][1]);
PARAM_CHECK(ret == 0, break, "Failed to add param cache");
}
PROPERTY_CHECK(ret == 0, break, "Failed to add property cache");
PARAM_CHECK(ret == 0, break, "Failed to add param cache");
}
pthread_mutex_unlock(&cacheLock);
return TestPropertyCache(cache, workSpace);
return TestParamCache(cache, workSpace);
}
......@@ -13,7 +13,7 @@
* limitations under the License.
*/
#include "property_manager.h"
#include "param_manager.h"
#include <ctype.h>
#include <errno.h>
......@@ -28,63 +28,61 @@
#define LABEL "Manager"
#ifdef PROPERTY_SUPPORT_SELINUX
#ifdef PARAM_SUPPORT_SELINUX
static int SelinuxAuditCallback(void *data,
__attribute__((unused))security_class_t class, char *msgBuf, size_t msgSize)
{
PropertyAuditData *auditData = (PropertyAuditData*)(data);
PROPERTY_CHECK(auditData != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PROPERTY_CHECK(auditData->name != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PROPERTY_CHECK(auditData->cr != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
snprintf(msgBuf, msgSize, "property=%s pid=%d uid=%d gid=%d",
ParamAuditData *auditData = (ParamAuditData*)(data);
PARAM_CHECK(auditData != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(auditData->name != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(auditData->cr != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
snprintf(msgBuf, msgSize, "param=%s pid=%d uid=%d gid=%d",
auditData->name, auditData->cr->pid, auditData->cr->uid, auditData->cr->gid);
return 0;
}
#endif
int InitPropertyWorkSpace(PropertyWorkSpace *workSpace, int onlyRead, const char *context)
int InitParamWorkSpace(ParamWorkSpace *workSpace, int onlyRead, const char *context)
{
u_int32_t flags = atomic_load_explicit(&workSpace->flags, memory_order_relaxed);
PROPERTY_LOGI("InitPropertyWorkSpace flags %x", flags);
if ((flags & WORKSPACE_FLAGS_INIT) == WORKSPACE_FLAGS_INIT) {
return 0;
}
#ifdef PROPERTY_SUPPORT_SELINUX
#ifdef PARAM_SUPPORT_SELINUX
union selinux_callback cb;
cb.func_audit = SelinuxAuditCallback;
selinux_set_callback(SELINUX_CB_AUDIT, cb);
#endif
#ifdef PROPERTY_SUPPORT_SELINUX
#ifdef PARAM_SUPPORT_SELINUX
if (context && fsetxattr(fd, XATTR_NAME_SELINUX, context, strlen(context) + 1, 0) != 0) {
PROPERTY_LOGI("fsetxattr context %s fail", context);
PARAM_LOGI("fsetxattr context %s fail", context);
}
#endif
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_NAME, "Invalid param");
workSpace->propertySpace.compareTrieNode = CompareTrieDataNode;
workSpace->propertySpace.allocTrieNode = AllocateTrieDataNode;
int ret = InitWorkSpace(PROPERTY_STORAGE_PATH, &workSpace->propertySpace, onlyRead);
// 保存selinux 使用的属性标签值
workSpace->propertyLabelSpace.compareTrieNode = CompareTrieNode; // 必须先设置
workSpace->propertyLabelSpace.allocTrieNode = AllocateTrieNode;
ret |= InitWorkSpace(PROPERTY_INFO_PATH, &workSpace->propertyLabelSpace, onlyRead);
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_NAME, "Invalid param");
workSpace->paramSpace.compareTrieNode = CompareTrieDataNode;
workSpace->paramSpace.allocTrieNode = AllocateTrieDataNode;
int ret = InitWorkSpace(PARAM_STORAGE_PATH, &workSpace->paramSpace, onlyRead);
workSpace->paramLabelSpace.compareTrieNode = CompareTrieNode; // 必须先设置
workSpace->paramLabelSpace.allocTrieNode = AllocateTrieNode;
ret |= InitWorkSpace(PARAM_INFO_PATH, &workSpace->paramLabelSpace, onlyRead);
atomic_store_explicit(&workSpace->flags, WORKSPACE_FLAGS_INIT, memory_order_release);
return ret;
}
void ClosePropertyWorkSpace(PropertyWorkSpace *workSpace)
void CloseParamWorkSpace(ParamWorkSpace *workSpace)
{
CloseWorkSpace(&workSpace->propertySpace);
CloseWorkSpace(&workSpace->propertyLabelSpace);
CloseWorkSpace(&workSpace->paramSpace);
CloseWorkSpace(&workSpace->paramLabelSpace);
atomic_store_explicit(&workSpace->flags, 0, memory_order_release);
}
int WritePropertyInfo(PropertyWorkSpace *workSpace, SubStringInfo *info, int subStrNumber)
int WriteParamInfo(ParamWorkSpace *workSpace, SubStringInfo *info, int subStrNumber)
{
PROPERTY_CHECK(workSpace != NULL && info != NULL && subStrNumber > SUBSTR_INFO_NAME,
return PROPERTY_CODE_INVALID_PARAM, "Failed to check param");
PARAM_CHECK(workSpace != NULL && info != NULL && subStrNumber > SUBSTR_INFO_NAME,
return PARAM_CODE_INVALID_PARAM, "Failed to check param");
const char *name = info[SUBSTR_INFO_NAME].value;
char *label = NULL;
char *type = NULL;
......@@ -99,81 +97,78 @@ int WritePropertyInfo(PropertyWorkSpace *workSpace, SubStringInfo *info, int sub
type = "string";
}
int ret = CheckPropertyName(name, 1);
PROPERTY_CHECK(ret == 0, return ret, "Illegal property name %s", name);
int ret = CheckParamName(name, 1);
PARAM_CHECK(ret == 0, return ret, "Illegal param name %s", name);
// 先保存标签值
TrieNode *node = AddTrieNode(&workSpace->propertyLabelSpace,
workSpace->propertyLabelSpace.rootNode, label, strlen(label));
PROPERTY_CHECK(node != NULL, return PROPERTY_CODE_REACHED_MAX, "Failed to add label");
u_int32_t offset = GetTrieNodeOffset(&workSpace->propertyLabelSpace, node);
TrieDataNode *dataNode = AddTrieDataNode(&workSpace->propertySpace, name, strlen(name));
PROPERTY_CHECK(dataNode != NULL, return PROPERTY_CODE_REACHED_MAX, "Failed to add node %s", name);
TrieNode *entry = (TrieNode *)GetTrieNode(&workSpace->propertyLabelSpace, &dataNode->labelIndex);
TrieNode *node = AddTrieNode(&workSpace->paramLabelSpace,
workSpace->paramLabelSpace.rootNode, label, strlen(label));
PARAM_CHECK(node != NULL, return PARAM_CODE_REACHED_MAX, "Failed to add label");
u_int32_t offset = GetTrieNodeOffset(&workSpace->paramLabelSpace, node);
TrieDataNode *dataNode = AddTrieDataNode(&workSpace->paramSpace, name, strlen(name));
PARAM_CHECK(dataNode != NULL, return PARAM_CODE_REACHED_MAX, "Failed to add node %s", name);
TrieNode *entry = (TrieNode *)GetTrieNode(&workSpace->paramLabelSpace, &dataNode->labelIndex);
if (entry != 0) { // 已经存在label
PROPERTY_LOGE("Has been set label %s old label %s new label: %s", name, entry->key, label);
PARAM_LOGE("Has been set label %s old label %s new label: %s", name, entry->key, label);
}
SaveIndex(&dataNode->labelIndex, offset);
return 0;
}
int AddProperty(WorkSpace *workSpace, const char *name, const char *value)
int AddParam(WorkSpace *workSpace, const char *name, const char *value)
{
PROPERTY_CHECK(workSpace != NULL && name != NULL && value != NULL,
return PROPERTY_CODE_INVALID_PARAM, "Failed to check param");
PARAM_CHECK(workSpace != NULL && name != NULL && value != NULL,
return PARAM_CODE_INVALID_PARAM, "Failed to check param");
TrieDataNode *node = AddTrieDataNode(workSpace, name, strlen(name));
PROPERTY_CHECK(node != NULL, return PROPERTY_CODE_REACHED_MAX, "Failed to add node");
PARAM_CHECK(node != NULL, return PARAM_CODE_REACHED_MAX, "Failed to add node");
DataEntry *entry = (DataEntry *)GetTrieNode(workSpace, &node->dataIndex);
//PARAM_LOGI("AddParam entry %p", entry);
if (entry == NULL) {
u_int32_t offset = AddData(workSpace, name, strlen(name), value, strlen(value));
PROPERTY_CHECK(offset != 0, return PROPERTY_CODE_REACHED_MAX, "Failed to allocate name %s", name);
PARAM_CHECK(offset > 0, return PARAM_CODE_REACHED_MAX, "Failed to allocate name %s", name);
SaveIndex(&node->dataIndex, offset);
//PARAM_LOGI("AddParam entry %p %u", entry, offset);
}
PROPERTY_LOGI("AddProperty trie %p dataIndex %u name %s", node, node->dataIndex, name);
atomic_store_explicit(&workSpace->area->serial,
atomic_load_explicit(&workSpace->area->serial, memory_order_relaxed) + 1,
memory_order_release);
atomic_load_explicit(&workSpace->area->serial, memory_order_relaxed) + 1, memory_order_release);
futex_wake(&workSpace->area->serial, INT_MAX);
return 0;
}
int UpdateProperty(WorkSpace *workSpace, u_int32_t *dataIndex, const char *name, const char *value)
int UpdateParam(WorkSpace *workSpace, u_int32_t *dataIndex, const char *name, const char *value)
{
PROPERTY_CHECK(workSpace != NULL && name != NULL && value != NULL,
return PROPERTY_CODE_INVALID_PARAM, "Failed to check param");
PARAM_CHECK(workSpace != NULL && name != NULL && value != NULL,
return PARAM_CODE_INVALID_PARAM, "Failed to check param");
DataEntry *entry = (DataEntry *)GetTrieNode(workSpace, dataIndex);
if (entry == NULL) {
PROPERTY_LOGE("Failed to update property value %s %u", name, *dataIndex);
return -1;
}
PARAM_CHECK(entry != NULL, return PARAM_CODE_REACHED_MAX,
"Failed to update param value %s %u", name, *dataIndex);
u_int32_t keyLen = DATA_ENTRY_KEY_LEN(entry);
PROPERTY_CHECK(keyLen == strlen(name), return PROPERTY_CODE_INVALID_NAME, "Failed to check name len %s", name);
PARAM_CHECK(keyLen == strlen(name), return PARAM_CODE_INVALID_NAME, "Failed to check name len %s", name);
u_int32_t serial = atomic_load_explicit(&entry->serial, memory_order_relaxed);
serial |= 1;
atomic_store_explicit(&entry->serial, serial | 1, memory_order_release);
atomic_thread_fence(memory_order_release);
int ret = UpdateDataValue(entry, value);
if (ret != 0) {
PROPERTY_LOGE("Failed to update property value %s %s", name, value);
PARAM_LOGE("Failed to update param value %s %s", name, value);
}
//PARAM_LOGI("UpdateParam entry %p", entry);
atomic_store_explicit(&entry->serial, serial + 1, memory_order_release);
futex_wake(&entry->serial, INT_MAX);
atomic_store_explicit(&workSpace->area->serial,
atomic_load_explicit(&workSpace->area->serial, memory_order_relaxed) + 1, memory_order_release);
futex_wake(&workSpace->area->serial, INT_MAX);
return ret;
}
DataEntry *FindProperty(WorkSpace *workSpace, const char *name)
DataEntry *FindParam(WorkSpace *workSpace, const char *name)
{
PROPERTY_CHECK(workSpace != NULL, return NULL, "Failed to check param");
PROPERTY_CHECK(name != NULL, return NULL, "Invalid param size");
PARAM_CHECK(workSpace != NULL, return NULL, "Failed to check param");
PARAM_CHECK(name != NULL, return NULL, "Invalid param size");
TrieDataNode *node = FindTrieDataNode(workSpace, name, strlen(name), 0);
if (node != NULL) {
......@@ -182,76 +177,73 @@ DataEntry *FindProperty(WorkSpace *workSpace, const char *name)
return NULL;
}
int WritePropertyWithCheck(PropertyWorkSpace *workSpace,
const PropertySecurityLabel *srcLabel, const char *name, const char *value)
int WriteParamWithCheck(ParamWorkSpace *workSpace,
const ParamSecurityLabel *srcLabel, const char *name, const char *value)
{
PROPERTY_CHECK(workSpace != NULL && srcLabel != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PROPERTY_CHECK(value != NULL && name != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(workSpace != NULL && srcLabel != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(value != NULL && name != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
u_int32_t flags = atomic_load_explicit(&workSpace->flags, memory_order_relaxed);
if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) {
return PROPERTY_CODE_NOT_INIT;
return PARAM_CODE_NOT_INIT;
}
int ret = CheckPropertyName(name, 0);
PROPERTY_CHECK(ret == 0, return ret, "Illegal property name %s", name);
// 取最长匹配的属性的label
TrieDataNode *propertInfo = FindTrieDataNode(&workSpace->propertySpace, name, strlen(name), 1);
ret = CanWriteProperty(workSpace, srcLabel, propertInfo, name, value);
PROPERTY_CHECK(ret == 0, return ret, "Permission to write property %s", name);
return WriteProperty(&workSpace->propertySpace, name, value);
int ret = CheckParamName(name, 0);
PARAM_CHECK(ret == 0, return ret, "Illegal param name %s", name);
TrieDataNode *info = FindTrieDataNode(&workSpace->paramSpace, name, strlen(name), 1);
ret = CanWriteParam(workSpace, srcLabel, info, name, value);
//PARAM_LOGI("WriteParamWithCheck info %p", info);
PARAM_CHECK(ret == 0, return ret, "Permission to write param %s", name);
return WriteParam(&workSpace->paramSpace, name, value);
}
int WriteProperty(WorkSpace *workSpace, const char *name, const char *value)
int WriteParam(WorkSpace *workSpace, const char *name, const char *value)
{
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PROPERTY_CHECK(value != NULL && name != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(value != NULL && name != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
TrieDataNode *node = FindTrieDataNode(workSpace, name, strlen(name), 0);
int ret = CheckPropertyValue(workSpace, node, name, value);
PROPERTY_CHECK(ret == 0, return ret, "Invalid value %s %s", name, value);
if (node != NULL) {
return UpdateProperty(workSpace, &node->dataIndex, name, value);
int ret = CheckParamValue(workSpace, node, name, value);
PARAM_CHECK(ret == 0, return ret, "Invalid value %s %s", name, value);
//PARAM_LOGI("WriteParamWithCheck node %p", node);
if (node != NULL && node->dataIndex != 0) {
return UpdateParam(workSpace, &node->dataIndex, name, value);
}
return AddProperty(workSpace, name, value);
return AddParam(workSpace, name, value);
}
int ReadPropertyWithCheck(PropertyWorkSpace *workSpace, const char *name, PropertyHandle *handle)
int ReadParamWithCheck(ParamWorkSpace *workSpace, const char *name, ParamHandle *handle)
{
PROPERTY_CHECK(handle != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PROPERTY_CHECK(workSpace != NULL && name != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(handle != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(workSpace != NULL && name != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
u_int32_t flags = atomic_load_explicit(&workSpace->flags, memory_order_relaxed);
if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) {
return PROPERTY_CODE_NOT_INIT;
return PARAM_CODE_NOT_INIT;
}
*handle = 0;
// 取最长匹配
TrieDataNode *propertyInfo = FindTrieDataNode(&workSpace->propertySpace, name, strlen(name), 1);
int ret = CanReadProperty(workSpace, propertyInfo == NULL ? 0 : propertyInfo->labelIndex, name);
PROPERTY_CHECK(ret == 0, return ret, "Permission to read property %s", name);
TrieDataNode *paramInfo = FindTrieDataNode(&workSpace->paramSpace, name, strlen(name), 1);
int ret = CanReadParam(workSpace, paramInfo == NULL ? 0 : paramInfo->labelIndex, name);
PARAM_CHECK(ret == 0, return ret, "Permission to read param %s", name);
// 查找结点
TrieDataNode *node = FindTrieDataNode(&workSpace->propertySpace, name, strlen(name), 0);
TrieDataNode *node = FindTrieDataNode(&workSpace->paramSpace, name, strlen(name), 0);
if (node != NULL && node->dataIndex != 0) {
PROPERTY_LOGI("ReadPropertyWithCheck trie %p dataIndex %u name %s", node, node->dataIndex, name);
//PARAM_LOGI("ReadParamWithCheck trie %p dataIndex %u name %s", node, node->dataIndex, name);
*handle = node->dataIndex;
return 0;
}
return PROPERTY_CODE_NOT_FOUND_PROP;
return PARAM_CODE_NOT_FOUND_PROP;
}
int ReadPropertyValue(PropertyWorkSpace *workSpace, PropertyHandle handle, char *value, u_int32_t *len)
int ReadParamValue(ParamWorkSpace *workSpace, ParamHandle handle, char *value, u_int32_t *len)
{
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
u_int32_t flags = atomic_load_explicit(&workSpace->flags, memory_order_relaxed);
if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) {
return PROPERTY_CODE_NOT_INIT;
return PARAM_CODE_NOT_INIT;
}
DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->propertySpace, &handle);
DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->paramSpace, &handle);
if (entry == NULL) {
return -1;
}
......@@ -264,7 +256,7 @@ int ReadPropertyValue(PropertyWorkSpace *workSpace, PropertyHandle handle, char
while (1) {
u_int32_t serial = GetDataSerial(entry);
int ret = GetDataValue(entry, value, *len);
PROPERTY_CHECK(ret == 0, return ret, "Failed to get value");
PARAM_CHECK(ret == 0, return ret, "Failed to get value");
atomic_thread_fence(memory_order_acquire);
if (serial == atomic_load_explicit(&(entry->serial), memory_order_relaxed)) {
return 0;
......@@ -273,31 +265,31 @@ int ReadPropertyValue(PropertyWorkSpace *workSpace, PropertyHandle handle, char
return 0;
}
int ReadPropertyName(PropertyWorkSpace *workSpace, PropertyHandle handle, char *name, u_int32_t len)
int ReadParamName(ParamWorkSpace *workSpace, ParamHandle handle, char *name, u_int32_t len)
{
PROPERTY_CHECK(workSpace != NULL && name != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->propertySpace, &handle);
PARAM_CHECK(workSpace != NULL && name != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->paramSpace, &handle);
if (entry == NULL) {
return -1;
}
return GetDataValue(entry, name, len);
return GetDataName(entry, name, len);
}
u_int32_t ReadPropertySerial(PropertyWorkSpace *workSpace, PropertyHandle handle)
u_int32_t ReadParamSerial(ParamWorkSpace *workSpace, ParamHandle handle)
{
PROPERTY_CHECK(workSpace != NULL, return 0, "Invalid param");
DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->propertySpace, &handle);
PARAM_CHECK(workSpace != NULL, return 0, "Invalid param");
DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->paramSpace, &handle);
if (entry == NULL) {
return 0;
}
return GetDataSerial(entry);
}
int CheckControlPropertyPerms(PropertyWorkSpace *workSpace,
const PropertySecurityLabel *srcLabel, const char *name, const char *value)
int CheckControlParamPerms(ParamWorkSpace *workSpace,
const ParamSecurityLabel *srcLabel, const char *name, const char *value)
{
PROPERTY_CHECK(srcLabel != NULL && name != NULL && value != NULL,
return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(srcLabel != NULL && name != NULL && value != NULL,
return PARAM_CODE_INVALID_PARAM, "Invalid param");
char * ctrlName[] = {
"ctl.start", "ctl.stop", "ctl.restart"
......@@ -306,21 +298,21 @@ int CheckControlPropertyPerms(PropertyWorkSpace *workSpace,
size_t size2 = strlen(name) + strlen(value) + 1;
size_t size = ((size1 > size2) ? size1 : size2) + 1;
char *legacyName = (char*)malloc(size);
PROPERTY_CHECK(legacyName != NULL, return PROPERTY_CODE_INVALID_PARAM, "Failed to alloc memory");
PARAM_CHECK(legacyName != NULL, return PARAM_CODE_INVALID_PARAM, "Failed to alloc memory");
// We check the legacy method first but these properties are dontaudit, so we only log an audit
// if the newer method fails as well. We only do this with the legacy ctl. properties.
// We check the legacy method first but these parameters are dontaudit, so we only log an audit
// if the newer method fails as well. We only do this with the legacy ctl. parameters.
for (size_t i = 0; i < sizeof(ctrlName) / sizeof(char*); i++) {
if (strcmp(name, ctrlName[i]) == 0) {
// The legacy permissions model is that ctl. properties have their name ctl.<action> and
// The legacy permissions model is that ctl. parameters have their name ctl.<action> and
// their value is the name of the service to apply that action to. Permissions for these
// actions are based on the service, so we must create a fake name of ctl.<service> to
// check permissions.
int n = snprintf_s(legacyName, size, size, "ctl.%s", value);
PROPERTY_CHECK(n > 0, free(legacyName); return PROPERTY_CODE_INVALID_PARAM, "Failed to snprintf value");
PARAM_CHECK(n > 0, free(legacyName); return PARAM_CODE_INVALID_PARAM, "Failed to snprintf value");
legacyName[n] = '\0';
TrieDataNode *node = FindTrieDataNode(&workSpace->propertySpace, legacyName, strlen(legacyName), 1);
TrieDataNode *node = FindTrieDataNode(&workSpace->paramSpace, legacyName, strlen(legacyName), 1);
int ret = CheckMacPerms(workSpace, srcLabel, legacyName, node == NULL ? 0 : node->labelIndex);
if (ret == 0) {
free(legacyName);
......@@ -330,32 +322,32 @@ int CheckControlPropertyPerms(PropertyWorkSpace *workSpace,
}
}
int n = snprintf_s(legacyName, size, size, "%s$%s", name, value);
PROPERTY_CHECK(n > 0, free(legacyName); return PROPERTY_CODE_INVALID_PARAM, "Failed to snprintf value");
PARAM_CHECK(n > 0, free(legacyName); return PARAM_CODE_INVALID_PARAM, "Failed to snprintf value");
TrieDataNode *node = FindTrieDataNode(&workSpace->propertySpace, name, strlen(name), 1);
TrieDataNode *node = FindTrieDataNode(&workSpace->paramSpace, name, strlen(name), 1);
int ret = CheckMacPerms(workSpace, srcLabel, name, node == NULL ? 0 : node->labelIndex);
free(legacyName);
return ret;
}
int CheckPropertyName(const char *name, int propInfo)
int CheckParamName(const char *name, int info)
{
size_t nameLen = strlen(name);
if (nameLen >= PROPERTY_VALUE_LEN_MAX) {
return PROPERTY_CODE_INVALID_NAME;
if (nameLen >= PARAM_VALUE_LEN_MAX) {
return PARAM_CODE_INVALID_NAME;
}
if (nameLen < 1 || name[0] == '.' || (!propInfo && name[nameLen - 1] == '.')) {
PROPERTY_LOGE("CheckPropertyName %s %d", name, propInfo);
return PROPERTY_CODE_INVALID_NAME;
if (nameLen < 1 || name[0] == '.' || (!info && name[nameLen - 1] == '.')) {
PARAM_LOGE("CheckParamName %s %d", name, info);
return PARAM_CODE_INVALID_NAME;
}
/* Only allow alphanumeric, plus '.', '-', '@', ':', or '_' */
/* Don't allow ".." to appear in a property name */
/* Don't allow ".." to appear in a param name */
for (size_t i = 0; i < nameLen; i++) {
if (name[i] == '.') {
if (name[i - 1] == '.') {
return PROPERTY_CODE_INVALID_NAME;
return PARAM_CODE_INVALID_NAME;
}
continue;
}
......@@ -365,80 +357,80 @@ int CheckPropertyName(const char *name, int propInfo)
if (isalnum(name[i])) {
continue;
}
return PROPERTY_CODE_INVALID_NAME;
return PARAM_CODE_INVALID_NAME;
}
return 0;
}
int CheckPropertyValue(WorkSpace *workSpace, const TrieDataNode *node, const char *name, const char *value)
int CheckParamValue(WorkSpace *workSpace, const TrieDataNode *node, const char *name, const char *value)
{
if (IS_READY_ONLY(name)) {
if (node != NULL && node->dataIndex != 0) {
PROPERTY_LOGE("Read-only property was already set %s", name);
return PROPERTY_CODE_READ_ONLY_PROPERTY;
PARAM_LOGE("Read-only param was already set %s", name);
return PARAM_CODE_READ_ONLY_PROPERTY;
}
} else {
// 限制非read only的属性,防止属性值修改后,原空间不能保存
PROPERTY_CHECK(strlen(value) < PROPERTY_VALUE_LEN_MAX,
return PROPERTY_CODE_INVALID_VALUE, "Illegal property value");
// 限制非read only的参数,防止参数值修改后,原空间不能保存
PARAM_CHECK(strlen(value) < PARAM_VALUE_LEN_MAX,
return PARAM_CODE_INVALID_VALUE, "Illegal param value");
}
return 0;
}
int CheckMacPerms(PropertyWorkSpace *workSpace,
const PropertySecurityLabel *srcLabel, const char *name, u_int32_t labelIndex)
int CheckMacPerms(ParamWorkSpace *workSpace,
const ParamSecurityLabel *srcLabel, const char *name, u_int32_t labelIndex)
{
#ifdef PROPERTY_SUPPORT_SELINUX
PropertyAuditData auditData;
#ifdef PARAM_SUPPORT_SELINUX
ParamAuditData auditData;
auditData.name = name;
auditData.cr = &srcLabel->cred;
int ret = 0;
TrieNode *node = (TrieNode *)GetTrieNode(&workSpace->propertyLabelSpace, &labelIndex);
TrieNode *node = (TrieNode *)GetTrieNode(&workSpace->paramLabelSpace, &labelIndex);
if (node != 0) { // 已经存在label
ret = selinux_check_access(srcLabel, node->key, "property_service", "set", &auditData);
ret = selinux_check_access(srcLabel, node->key, "param_service", "set", &auditData);
} else {
ret = selinux_check_access(srcLabel, "u:object_r:default_prop:s0", "property_service", "set", &auditData);
ret = selinux_check_access(srcLabel, "u:object_r:default_prop:s0", "param_service", "set", &auditData);
}
return ret == 0 ? 0 : PROPERTY_CODE_PERMISSION_DENIED;
return ret == 0 ? 0 : PARAM_CODE_PERMISSION_DENIED;
#else
return 0;
#endif
}
int CanWriteProperty(PropertyWorkSpace *workSpace,
const PropertySecurityLabel *srcLabel, const TrieDataNode *node, const char *name, const char *value)
int CanWriteParam(ParamWorkSpace *workSpace,
const ParamSecurityLabel *srcLabel, const TrieDataNode *node, const char *name, const char *value)
{
PROPERTY_CHECK(workSpace != NULL && name != NULL && value != NULL && srcLabel != NULL,
return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(workSpace != NULL && name != NULL && value != NULL && srcLabel != NULL,
return PARAM_CODE_INVALID_PARAM, "Invalid param");
if (strncmp(name, "ctl.", strlen("ctl.")) == 0) { // 处理ctrl TODO
return CheckControlPropertyPerms(workSpace, srcLabel, name, value);
return CheckControlParamPerms(workSpace, srcLabel, name, value);
}
int ret = CheckMacPerms(workSpace, srcLabel, name, node == NULL ? 0 : node->labelIndex);
PROPERTY_CHECK(ret == 0, return ret, "SELinux permission check failed");
PARAM_CHECK(ret == 0, return ret, "SELinux permission check failed");
return 0;
}
int CanReadProperty(PropertyWorkSpace *workSpace, u_int32_t labelIndex, const char *name)
int CanReadParam(ParamWorkSpace *workSpace, u_int32_t labelIndex, const char *name)
{
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PROPERTY_CHECK(name != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
#ifdef PROPERTY_SUPPORT_SELINUX
PropertyAuditData auditData;
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(name != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
#ifdef PARAM_SUPPORT_SELINUX
ParamAuditData auditData;
auditData.name = name;
UserCred cr = {.pid = 0, .uid = 0, .gid = 0};
auditData.cr = &cr;
int ret = 0;
TrieNode *node = (TrieNode *)GetTrieNode(&workSpace->propertyLabelSpace, &labelIndex);
TrieNode *node = (TrieNode *)GetTrieNode(&workSpace->paramLabelSpace, &labelIndex);
if (node != 0) { // 已经存在label
ret = selinux_check_access(&workSpace->context, node->key, "property_service", "read", &auditData);
ret = selinux_check_access(&workSpace->context, node->key, "param_service", "read", &auditData);
} else {
ret = selinux_check_access(&workSpace->context, "selinux_check_access", "file", "read", &auditData);
}
return ret == 0 ? 0 : PROPERTY_CODE_PERMISSION_DENIED;
return ret == 0 ? 0 : PARAM_CODE_PERMISSION_DENIED;
#else
return 0;
#endif
......@@ -458,6 +450,7 @@ int GetSubStringInfo(const char *buff, u_int32_t buffLen, char delimiter, SubStr
return -1;
}
// 分割字符串
int spaceIsValid = 0;
int curr = 0;
int valueCurr = 0;
for (; i < buffLen; i++) {
......@@ -468,9 +461,11 @@ int GetSubStringInfo(const char *buff, u_int32_t buffLen, char delimiter, SubStr
info[curr].value[valueCurr] = '\0';
valueCurr = 0;
curr++;
} else if (isspace(buff[i])) { // 无效字符,进行过滤
continue;
spaceIsValid = 1;
} else {
if (!spaceIsValid && isspace(buff[i])) {
continue;
}
if ((valueCurr + 1) >= (int)sizeof(info[curr].value)) {
continue;
}
......@@ -488,12 +483,12 @@ int GetSubStringInfo(const char *buff, u_int32_t buffLen, char delimiter, SubStr
return curr;
}
int BuildPropertyContent(char *content, u_int32_t contentSize, const char *name, const char *value)
int BuildParamContent(char *content, u_int32_t contentSize, const char *name, const char *value)
{
PROPERTY_CHECK(name != NULL && value != NULL && content != NULL, return -1, "Invalid param");
PARAM_CHECK(name != NULL && value != NULL && content != NULL, return -1, "Invalid param");
u_int32_t nameLen = (u_int32_t)strlen(name);
u_int32_t valueLen = (u_int32_t)strlen(value);
PROPERTY_CHECK(contentSize >= (nameLen + valueLen + 2), return -1, "Invalid content size %u", contentSize);
PARAM_CHECK(contentSize >= (nameLen + valueLen + 2), return -1, "Invalid content size %u", contentSize);
int offset = 0;
int ret = memcpy_s(content + offset, contentSize - offset, name, nameLen);
......@@ -503,14 +498,14 @@ int BuildPropertyContent(char *content, u_int32_t contentSize, const char *name,
ret |= memcpy_s(content + offset, contentSize - offset, value, valueLen);
offset += valueLen;
content[offset] = '\0';
PROPERTY_CHECK(ret == 0, return -1, "Failed to copy porperty");
PARAM_CHECK(ret == 0, return -1, "Failed to copy porperty");
offset += 1;
return offset;
}
int ProcessPropertTraversal(WorkSpace *workSpace, TrieNode *node, void *cookie)
int ProcessParamTraversal(WorkSpace *workSpace, TrieNode *node, void *cookie)
{
PropertyTraversalContext *context = (PropertyTraversalContext *)cookie;
ParamTraversalContext *context = (ParamTraversalContext *)cookie;
TrieDataNode *current = (TrieDataNode *)node;
if (current == NULL) {
return 0;
......@@ -522,11 +517,11 @@ int ProcessPropertTraversal(WorkSpace *workSpace, TrieNode *node, void *cookie)
return 0;
}
int TraversalProperty(PropertyWorkSpace *workSpace, TraversalParamPtr walkFunc, void *cookie)
int TraversalParam(ParamWorkSpace *workSpace, TraversalParamPtr walkFunc, void *cookie)
{
PropertyTraversalContext context = {
ParamTraversalContext context = {
walkFunc, cookie
};
return TraversalTrieDataNode(&workSpace->propertySpace,
(TrieDataNode *)workSpace->propertySpace.rootNode, ProcessPropertTraversal, &context);
return TraversalTrieDataNode(&workSpace->paramSpace,
(TrieDataNode *)workSpace->paramSpace.rootNode, ProcessParamTraversal, &context);
}
\ No newline at end of file
......@@ -13,7 +13,7 @@
* limitations under the License.
*/
#include "property_trie.h"
#include "param_trie.h"
#include <ctype.h>
#include <errno.h>
......@@ -28,21 +28,21 @@
#include <unistd.h>
#include "init_utils.h"
#include "property.h"
#include "property_manager.h"
#include "sys_param.h"
#include "param_manager.h"
#define LABEL "Manager"
int InitWorkSpace(const char *fileName, WorkSpace *workSpace, int onlyRead)
{
PROPERTY_CHECK(fileName != NULL, return PROPERTY_CODE_INVALID_NAME, "Invalid param");
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_NAME, "Invalid param");
PARAM_CHECK(fileName != NULL, return PARAM_CODE_INVALID_NAME, "Invalid param");
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_NAME, "Invalid param");
if (workSpace->area != NULL) {
return 0;
}
int ret = memcpy_s(workSpace->fileName, FILENAME_LEN_MAX, fileName, strlen(fileName));
PROPERTY_CHECK(ret == 0, return PROPERTY_CODE_INVALID_NAME, "Copy file %s fail ", fileName);
PARAM_CHECK(ret == 0, return PARAM_CODE_INVALID_NAME, "Copy file %s fail ", fileName);
int openMode = 0;
int prot = PROT_READ;
if (onlyRead) {
......@@ -51,50 +51,50 @@ int InitWorkSpace(const char *fileName, WorkSpace *workSpace, int onlyRead)
openMode = O_CREAT | O_RDWR | O_TRUNC;
prot = PROT_READ | PROT_WRITE;
}
ret = InitWorkSpace_(workSpace, openMode, prot, PROPERTY_WORKSPACE_MAX, onlyRead);
PROPERTY_CHECK(ret == 0, return ret, "Failed to init workspace %s", workSpace->fileName);
ret = InitWorkSpace_(workSpace, openMode, prot, PARAM_WORKSPACE_MAX, onlyRead);
PARAM_CHECK(ret == 0, return ret, "Failed to init workspace %s", workSpace->fileName);
return ret;
}
int InitPersistWorkSpace(const char *fileName, WorkSpace *workSpace)
{
PROPERTY_CHECK(fileName != NULL, return PROPERTY_CODE_INVALID_NAME, "Invalid param");
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_NAME, "Invalid param");
PARAM_CHECK(fileName != NULL, return PARAM_CODE_INVALID_NAME, "Invalid param");
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_NAME, "Invalid param");
if (workSpace->area != NULL) {
return 0;
}
int ret = memcpy_s(workSpace->fileName, FILENAME_LEN_MAX, fileName, strlen(fileName));
PROPERTY_CHECK(ret == 0, return PROPERTY_CODE_INVALID_NAME, "Copy file %s fail ", fileName);
PARAM_CHECK(ret == 0, return PARAM_CODE_INVALID_NAME, "Copy file %s fail ", fileName);
int flag = (access(fileName, F_OK) == 0) ? 1 : 0;
int openMode = (flag == 0) ? (O_CREAT | O_RDWR | O_TRUNC) : O_RDWR;
int prot = PROT_READ | PROT_WRITE;
ret = InitWorkSpace_(workSpace, openMode, prot, PROPERTY_WORKSPACE_MAX, flag);
PROPERTY_CHECK(ret == 0, return ret, "Failed to init workspace %s", workSpace->fileName);
ret = InitWorkSpace_(workSpace, openMode, prot, PARAM_WORKSPACE_MAX, flag);
PARAM_CHECK(ret == 0, return ret, "Failed to init workspace %s", workSpace->fileName);
return ret;
}
int InitWorkSpace_(WorkSpace *workSpace, int mode, int prot, u_int32_t spaceSize, int readOnly)
{
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid fileName");
PROPERTY_CHECK(workSpace->allocTrieNode != NULL,
return PROPERTY_CODE_INVALID_PARAM, "Invalid param %s", workSpace->fileName);
PROPERTY_CHECK(workSpace->compareTrieNode != NULL,
return PROPERTY_CODE_INVALID_PARAM, "Invalid param %s", workSpace->fileName);
PROPERTY_LOGI("InitWorkSpace %s ", workSpace->fileName);
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid fileName");
PARAM_CHECK(workSpace->allocTrieNode != NULL,
return PARAM_CODE_INVALID_PARAM, "Invalid param %s", workSpace->fileName);
PARAM_CHECK(workSpace->compareTrieNode != NULL,
return PARAM_CODE_INVALID_PARAM, "Invalid param %s", workSpace->fileName);
PARAM_LOGI("InitWorkSpace %s ", workSpace->fileName);
CheckAndCreateDir(workSpace->fileName);
int fd = open(workSpace->fileName, mode, 00777); //0444);
PROPERTY_CHECK(fd >= 0, return PROPERTY_CODE_INVALID_NAME,
PARAM_CHECK(fd >= 0, return PARAM_CODE_INVALID_NAME,
"Open file %s fail error %s", workSpace->fileName, strerror(errno));
if (!readOnly) {
lseek(fd, spaceSize, SEEK_SET);
lseek(fd, spaceSize - 1, SEEK_SET);
write(fd, "", 1);
}
void *areaAddr = (void *)mmap(NULL, spaceSize, prot, MAP_SHARED, fd, 0);
PROPERTY_CHECK(areaAddr != MAP_FAILED, close(fd); return PROPERTY_CODE_ERROR_MAP_FILE,
PARAM_CHECK(areaAddr != MAP_FAILED, close(fd); return PARAM_CODE_ERROR_MAP_FILE,
"Failed to map memory error %s", strerror(errno));
close(fd);
......@@ -111,34 +111,35 @@ int InitWorkSpace_(WorkSpace *workSpace, int mode, int prot, u_int32_t spaceSize
workSpace->area = (WorkArea*)areaAddr;
workSpace->rootNode = GetTrieNode(workSpace, &workSpace->area->firstNode);
}
PROPERTY_LOGI("InitWorkSpace success, currOffset %u firstNode %u dataSize %u",
workSpace->area->currOffset, workSpace->area->firstNode, workSpace->area->dataSize);
PARAM_LOGI("InitWorkSpace success, readOnly %d currOffset %u firstNode %u dataSize %u",
readOnly, workSpace->area->currOffset, workSpace->area->firstNode, workSpace->area->dataSize);
return 0;
}
void CloseWorkSpace(WorkSpace *workSpace)
{
PROPERTY_CHECK(workSpace != NULL && workSpace->area != NULL, return, "The workspace is null");
PARAM_CHECK(workSpace != NULL && workSpace->area != NULL, return, "The workspace is null");
munmap((char *)workSpace->area, workSpace->area->dataSize);
workSpace->area = NULL;
}
u_int32_t GetWorkSpaceSerial(WorkSpace *workSpace)
{
PROPERTY_CHECK(workSpace != NULL && workSpace->area != NULL, return 0, "The workspace is null");
PARAM_CHECK(workSpace != NULL && workSpace->area != NULL, return 0, "The workspace is null");
return (u_int32_t)workSpace->area->serial;
}
u_int32_t AllocateTrieNode(WorkSpace *workSpace, const char *key, u_int32_t keyLen)
{
u_int32_t len = keyLen + sizeof(TrieNode) + 1;
PROPERTY_CHECK((workSpace->area->currOffset + len) < workSpace->area->dataSize, return 0,
len = (len + 0x03) & (~0x03);
PARAM_CHECK((workSpace->area->currOffset + len) < workSpace->area->dataSize, return 0,
"Failed to allocate currOffset %d, dataSize %d", workSpace->area->currOffset, workSpace->area->dataSize);
TrieNode *node = (TrieNode*)(workSpace->area->data + workSpace->area->currOffset + len);
atomic_init(&node->serial, ATOMIC_VAR_INIT(keyLen << TRIE_SERIAL_KEY_LEN_OFFSET));
int ret = memcpy_s(node->key, keyLen, key, keyLen);
PROPERTY_CHECK(ret == 0, return 0, "Failed to copy key");
PARAM_CHECK(ret == 0, return 0, "Failed to copy key");
node->key[keyLen] = '\0';
node->left = 0;
node->right = 0;
......@@ -150,13 +151,14 @@ u_int32_t AllocateTrieNode(WorkSpace *workSpace, const char *key, u_int32_t keyL
u_int32_t AllocateTrieDataNode(WorkSpace *workSpace, const char *key, u_int32_t keyLen)
{
u_int32_t len = keyLen + sizeof(TrieDataNode) + 1;
PROPERTY_CHECK((workSpace->area->currOffset + len) < workSpace->area->dataSize, return 0,
len = (len + 0x03) & (~0x03);
PARAM_CHECK((workSpace->area->currOffset + len) < workSpace->area->dataSize, return 0,
"Failed to allocate currOffset %d, dataSize %d", workSpace->area->currOffset, workSpace->area->dataSize);
TrieDataNode *node = (TrieDataNode*)(workSpace->area->data + workSpace->area->currOffset);
atomic_init(&node->serial, ATOMIC_VAR_INIT(keyLen << TRIE_SERIAL_KEY_LEN_OFFSET));
int ret = memcpy_s(node->key, keyLen, key, keyLen);
PROPERTY_CHECK(ret == 0, return 0, "Failed to copy key");
PARAM_CHECK(ret == 0, return 0, "Failed to copy key");
node->key[keyLen] = '\0';
node->left = 0;
node->right = 0;
......@@ -234,11 +236,12 @@ static void GetNextKey(const char **remainingKey, int *hasDot, char **subKey, u_
TrieDataNode *AddTrieDataNode(WorkSpace *workSpace, const char *key, u_int32_t keyLen)
{
PROPERTY_CHECK(workSpace->allocTrieNode != NULL, return NULL, "Invalid param %s", key);
PROPERTY_CHECK(workSpace->compareTrieNode != NULL, return NULL, "Invalid param %s", key);
PARAM_CHECK(workSpace->allocTrieNode != NULL, return NULL, "Invalid param %s", key);
PARAM_CHECK(workSpace->compareTrieNode != NULL, return NULL, "Invalid param %s", key);
const char *remainingKey = key;
TrieDataNode *current = (TrieDataNode *)workSpace->rootNode;
PARAM_CHECK(current != NULL, return NULL, "Invalid current param %s", key);
while (1) {
int hasDot = 0;
u_int32_t subKeyLen = 0;
......@@ -258,7 +261,7 @@ TrieDataNode *AddTrieDataNode(WorkSpace *workSpace, const char *key, u_int32_t k
}
} else if (hasDot) {
u_int32_t offset = workSpace->allocTrieNode(workSpace, remainingKey, subKeyLen);
PROPERTY_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
PARAM_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
SaveIndex(&current->child, offset);
current = (TrieDataNode*)GetTrieNode(workSpace, &current->child);
} else {
......@@ -283,7 +286,7 @@ TrieDataNode *AddToSubTrie(WorkSpace *workSpace, TrieDataNode *dataNode, const c
root = (TrieDataNode *)GetTrieNode(workSpace, &dataNode->left);
if (root == NULL) {
u_int32_t offset = workSpace->allocTrieNode(workSpace, key, keyLen);
PROPERTY_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
PARAM_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
SaveIndex(&dataNode->left, offset);
return (TrieDataNode *)GetTrieNode(workSpace, &dataNode->left);
}
......@@ -291,7 +294,7 @@ TrieDataNode *AddToSubTrie(WorkSpace *workSpace, TrieDataNode *dataNode, const c
root = (TrieDataNode *)GetTrieNode(workSpace, &dataNode->right);
if (root == NULL) {
u_int32_t offset = workSpace->allocTrieNode(workSpace, key, keyLen);
PROPERTY_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
PARAM_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
SaveIndex(&dataNode->right, offset);
return (TrieDataNode *)GetTrieNode(workSpace, &dataNode->right);
}
......@@ -301,7 +304,7 @@ TrieDataNode *AddToSubTrie(WorkSpace *workSpace, TrieDataNode *dataNode, const c
TrieNode *AddTrieNode(WorkSpace *workSpace, TrieNode *root, const char *key, u_int32_t keyLen)
{
PROPERTY_CHECK(root != NULL, return NULL, "Invalid param %s", key);
PARAM_CHECK(root != NULL, return NULL, "Invalid param %s", key);
TrieNode *current = root;
TrieNode *next = NULL;
while (1) {
......@@ -316,7 +319,7 @@ TrieNode *AddTrieNode(WorkSpace *workSpace, TrieNode *root, const char *key, u_i
next = GetTrieNode(workSpace, &current->left);
if (next == NULL) {
u_int32_t offset = workSpace->allocTrieNode(workSpace, key, keyLen);
PROPERTY_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
PARAM_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
SaveIndex(&current->left, offset);
return GetTrieNode(workSpace, &current->left);
}
......@@ -324,7 +327,7 @@ TrieNode *AddTrieNode(WorkSpace *workSpace, TrieNode *root, const char *key, u_i
next = GetTrieNode(workSpace, &current->right);
if (next == NULL) {
u_int32_t offset = workSpace->allocTrieNode(workSpace, key, keyLen);
PROPERTY_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
PARAM_CHECK(offset != 0, return NULL, "Failed to allocate key %s", key);
SaveIndex(&current->right, offset);
return GetTrieNode(workSpace, &current->right);
}
......@@ -336,12 +339,13 @@ TrieNode *AddTrieNode(WorkSpace *workSpace, TrieNode *root, const char *key, u_i
TrieDataNode *FindTrieDataNode(WorkSpace *workSpace, const char *key, u_int32_t keyLen, int matchPrefix)
{
PROPERTY_CHECK(workSpace->allocTrieNode != NULL, return NULL, "Invalid param %s", key);
PROPERTY_CHECK(workSpace->compareTrieNode != NULL, return NULL, "Invalid param %s", key);
PARAM_CHECK(workSpace->allocTrieNode != NULL, return NULL, "Invalid param %s", key);
PARAM_CHECK(workSpace->compareTrieNode != NULL, return NULL, "Invalid param %s", key);
const char *remainingKey = key;
TrieDataNode *matchNode = (TrieDataNode *)workSpace->rootNode;
TrieDataNode *current = (TrieDataNode *)workSpace->rootNode;
PARAM_CHECK(current != NULL, return NULL, "Invalid current param %s", key);
while (1) {
int hasDot = 0;
u_int32_t subKeyLen = 0;
......@@ -394,7 +398,7 @@ TrieDataNode *FindSubTrie(WorkSpace *workSpace, TrieDataNode *dataNode, const ch
TrieNode *FindTrieNode(WorkSpace *workSpace, TrieNode *root, const char *key, u_int32_t keyLen)
{
PROPERTY_CHECK(root != NULL, return NULL, "Invalid param %s", key);
PARAM_CHECK(root != NULL, return NULL, "Invalid param %s", key);
TrieNode *current = root;
TrieNode *next = NULL;
while (1) {
......@@ -420,8 +424,8 @@ TrieNode *FindTrieNode(WorkSpace *workSpace, TrieNode *root, const char *key, u_
int TraversalTrieDataNode(WorkSpace *workSpace, TrieDataNode *current, TraversalTrieNodePtr walkFunc, void* cookie)
{
PROPERTY_CHECK(walkFunc != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(walkFunc != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
if (current == NULL) {
return 0;
}
......@@ -446,8 +450,8 @@ int TraversalTrieDataNode(WorkSpace *workSpace, TrieDataNode *current, Traversal
int TraversalTrieNode(WorkSpace *workSpace, TrieNode *root, TraversalTrieNodePtr walkFunc, void* cookie)
{
PROPERTY_CHECK(workSpace != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PROPERTY_CHECK(walkFunc != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(workSpace != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(walkFunc != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
if (root == NULL) {
return 0;
}
......@@ -459,43 +463,45 @@ int TraversalTrieNode(WorkSpace *workSpace, TrieNode *root, TraversalTrieNodePtr
u_int32_t AddData(WorkSpace *workSpace, const char *key, u_int32_t keyLen, const char *value, u_int32_t valueLen)
{
PROPERTY_CHECK(workSpace != NULL, return 0, "Invalid param");
PROPERTY_CHECK(key != NULL && value != NULL, return 0, "Invalid param");
PARAM_CHECK(workSpace != NULL, return 0, "Invalid param");
PARAM_CHECK(key != NULL && value != NULL, return 0, "Invalid param");
u_int32_t realLen = sizeof(DataEntry) + 1 + 1;
if (valueLen > PROPERTY_VALUE_LEN_MAX) { // value超过最大时,只能是只读属性,保存最大字符串
realLen = keyLen + valueLen;
if (valueLen > PARAM_VALUE_LEN_MAX) {
realLen += keyLen + valueLen;
} else {
realLen = keyLen + PROPERTY_VALUE_LEN_MAX; // 属性保存,预留最大属性值长度
realLen += keyLen + PARAM_VALUE_LEN_MAX;
}
PROPERTY_CHECK((workSpace->area->currOffset + realLen) < workSpace->area->dataSize, return 0,
realLen = (realLen + 0x03) & (~0x03);
//PARAM_LOGI("AddData realLen %u %u %u", realLen, keyLen, valueLen);
PARAM_CHECK((workSpace->area->currOffset + realLen) < workSpace->area->dataSize, return 0,
"Failed to allocate currOffset %d, dataSize %d", workSpace->area->currOffset, workSpace->area->dataSize);
DataEntry *node = (DataEntry*)(workSpace->area->data + workSpace->area->currOffset);
u_int32_t dataLength = keyLen << TRIE_SERIAL_KEY_LEN_OFFSET | valueLen << TRIE_SERIAL_DATA_LEN_OFFSET;
atomic_init(&node->serial, ATOMIC_VAR_INIT(0));
atomic_init(&node->dataLength, ATOMIC_VAR_INIT(dataLength));
int ret = memcpy_s(node->data, keyLen, key, keyLen);
ret |= memcpy_s(node->data + keyLen + 1, valueLen, value, valueLen);
PROPERTY_CHECK(ret == 0, return 0, "Failed to copy key");
PARAM_CHECK(ret == 0, return 0, "Failed to copy key");
node->data[keyLen] = '=';
node->data[keyLen + 1 + valueLen] = '\0';
u_int32_t offset = workSpace->area->currOffset;
workSpace->area->currOffset += realLen;
//PARAM_LOGI("AddData node %p %u %d", node, offset, gettid());
return offset;
}
int UpdateDataValue(DataEntry *entry, const char *value)
{
PROPERTY_CHECK(entry != NULL && value != NULL, return PROPERTY_CODE_INVALID_PARAM, "Failed to check param");
int ret = PROPERTY_CODE_INVALID_VALUE;
PARAM_CHECK(entry != NULL && value != NULL, return PARAM_CODE_INVALID_PARAM, "Failed to check param");
int ret = PARAM_CODE_INVALID_VALUE;
u_int32_t keyLen = DATA_ENTRY_KEY_LEN(entry);
u_int32_t valueLen = strlen(value);
u_int32_t oldLen = DATA_ENTRY_DATA_LEN(entry);
if (oldLen < PROPERTY_VALUE_LEN_MAX && valueLen < PROPERTY_VALUE_LEN_MAX) {
PROPERTY_LOGE("Old value %s new value %s", entry->data + keyLen + 1, value);
ret = memcpy_s(entry->data + keyLen + 1, PROPERTY_VALUE_LEN_MAX, value, valueLen + 1);
PROPERTY_CHECK(ret == 0, return PROPERTY_CODE_INVALID_VALUE, "Failed to copy value");
if (oldLen < PARAM_VALUE_LEN_MAX && valueLen < PARAM_VALUE_LEN_MAX) {
PARAM_LOGE("Old value %s new value %s", entry->data + keyLen + 1, value);
ret = memcpy_s(entry->data + keyLen + 1, PARAM_VALUE_LEN_MAX, value, valueLen + 1);
PARAM_CHECK(ret == 0, return PARAM_CODE_INVALID_VALUE, "Failed to copy value");
u_int32_t dataLength = keyLen << TRIE_SERIAL_KEY_LEN_OFFSET | valueLen << TRIE_SERIAL_DATA_LEN_OFFSET;
atomic_store_explicit(&entry->dataLength, dataLength, memory_order_release);
}
......@@ -514,23 +520,23 @@ u_int32_t GetDataSerial(const DataEntry *entry)
int GetDataName(const DataEntry *entry, char *name, u_int32_t len)
{
PROPERTY_CHECK(entry != NULL && name != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(entry != NULL && name != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
u_int32_t keyLen = DATA_ENTRY_KEY_LEN(entry);
PROPERTY_CHECK(len > keyLen, return -1, "Invalid param size");
PARAM_CHECK(len > keyLen, return -1, "Invalid param size");
int ret = memcpy_s(name, len, entry->data, keyLen);
PROPERTY_CHECK(ret == 0, return PROPERTY_CODE_INVALID_PARAM, "Failed to copy name");
PARAM_CHECK(ret == 0, return PARAM_CODE_INVALID_PARAM, "Failed to copy name");
name[keyLen] = '\0';
return ret;
}
int GetDataValue(const DataEntry *entry, char *value, u_int32_t len)
{
PROPERTY_CHECK(entry != NULL && value != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
PARAM_CHECK(entry != NULL && value != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
u_int32_t keyLen = DATA_ENTRY_KEY_LEN(entry);
u_int32_t valueLen = DATA_ENTRY_DATA_LEN(entry);
PROPERTY_CHECK(len > valueLen, return PROPERTY_CODE_INVALID_PARAM, "Invalid value len %u %u", len, valueLen);
PARAM_CHECK(len > valueLen, return PARAM_CODE_INVALID_PARAM, "Invalid value len %u %u", len, valueLen);
int ret = memcpy_s(value, len, entry->data + keyLen + 1, valueLen);
PROPERTY_CHECK(ret == 0, return PROPERTY_CODE_INVALID_PARAM, "Failed to copy value");
PARAM_CHECK(ret == 0, return PARAM_CODE_INVALID_PARAM, "Failed to copy value");
value[valueLen] = '\0';
return ret;
}
......@@ -12,7 +12,7 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "property.h"
#include "sys_param.h"
#include <ctype.h>
#include <errno.h>
......@@ -26,8 +26,8 @@
#include <sys/types.h>
#include <unistd.h>
#include "property_manager.h"
#include "property_trie.h"
#include "param_manager.h"
#include "param_trie.h"
#define LABEL "Manager"
#define MAX_BUFF 256
......@@ -38,11 +38,11 @@ typedef struct {
char *buffer;
} PersistContext;
static PropertyPersistWorkSpace g_persistWorkSpace = {ATOMIC_VAR_INIT(0), };
static ParamPersistWorkSpace g_persistWorkSpace = {ATOMIC_VAR_INIT(0), };
static int ProcessPropertTraversal(WorkSpace *workSpace, TrieNode *node, void *cookie)
static int ProcessParamTraversal(WorkSpace *workSpace, TrieNode *node, void *cookie)
{
PROPERTY_CHECK(workSpace != 0 && node != NULL && cookie != NULL, return -1, "Invalid param");
PARAM_CHECK(workSpace != 0 && node != NULL && cookie != NULL, return -1, "Invalid param");
TrieDataNode *current = (TrieDataNode *)node;
if (current == NULL || current->dataIndex == 0) {
return 0;
......@@ -58,10 +58,11 @@ static int ProcessPropertTraversal(WorkSpace *workSpace, TrieNode *node, void *c
}
ret |= GetDataValue(entry, persistContext->buffer + MAX_BUFF, MAX_BUFF);
if (ret == 0) { // 只支持新建
PROPERTY_LOGI("Insert new persist property from normal property %s", persistContext->buffer);
ret = AddProperty(persistContext->persistWorkSpace, persistContext->buffer, persistContext->buffer + MAX_BUFF);
//PARAM_LOGI("Insert new persist param from normal param %s %s",
// persistContext->buffer, persistContext->buffer + MAX_BUFF);
ret = AddParam(persistContext->persistWorkSpace, persistContext->buffer, persistContext->buffer + MAX_BUFF);
}
PROPERTY_CHECK(ret == 0, return ret, "Failed to add persist property");
PARAM_CHECK(ret == 0, return ret, "Failed to add persist param");
return ret;
}
......@@ -79,53 +80,50 @@ static int ProcessPersistPropertTraversal(WorkSpace *workSpace, TrieNode *node,
int ret = GetDataName(entry, persistContext->buffer, MAX_BUFF);
ret |= GetDataValue(entry, persistContext->buffer + MAX_BUFF, MAX_BUFF);
if (ret == 0) {
PROPERTY_LOGI("update normal property %s %s from persist property ",
persistContext->buffer, persistContext->buffer + MAX_BUFF);
ret = WriteProperty(persistContext->workSpace, persistContext->buffer, persistContext->buffer + MAX_BUFF);
//PARAM_LOGI("update normal param %s %s from persist param %u",
// persistContext->buffer, persistContext->buffer + MAX_BUFF, current->dataIndex);
ret = WriteParam(persistContext->workSpace, persistContext->buffer, persistContext->buffer + MAX_BUFF);
}
PROPERTY_CHECK(ret == 0, return ret, "Failed to add persist property");
PARAM_CHECK(ret == 0, return ret, "Failed to add persist param");
return ret;
}
int InitPersistPropertyWorkSpace(const char *context)
int InitPersistParamWorkSpace(const char *context)
{
u_int32_t flags = atomic_load_explicit(&g_persistWorkSpace.flags, memory_order_relaxed);
PROPERTY_LOGI("InitPersistPropertyWorkSpace flags %x", flags);
if ((flags & WORKSPACE_FLAGS_INIT) == WORKSPACE_FLAGS_INIT) {
return 0;
}
g_persistWorkSpace.persistWorkSpace.compareTrieNode = CompareTrieDataNode;
g_persistWorkSpace.persistWorkSpace.allocTrieNode = AllocateTrieDataNode;
int ret = InitPersistWorkSpace(PROPERTY_PERSIST_PATH, &g_persistWorkSpace.persistWorkSpace);
int ret = InitPersistWorkSpace(PARAM_PERSIST_PATH, &g_persistWorkSpace.persistWorkSpace);
PARAM_CHECK(ret == 0, return ret, "Failed to init persist param");
atomic_store_explicit(&g_persistWorkSpace.flags, WORKSPACE_FLAGS_INIT, memory_order_release);
return ret;
}
int RefreshPersistProperties(PropertyWorkSpace *workSpace, const char *context)
int RefreshPersistParams(ParamWorkSpace *workSpace, const char *context)
{
int ret = InitPersistParamWorkSpace(context);
PARAM_CHECK(ret == 0, return ret, "Failed to init persist param");
u_int32_t flags = atomic_load_explicit(&g_persistWorkSpace.flags, memory_order_relaxed);
if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) {
int ret = InitPersistPropertyWorkSpace(context);
PROPERTY_CHECK(ret == 0, return ret, "Failed to init persist property");
flags = atomic_load_explicit(&g_persistWorkSpace.flags, memory_order_relaxed);
}
if ((flags & WORKSPACE_FLAGS_LOADED) == WORKSPACE_FLAGS_LOADED) {
PARAM_LOGE("RefreshPersistParams has been loaded");
return 0;
}
// 申请临时的缓存,用于数据读取
char *buffer = (char *)malloc(MAX_BUFF + MAX_BUFF);
PROPERTY_CHECK(buffer != NULL, return -1, "Failed to malloc memory for property");
PARAM_CHECK(buffer != NULL, return -1, "Failed to malloc memory for param");
PersistContext persistContext = {
&workSpace->propertySpace, &g_persistWorkSpace.persistWorkSpace, buffer
&workSpace->paramSpace, &g_persistWorkSpace.persistWorkSpace, buffer
};
// 遍历当前的属性,并把persist的写入
int ret = TraversalTrieDataNode(&workSpace->propertySpace,
(TrieDataNode *)workSpace->propertySpace.rootNode, ProcessPropertTraversal, &persistContext);
// 遍历当前的参数,并把persist的写入
ret = TraversalTrieDataNode(&workSpace->paramSpace,
(TrieDataNode *)workSpace->paramSpace.rootNode, ProcessParamTraversal, &persistContext);
// 修改默认属性
// 修改默认参数
ret = TraversalTrieDataNode(&g_persistWorkSpace.persistWorkSpace,
(TrieDataNode *)g_persistWorkSpace.persistWorkSpace.rootNode, ProcessPersistPropertTraversal, &persistContext);
......@@ -134,23 +132,23 @@ int RefreshPersistProperties(PropertyWorkSpace *workSpace, const char *context)
return ret;
}
void ClosePersistPropertyWorkSpace()
void ClosePersistParamWorkSpace()
{
CloseWorkSpace(&g_persistWorkSpace.persistWorkSpace);
atomic_store_explicit(&g_persistWorkSpace.flags, 0, memory_order_release);
}
int WritePersistProperty(const char *name, const char *value)
int WritePersistParam(const char *name, const char *value)
{
PROPERTY_CHECK(value != NULL && name != NULL, return PROPERTY_CODE_INVALID_PARAM, "Invalid param");
u_int32_t flags = atomic_load_explicit(&g_persistWorkSpace.flags, memory_order_relaxed);
if ((flags & WORKSPACE_FLAGS_LOADED) != WORKSPACE_FLAGS_LOADED) {
PARAM_CHECK(value != NULL && name != NULL, return PARAM_CODE_INVALID_PARAM, "Invalid param");
if (strncmp(name, "persist.", strlen("persist.")) != 0) {
return 0;
}
if (strncmp(name, "persist.", strlen("persist.")) != 0) {
int ret = InitPersistParamWorkSpace("");
PARAM_CHECK(ret == 0, return ret, "Failed to init persist param");
u_int32_t flags = atomic_load_explicit(&g_persistWorkSpace.flags, memory_order_relaxed);
if ((flags & WORKSPACE_FLAGS_LOADED) != WORKSPACE_FLAGS_LOADED) {
return 0;
}
return WriteProperty(&g_persistWorkSpace.persistWorkSpace, name, value);
return WriteParam(&g_persistWorkSpace.persistWorkSpace, name, value);
}
......@@ -13,17 +13,17 @@
* limitations under the License.
*/
#include "property_service.h"
#include "param_service.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include "property.h"
#include "property_manager.h"
#include "property_request.h"
#include "trigger.h"
#include "sys_param.h"
#include "param_manager.h"
#include "param_request.h"
#include "init_param.h"
#include "uv.h"
......@@ -31,95 +31,90 @@
#define LABEL "Server"
static char *g_initContext = "";
static PropertyWorkSpace g_propertyWorkSpace = {ATOMIC_VAR_INIT(0), {}, {}, {}};
static ParamWorkSpace g_paramWorkSpace = {ATOMIC_VAR_INIT(0), {}, {}, {}};
void InitPropertyService()
void InitParamService()
{
int ret = InitPropertyWorkSpace(&g_propertyWorkSpace, 0, g_initContext);
PROPERTY_CHECK(ret == 0, return, "Init propert workspace fail");
int ret = InitParamWorkSpace(&g_paramWorkSpace, 0, g_initContext);
PARAM_CHECK(ret == 0, return, "Init parameter workspace fail");
}
int LoadDefaultProperty(const char *fileName)
int LoadDefaultParams(const char *fileName)
{
u_int32_t flags = atomic_load_explicit(&g_propertyWorkSpace.flags, memory_order_relaxed);
u_int32_t flags = atomic_load_explicit(&g_paramWorkSpace.flags, memory_order_relaxed);
if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) {
return PROPERTY_CODE_NOT_INIT;
return PARAM_CODE_NOT_INIT;
}
FILE *fp = fopen(fileName, "r");
PROPERTY_CHECK(fp != NULL, return -1, "Open file %s fail", fileName);
PARAM_CHECK(fp != NULL, return -1, "Open file %s fail", fileName);
char buff[BUFFER_SIZE];
SubStringInfo *info = malloc(sizeof(SubStringInfo) * (SUBSTR_INFO_LABEL + 1));
while(fgets(buff, BUFFER_SIZE, fp) != NULL) {
int subStrNumber = GetSubStringInfo(buff, strlen(buff), '\n', info, SUBSTR_INFO_LABEL + 1);
int subStrNumber = GetSubStringInfo(buff, strlen(buff), '=', info, SUBSTR_INFO_LABEL + 1);
if (subStrNumber <= SUBSTR_INFO_LABEL) {
continue;
}
if (strncmp(info[0].value, "ctl.", strlen("ctl.")) == 0) {
PROPERTY_LOGE("Do not set ctl. properties from init %s", info[0].value);
PARAM_LOGE("Do not set ctl. parameters from init %s", info[0].value);
continue;
}
if (strcmp(info[0].value, "selinux.restorecon_recursive") == 0) {
PROPERTY_LOGE("Do not set selinux.restorecon_recursive from init %s", info[0].value);
PARAM_LOGE("Do not set selinux.restorecon_recursive from init %s", info[0].value);
continue;
}
int ret = CheckPropertyName(info[0].value, 0);
PROPERTY_CHECK(ret == 0, continue, "Illegal property name %s", info[0].value);
int ret = CheckParamName(info[0].value, 0);
PARAM_CHECK(ret == 0, continue, "Illegal param name %s", info[0].value);
ret = WriteProperty(&g_propertyWorkSpace.propertySpace, info[0].value, info[1].value);
PROPERTY_CHECK(ret == 0, continue, "Failed to set property %d %s", ret, buff);
ret = WritePersistProperty(info[0].value, info[1].value);
PROPERTY_CHECK(ret == 0, continue, "Failed to set persist property %d %s", ret, buff);
ret = WriteParam(&g_paramWorkSpace.paramSpace, info[0].value, info[1].value);
PARAM_CHECK(ret == 0, continue, "Failed to set param %d %s", ret, buff);
}
fclose(fp);
free(info);
PROPERTY_LOGI("LoadDefaultProperty proterty success %s", fileName);
PARAM_LOGI("LoadDefaultParams proterty success %s", fileName);
return 0;
}
int LoadPropertyInfo(const char *fileName)
int LoadParamInfos(const char *fileName)
{
u_int32_t flags = atomic_load_explicit(&g_propertyWorkSpace.flags, memory_order_relaxed);
u_int32_t flags = atomic_load_explicit(&g_paramWorkSpace.flags, memory_order_relaxed);
if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) {
return PROPERTY_CODE_NOT_INIT;
return PARAM_CODE_NOT_INIT;
}
FILE *fp = fopen(fileName, "r");
PROPERTY_CHECK(fp != NULL, return -1, "Open file %s fail", fileName);
PARAM_CHECK(fp != NULL, return -1, "Open file %s fail", fileName);
SubStringInfo *info = malloc(sizeof(SubStringInfo) * SUBSTR_INFO_MAX);
char buff[BUFFER_SIZE];
int propInfoCount = 0;
int infoCount = 0;
while(fgets(buff, BUFFER_SIZE, fp) != NULL) {
int subStrNumber = GetSubStringInfo(buff, strlen(buff), ' ', info, SUBSTR_INFO_MAX);
if (subStrNumber <= 0) {
continue;
}
int ret = WritePropertyInfo(&g_propertyWorkSpace, info, subStrNumber);
PROPERTY_CHECK(ret == 0, continue, "Failed to write property info %d %s", ret, buff);
propInfoCount++;
int ret = WriteParamInfo(&g_paramWorkSpace, info, subStrNumber);
PARAM_CHECK(ret == 0, continue, "Failed to write param info %d %s", ret, buff);
infoCount++;
}
fclose(fp);
free(info);
PROPERTY_LOGI("Load proterty info %d success %s", propInfoCount, fileName);
PARAM_LOGI("Load parameter info %d success %s", infoCount, fileName);
return 0;
}
static int ProcessPropertySet(RequestMsg *msg)
static int ProcessParamSet(RequestMsg *msg)
{
PROPERTY_CHECK(msg != NULL, return PROPERTY_CODE_INVALID_PARAM, "Failed to check param");
PARAM_CHECK(msg != NULL, return PARAM_CODE_INVALID_PARAM, "Failed to check param");
SubStringInfo info[3];
int ret = GetSubStringInfo(msg->content, msg->contentSize, '=', info, sizeof(info)/sizeof(info[0]));
PROPERTY_CHECK(ret >= 2, return ret, "Failed to get name from content %s", msg->content);
PROPERTY_LOGI("ProcessPropertySet name %s value: %s", info[0].value, info[1].value);
ret = WritePropertyWithCheck(&g_propertyWorkSpace, &msg->securitylabel, info[0].value, info[1].value);
PROPERTY_CHECK(ret == 0, return ret, "Failed to set property %d name %s %s", ret, info[0].value, info[1].value);
ret = WritePersistProperty(info[0].value, info[1].value);
PROPERTY_CHECK(ret == 0, return ret, "Failed to set property");
PARAM_CHECK(ret >= 2, return ret, "Failed to get name from content %s", msg->content);
PARAM_LOGI("ProcessParamSet name %s value: %s", info[0].value, info[1].value);
ret = WriteParamWithCheck(&g_paramWorkSpace, &msg->securitylabel, info[0].value, info[1].value);
PARAM_CHECK(ret == 0, return ret, "Failed to set param %d name %s %s", ret, info[0].value, info[1].value);
ret = WritePersistParam(info[0].value, info[1].value);
PARAM_CHECK(ret == 0, return ret, "Failed to set param");
// notify event to process trigger
PostTrigger(EVENT_PROPERTY, msg->content, msg->contentSize);
return 0;
......@@ -133,14 +128,14 @@ static void OnClose(uv_handle_t *handle)
static void OnReceiveAlloc(uv_handle_t *handle, size_t suggestedSize, uv_buf_t* buf)
{
// 这里需要按实际消息的大小申请内存,取最大消息的长度
buf->base = (char *)malloc(sizeof(RequestMsg) + BUFFER_SIZE * 2);
buf->len = suggestedSize;
buf->len = sizeof(RequestMsg) + BUFFER_SIZE * 2;
buf->base = (char *)malloc(buf->len);
}
static void OnWriteResponse(uv_write_t *req, int status)
{
// 发送成功,释放请求内存
PROPERTY_LOGI("OnWriteResponse status %d", status);
PARAM_LOGI("OnWriteResponse status %d", status);
ResponseNode *node = (ResponseNode*)req;
free(node);
}
......@@ -150,17 +145,17 @@ static void SendResponse(uv_stream_t *handle, RequestType type, int result, void
int ret = 0;
// 申请整块内存,用于回复数据和写请求
ResponseNode *response = (ResponseNode *)malloc(sizeof(ResponseNode) + size);
PROPERTY_CHECK(response != NULL, return, "Failed to alloc memory for response");
PARAM_CHECK(response != NULL, return, "Failed to alloc memory for response");
response->msg.type = type;
response->msg.contentSize = size;
response->msg.result = result;
if (content != NULL && size != 0) {
ret = memcpy_s(response->msg.content, size, content, size);
PROPERTY_CHECK(ret == 0, return, "Failed to copy content");
PARAM_CHECK(ret == 0, return, "Failed to copy content");
}
uv_buf_t buf = uv_buf_init((char *)&response->msg, sizeof(response->msg) + size);
ret = uv_write2(&response->writer, handle, &buf, 1, handle, OnWriteResponse);
PROPERTY_CHECK(ret >= 0, return, "Failed to uv_write2 ret %s", uv_strerror(ret));
PARAM_CHECK(ret >= 0, return, "Failed to uv_write2 ret %s", uv_strerror(ret));
}
static void OnReceiveRequest(uv_stream_t *handle, ssize_t nread, const uv_buf_t *buf)
......@@ -173,110 +168,109 @@ static void OnReceiveRequest(uv_stream_t *handle, ssize_t nread, const uv_buf_t
int freeHandle = 1;
RequestMsg *msg = (RequestMsg *)buf->base;
switch (msg->type) {
case SET_PROPERTY: {
case SET_PARAM: {
freeHandle = 0;
int ret = ProcessPropertySet(msg);
SendResponse(handle, SET_PROPERTY, ret, NULL, 0);
int ret = ProcessParamSet(msg);
SendResponse(handle, SET_PARAM, ret, NULL, 0);
break;
}
default:
PROPERTY_LOGE("not supported the command: %d", msg->type);
PARAM_LOGE("not supported the command: %d", msg->type);
break;
}
free(buf->base);
uv_close((uv_handle_t*)handle, OnClose);
}
static void RemoveSocket(int sig)
{
uv_fs_t req;
uv_fs_unlink(uv_default_loop(), &req, PIPE_NAME, NULL);
ClosePropertyWorkSpace(&g_propertyWorkSpace);
ClosePersistPropertyWorkSpace();
uv_stop(uv_default_loop());
exit(0);
}
static void OnConnection(uv_stream_t *server, int status)
{
PROPERTY_CHECK(status >= 0, return, "Error status %d", status);
PROPERTY_CHECK(server != NULL, return, "Error server");
PARAM_CHECK(status >= 0, return, "Error status %d", status);
PARAM_CHECK(server != NULL, return, "Error server");
uv_pipe_t *stream = (uv_pipe_t*)malloc(sizeof(uv_pipe_t));
PROPERTY_CHECK(stream != NULL, return, "Failed to alloc stream");
PARAM_CHECK(stream != NULL, return, "Failed to alloc stream");
int ret = uv_pipe_init(uv_default_loop(), (uv_pipe_t*)stream, 1);
PROPERTY_CHECK(ret == 0, free(stream); return, "Failed to uv_pipe_init %d", ret);
PARAM_CHECK(ret == 0, free(stream); return, "Failed to uv_pipe_init %d", ret);
stream->data = server;
ret = uv_accept(server, (uv_stream_t *)stream);
PROPERTY_CHECK(ret == 0, uv_close((uv_handle_t*)stream, NULL); free(stream);
PARAM_CHECK(ret == 0, uv_close((uv_handle_t*)stream, NULL); free(stream);
return, "Failed to uv_accept %d", ret);
ret = uv_read_start((uv_stream_t *)stream, OnReceiveAlloc, OnReceiveRequest);
PROPERTY_CHECK(ret == 0, uv_close((uv_handle_t*)stream, NULL); free(stream);
PARAM_CHECK(ret == 0, uv_close((uv_handle_t*)stream, NULL); free(stream);
return, "Failed to uv_read_start %d", ret);
}
int StartPropertyService()
void StopParamService()
{
PROPERTY_LOGI("StartPropertyService.");
uv_fs_t req;
uv_fs_unlink(uv_default_loop(), &req, PIPE_NAME, NULL);
CloseParamWorkSpace(&g_paramWorkSpace);
ClosePersistParamWorkSpace();
uv_stop(uv_default_loop());
PARAM_LOGI("StopParamService.");
}
signal(SIGINT, RemoveSocket);
int StartParamService()
{
PARAM_LOGI("StartParamService.");
uv_fs_t req;
uv_fs_unlink(uv_default_loop(), &req, PIPE_NAME, NULL);
uv_pipe_t pipeServer;
int ret = uv_pipe_init(uv_default_loop(), &pipeServer, 0);
PROPERTY_CHECK(ret == 0, return ret, "Failed to uv_pipe_init %d", ret);
PARAM_CHECK(ret == 0, return ret, "Failed to uv_pipe_init %d", ret);
ret = uv_pipe_bind(&pipeServer, PIPE_NAME);
PROPERTY_CHECK(ret == 0, return ret, "Failed to uv_pipe_bind %d %s", ret, uv_err_name(ret));
PARAM_CHECK(ret == 0, return ret, "Failed to uv_pipe_bind %d %s", ret, uv_err_name(ret));
ret = uv_listen((uv_stream_t*)&pipeServer, SOMAXCONN, OnConnection);
PROPERTY_CHECK(ret == 0, return ret, "Failed to uv_listen %d %s", ret, uv_err_name(ret));
PARAM_CHECK(ret == 0, return ret, "Failed to uv_listen %d %s", ret, uv_err_name(ret));
uv_run(uv_default_loop(), UV_RUN_DEFAULT);
PROPERTY_LOGI("Start service exit.");
PARAM_LOGI("Start service exit.");
return 0;
}
int SystemWriteParameter(const char *name, const char *value)
int SystemWriteParam(const char *name, const char *value)
{
PROPERTY_CHECK(name != NULL && value != NULL, return -1, "The name is null");
PROPERTY_LOGI("SystemWriteParameter name %s value: %s", name, value);
int ret = WritePropertyWithCheck(&g_propertyWorkSpace, &g_propertyWorkSpace.label, name, value);
PARAM_CHECK(name != NULL && value != NULL, return -1, "The name is null");
PARAM_LOGI("SystemWriteParam name %s value: %s", name, value);
int ret = WriteParamWithCheck(&g_paramWorkSpace, &g_paramWorkSpace.label, name, value);
//PARAM_LOGI("SystemWriteParam name %s value: %s", name, value);
if (ret == 0) {
ret = WritePersistProperty(name, value);
PROPERTY_CHECK(ret == 0, return ret, "Failed to set property");
ret = WritePersistParam(name, value);
PARAM_CHECK(ret == 0, return ret, "Failed to set param");
} else {
PROPERTY_LOGE("Failed to set property %d name %s %s", ret, name, value);
PARAM_LOGE("Failed to set param %d name %s %s", ret, name, value);
}
// notify event to process trigger
PostPropertyTrigger(name, value);
PostParamTrigger(name, value);
return 0;
}
int SystemReadParameter(const char *name, char *value, unsigned int *len)
int SystemReadParam(const char *name, char *value, unsigned int *len)
{
PROPERTY_CHECK(name != NULL && len != NULL, return -1, "The name is null");
PropertyHandle handle = 0;
int ret = ReadPropertyWithCheck(&g_propertyWorkSpace, name, &handle);
PARAM_CHECK(name != NULL && len != NULL, return -1, "The name is null");
ParamHandle handle = 0;
int ret = ReadParamWithCheck(&g_paramWorkSpace, name, &handle);
if (ret == 0) {
ret = ReadPropertyValue(&g_propertyWorkSpace, handle, value, len);
ret = ReadParamValue(&g_paramWorkSpace, handle, value, len);
}
return ret;
}
int SystemTraversalParameters(void (*traversalParameter)(PropertyHandle handle, void* cookie), void* cookie)
ParamWorkSpace *GetParamWorkSpace()
{
PROPERTY_CHECK(traversalParameter != NULL, return -1, "The param is null");
return TraversalProperty(&g_propertyWorkSpace, traversalParameter, cookie);
return &g_paramWorkSpace;
}
PropertyWorkSpace *GetPropertyWorkSpace()
int LoadPersistParams()
{
return &g_propertyWorkSpace;
return RefreshPersistParams(&g_paramWorkSpace, g_initContext);
}
int LoadPersistProperties()
int SystemTraversalParam(void (*traversalParameter)(ParamHandle handle, void* cookie), void* cookie)
{
return RefreshPersistProperties(&g_propertyWorkSpace, g_initContext);
}
PARAM_CHECK(traversalParameter != NULL, return -1, "The param is null");
return TraversalParam(&g_paramWorkSpace, traversalParameter, cookie);
}
\ No newline at end of file
......@@ -16,18 +16,19 @@
#include "trigger_checker.h"
#include <ctype.h>
#include "trigger_manager.h"
#include "property_service.h"
#include "param_service.h"
#define LABEL "Trigger"
// 申请整块能存作为计算的节点
int CalculatorInit(LogicCalculator *calculator, int dataNumber, int dataUnit, int needCondition)
{
TRIGGER_CHECK(calculator != NULL, return -1, "Invalid param");
PARAM_CHECK(calculator != NULL, return -1, "Invalid param");
int dataSize = dataUnit * dataNumber;
if (needCondition) {
dataSize += 5 * SUPPORT_DATA_BUFFER_MAX;
}
calculator->data = (char *)malloc(dataSize);
TRIGGER_CHECK(calculator->data != NULL, return -1, "Failed to malloc for calculator");
PARAM_CHECK(calculator->data != NULL, return -1, "Failed to malloc for calculator");
calculator->dataNumber = dataNumber;
calculator->endIndex = 0;
calculator->dataUnit = dataUnit;
......@@ -47,30 +48,30 @@ int CalculatorInit(LogicCalculator *calculator, int dataNumber, int dataUnit, in
void CalculatorFree(LogicCalculator *calculator)
{
TRIGGER_CHECK(calculator != NULL, return, "Invalid param");
PARAM_CHECK(calculator != NULL, return, "Invalid param");
free(calculator->data);
calculator->data = NULL;
}
static void CalculatorClear(LogicCalculator *calculator)
{
TRIGGER_CHECK(calculator != NULL, return, "Invalid param");
PARAM_CHECK(calculator != NULL, return, "Invalid param");
calculator->endIndex = 0;
}
static int CalculatorPushChar(LogicCalculator *calculator, char data)
{
TRIGGER_CHECK(calculator != NULL, return -1, "Invalid param");
TRIGGER_CHECK(calculator->endIndex < calculator->dataNumber, return -1, "More data for calculator support");
TRIGGER_CHECK(sizeof(char) == calculator->dataUnit, return -1, "More data for calculator support");
PARAM_CHECK(calculator != NULL, return -1, "Invalid param");
PARAM_CHECK(calculator->endIndex < calculator->dataNumber, return -1, "More data for calculator support");
PARAM_CHECK(sizeof(char) == calculator->dataUnit, return -1, "More data for calculator support");
calculator->data[calculator->endIndex++] = data;
return 0;
}
static int CalculatorPopChar(LogicCalculator *calculator, char *data)
{
TRIGGER_CHECK(calculator != NULL, return -1, "Invalid param");
TRIGGER_CHECK(calculator->endIndex < calculator->dataNumber, return -1, "More data for calculator support");
PARAM_CHECK(calculator != NULL, return -1, "Invalid param");
PARAM_CHECK(calculator->endIndex < calculator->dataNumber, return -1, "More data for calculator support");
if (calculator->endIndex == 0) {
return -1;
}
......@@ -80,32 +81,32 @@ static int CalculatorPopChar(LogicCalculator *calculator, char *data)
static int CalculatorPush(LogicCalculator *calculator, void *data)
{
TRIGGER_CHECK(calculator != NULL, return -1, "Invalid param");
TRIGGER_CHECK(calculator->endIndex < calculator->dataNumber, return -1, "More data for calculator support");
PARAM_CHECK(calculator != NULL, return -1, "Invalid param");
PARAM_CHECK(calculator->endIndex < calculator->dataNumber, return -1, "More data for calculator support");
char *tmpData = (calculator->data + calculator->dataUnit * calculator->endIndex);
int ret = memcpy_s(tmpData, calculator->dataUnit, data, calculator->dataUnit);
TRIGGER_CHECK(ret == 0, return -1, "Failed to copy logic data");
PARAM_CHECK(ret == 0, return -1, "Failed to copy logic data");
calculator->endIndex++;
return 0;
}
static int CalculatorPop(LogicCalculator *calculator, void *data)
{
TRIGGER_CHECK(calculator != NULL || data == NULL, return -1, "Invalid param");
TRIGGER_CHECK(calculator->endIndex < calculator->dataNumber, return -1, "More data for calculator support");
PARAM_CHECK(calculator != NULL || data == NULL, return -1, "Invalid param");
PARAM_CHECK(calculator->endIndex < calculator->dataNumber, return -1, "More data for calculator support");
if (calculator->endIndex == 0) {
return -1;
}
char *tmpData = calculator->data + calculator->dataUnit * (calculator->endIndex - 1);
int ret = memcpy_s(data, calculator->dataUnit, tmpData, calculator->dataUnit);
TRIGGER_CHECK(ret == 0, return -1, "Failed to copy logic data");
PARAM_CHECK(ret == 0, return -1, "Failed to copy logic data");
calculator->endIndex--;
return 0;
}
static int CalculatorLength(const LogicCalculator *calculator)
{
TRIGGER_CHECK(calculator != NULL, return 0, "Invalid param");
PARAM_CHECK(calculator != NULL, return 0, "Invalid param");
return calculator->endIndex;
}
......@@ -134,7 +135,7 @@ static int HandleOperationOr(LogicCalculator *calculator, char *prefix, u_int32_
CalculatorPushChar(calculator, e);
} else {
ret = PrefixAdd(prefix, prefixIndex, prefixLen, e);
TRIGGER_CHECK(ret == 0, return -1, "Invalid prefix");
PARAM_CHECK(ret == 0, return -1, "Invalid prefix");
}
} while (CalculatorLength(calculator) > 0 && e != '(');
CalculatorPushChar(calculator, '|');
......@@ -150,13 +151,10 @@ static int ComputeSubCondition(LogicCalculator *calculator, LogicData *data, con
// 解析条件
int ret = GetValueFromContent(condition + data->startIndex,
data->endIndex - data->startIndex, 0, calculator->conditionName, SUPPORT_DATA_BUFFER_MAX);
TRIGGER_CHECK(ret == 0, return -1, "Failed parse content name");
PARAM_CHECK(ret == 0, return -1, "Failed parse content name");
ret = GetValueFromContent(condition + data->startIndex, data->endIndex - data->startIndex,
strlen(calculator->conditionName) + 1, calculator->conditionContent, SUPPORT_DATA_BUFFER_MAX);
TRIGGER_CHECK(ret == 0, return -1, "Failed parse content value");
TRIGGER_LOGI("ComputeSubCondition subcondition \'%s\' \'%s\'",
calculator->conditionName, calculator->conditionContent);
PARAM_CHECK(ret == 0, return -1, "Failed parse content value");
// check name
if (strcmp(calculator->conditionName, calculator->inputName) == 0) {
if (strcmp(calculator->conditionContent, "*") == 0) {
......@@ -165,13 +163,13 @@ static int ComputeSubCondition(LogicCalculator *calculator, LogicData *data, con
if (strcmp(calculator->conditionContent, calculator->inputContent) == 0) {
return 1;
}
} else {
}/* else {
u_int32_t len = SUPPORT_DATA_BUFFER_MAX;
ret = SystemReadParameter(calculator->conditionName, calculator->readContent, &len);
ret = SystemReadParam(calculator->conditionName, calculator->readContent, &len);
if (ret == 0 && strcmp(calculator->conditionContent, calculator->readContent) == 0) {
return 1;
}
}
}*/
return 0;
}
......@@ -210,7 +208,7 @@ int ComputeCondition(LogicCalculator *calculator, const char *condition)
noneOper = 0;
int ret = CalculatorPop(calculator, (void*)&data2);
ret |= CalculatorPop(calculator, (void*)&data1);
TRIGGER_CHECK(ret == 0, return -1, "Failed to pop data");
PARAM_CHECK(ret == 0, return -1, "Failed to pop data");
ret = ComputeSubCondition(calculator, &data1, condition);
data1.flags = 0;
......@@ -222,7 +220,7 @@ int ComputeCondition(LogicCalculator *calculator, const char *condition)
}
}
ret = CalculatorPush(calculator, (void*)&data1);
TRIGGER_CHECK(ret == 0, return -1, "Failed to push data");
PARAM_CHECK(ret == 0, return -1, "Failed to push data");
start = currIndex + 1; // 跳过符号
} else if (isspace(condition[currIndex])) {
if (start == currIndex) {
......@@ -233,7 +231,7 @@ int ComputeCondition(LogicCalculator *calculator, const char *condition)
data1.startIndex = start;
data1.endIndex = currIndex;
int ret = CalculatorPush(calculator, (void*)&data1);
TRIGGER_CHECK(ret == 0, return -1, "Failed to push data");
PARAM_CHECK(ret == 0, return -1, "Failed to push data");
start = currIndex + 1;
}
currIndex++;
......@@ -244,7 +242,7 @@ int ComputeCondition(LogicCalculator *calculator, const char *condition)
data1.endIndex = strlen(condition);
} else {
int ret = CalculatorPop(calculator, &data1);
TRIGGER_CHECK(ret == 0, return -1, "Invalid calculator");
PARAM_CHECK(ret == 0, return -1, "Invalid calculator");
}
return ComputeSubCondition(calculator, &data1, condition);
}
......@@ -263,17 +261,17 @@ int ConvertInfixToPrefix(const char *condition, char *prefix, u_int32_t prefixLe
CalculatorPopChar(&calculator, &e);
while (e != '(') {
ret = PrefixAdd(prefix, &prefixIndex, prefixLen, e);
TRIGGER_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Invalid prefix");
PARAM_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Invalid prefix");
ret = CalculatorPopChar(&calculator, &e);
TRIGGER_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Invalid calculator");
PARAM_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Invalid calculator");
}
} else if (condition[curr] == '|') {
TRIGGER_CHECK(condition[curr + 1] == '|', CalculatorFree(&calculator); return -1, "Invalid condition");
PARAM_CHECK(condition[curr + 1] == '|', CalculatorFree(&calculator); return -1, "Invalid condition");
ret = HandleOperationOr(&calculator, prefix, &prefixIndex, prefixLen);
TRIGGER_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Invalid prefix");
PARAM_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Invalid prefix");
curr++;
} else if (condition[curr] == '&') {
TRIGGER_CHECK(condition[curr + 1] == '&', CalculatorFree(&calculator); return -1, "Invalid condition");
PARAM_CHECK(condition[curr + 1] == '&', CalculatorFree(&calculator); return -1, "Invalid condition");
prefix[prefixIndex++] = ' ';
CalculatorPushChar(&calculator, condition[curr]);
curr++;
......@@ -283,13 +281,13 @@ int ConvertInfixToPrefix(const char *condition, char *prefix, u_int32_t prefixLe
prefix[prefixIndex++] = condition[curr];
}
curr++;
TRIGGER_CHECK(prefixIndex < prefixLen, CalculatorFree(&calculator); return -1, "Invalid prefixIndex");
PARAM_CHECK(prefixIndex < prefixLen, CalculatorFree(&calculator); return -1, "Invalid prefixIndex");
}
while (CalculatorLength(&calculator) > 0) {
CalculatorPopChar(&calculator, &e);
ret = PrefixAdd(prefix, &prefixIndex, prefixLen, e);
TRIGGER_CHECK(ret == 0, CalculatorFree(&calculator);
PARAM_CHECK(ret == 0, CalculatorFree(&calculator);
return -1, "Invalid prefix %u %u", prefixIndex, prefixLen);
}
prefix[prefixIndex] = '\0';
......
......@@ -30,6 +30,7 @@
#include "init_utils.h"
#include "trigger_checker.h"
#define LABEL "Trigger"
#define TRIGGER_AREA_SPACE 1024*64
#define TRIGGER_EXECUTE_QUEUE 64
#define BUFFER_SIZE 256
......@@ -44,18 +45,18 @@
int InitTriggerWorkSpace(TriggerWorkSpace *workSpace)
{
TRIGGER_CHECK(workSpace != NULL, return -1, "Invalid parm");
PARAM_CHECK(workSpace != NULL, return -1, "Invalid parm");
if (workSpace->area != NULL) {
return 0;
}
CheckAndCreateDir(TRIGGER_PATH);
int fd = open(TRIGGER_PATH, O_CREAT | O_RDWR | O_TRUNC | O_CLOEXEC, 0444);
TRIGGER_CHECK(fd >= 0, return -1, "Open file fail error %s", strerror(errno));
PARAM_CHECK(fd >= 0, return -1, "Open file fail error %s", strerror(errno));
lseek(fd, TRIGGER_AREA_SPACE, SEEK_SET);
write(fd, "", 1);
void *areaAddr = (void *)mmap(NULL, TRIGGER_AREA_SPACE, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
TRIGGER_CHECK(areaAddr != MAP_FAILED, close(fd); return -1,
PARAM_CHECK(areaAddr != MAP_FAILED, close(fd); return -1,
"Failed to map memory error %s", strerror(errno));
close(fd);
......@@ -84,30 +85,29 @@ static CommandNode *GetCmdByIndex(TriggerWorkSpace *workSpace, TriggerNode *trig
return NULL;
}
u_int32_t size = sizeof(CommandNode) + 2;
TRIGGER_CHECK((index + size) < workSpace->area->dataSize,
PARAM_CHECK((index + size) < workSpace->area->dataSize,
return NULL, "Invalid index for cmd %u", index);
return (CommandNode *)(workSpace->area->data + index);
}
static u_int32_t AddCommand(TriggerWorkSpace *workSpace, TriggerNode *trigger, const char *cmdName, const char *content)
{
TRIGGER_CHECK(workSpace != NULL && trigger != NULL, return 0, "list is null");
TRIGGER_CHECK(content != NULL, return 0, "command is null");
PARAM_CHECK(workSpace != NULL && trigger != NULL, return 0, "list is null");
u_int32_t size = sizeof(CommandNode) + strlen(cmdName) + 1;
size += (content == NULL) ? 1 : strlen(content) + 1;
TRIGGER_CHECK((workSpace->area->currOffset + size) < workSpace->area->dataSize,
PARAM_CHECK((workSpace->area->currOffset + size) < workSpace->area->dataSize,
return 0, "Not enough memory for cmd %u %u", size, workSpace->area->currOffset);
CommandNode *node = (CommandNode *)(workSpace->area->data + workSpace->area->currOffset);
TRIGGER_CHECK(node != NULL, return 0, "Failed to alloc memory for command");
PARAM_CHECK(node != NULL, return 0, "Failed to alloc memory for command");
int ret = memcpy_s(node->name, sizeof(node->name) - 1, cmdName, strlen(cmdName));
TRIGGER_CHECK(ret == 0, return 0, "Failed to copy command");
PARAM_CHECK(ret == 0, return 0, "Failed to copy command");
node->name[strlen(cmdName)] = '\0';
if (content != NULL) {
ret = memcpy_s(node->content, size, content, strlen(content));
node->content[strlen(content)] = '\0';
TRIGGER_CHECK(ret == 0, return 0, "Failed to copy command");
PARAM_CHECK(ret == 0, return 0, "Failed to copy command");
} else {
node->content[0] = '\0';
}
......@@ -135,36 +135,36 @@ static TriggerNode *GetTriggerByIndex(TriggerWorkSpace *workSpace, u_int32_t ind
return NULL;
}
u_int32_t size = sizeof(TriggerNode) + 1;
TRIGGER_CHECK((index + size) < workSpace->area->dataSize,
PARAM_CHECK((index + size) < workSpace->area->dataSize,
return NULL, "Invalid index for trigger %u", index);
return (TriggerNode *)(workSpace->area->data + index);
}
static u_int32_t AddTrigger(TriggerWorkSpace *workSpace, int type, const char *name, const char *condition)
{
TRIGGER_CHECK(workSpace != NULL && name != NULL, return 0, "list is null");
PARAM_CHECK(workSpace != NULL && name != NULL, return 0, "list is null");
const char *tmpCond = condition;
if (type == TRIGGER_BOOT && condition == NULL) {
tmpCond = name;
}
u_int32_t conditionSize = (tmpCond == NULL) ? 1 : strlen(tmpCond) + 1 + CONDITION_EXTEND_LEN;
TRIGGER_CHECK((workSpace->area->currOffset + sizeof(TriggerNode) + conditionSize) < workSpace->area->dataSize,
PARAM_CHECK((workSpace->area->currOffset + sizeof(TriggerNode) + conditionSize) < workSpace->area->dataSize,
return -1, "Not enough memory for cmd");
TriggerNode *node = (TriggerNode *)(workSpace->area->data + workSpace->area->currOffset);
TRIGGER_CHECK(node != NULL, return 0, "Failed to alloc memory for trigger");
PARAM_CHECK(node != NULL, return 0, "Failed to alloc memory for trigger");
node->type = type;
int ret = memcpy_s(node->name, sizeof(node->name) - 1, name, strlen(name));
TRIGGER_CHECK(ret == 0, return 0, "Failed to memcpy_s for trigger");
PARAM_CHECK(ret == 0, return 0, "Failed to memcpy_s for trigger");
node->name[strlen(name)] = '\0';
if (tmpCond != NULL) {
if (type == TRIGGER_PROPERTY) {
ret = ConvertInfixToPrefix(tmpCond, node->condition, conditionSize);
TRIGGER_CHECK(ret == 0, return 0, "Failed to memcpy_s for trigger");
PARAM_CHECK(ret == 0, return 0, "Failed to memcpy_s for trigger");
} else {
ret = memcpy_s(node->condition, strlen(tmpCond) + 1, tmpCond, strlen(tmpCond));
TRIGGER_CHECK(ret == 0, return 0, "Failed to memcpy_s for trigger");
PARAM_CHECK(ret == 0, return 0, "Failed to memcpy_s for trigger");
node->condition[strlen(tmpCond)] = '\0';
}
} else {
......@@ -194,22 +194,22 @@ static u_int32_t AddTrigger(TriggerWorkSpace *workSpace, int type, const char *n
static int GetTriggerIndex(const char *type)
{
if (strncmp("property", type, strlen("property")) == 0) {
if (strncmp("param", type, strlen("param")) == 0) {
return TRIGGER_PROPERTY;
}
static const char *triggerType[] = {
"boot", "early-init", "init", "early-init", "late-init",
"pre-init", "boot", "early-init", "init", "early-init", "late-init", "post-init",
"early-fs", "post-fs", "late-fs", "post-fs-data",
"nonencrypted",
"firmware_mounts_complete",
"load_persist_props_action"
"load_persist_params_action"
};
for (size_t i = 0; i < sizeof(triggerType) / sizeof(char*); i++) {
if (strncmp(triggerType[i], type, strlen(triggerType[i])) == 0) {
return TRIGGER_BOOT;
}
}
return TRIGGER_UNKNOW;
return TRIGGER_BOOT;
}
static int CheckBootTriggerMatch(TriggerNode *trigger, void *content, u_int32_t contentSize)
......@@ -222,53 +222,61 @@ static int CheckBootTriggerMatch(TriggerNode *trigger, void *content, u_int32_t
int ParseTrigger(TriggerWorkSpace *workSpace, cJSON *triggerItem)
{
TRIGGER_CHECK(triggerItem != NULL, return -1, "Invalid file");
TRIGGER_CHECK(workSpace != NULL, return -1, "Failed to create trigger list");
PARAM_CHECK(triggerItem != NULL, return -1, "Invalid file");
PARAM_CHECK(workSpace != NULL, return -1, "Failed to create trigger list");
char *name = cJSON_GetStringValue(cJSON_GetObjectItem(triggerItem, "name"));
TRIGGER_CHECK(name != NULL, return -1, "Can not get name from cfg");
PARAM_CHECK(name != NULL, return -1, "Can not get name from cfg");
char *condition = cJSON_GetStringValue(cJSON_GetObjectItem(triggerItem, "condition"));
int index = GetTriggerIndex(name);
TRIGGER_CHECK(CHECK_INDEX_VALID(workSpace, index), return -1, "Failed to get trigger index");
u_int32_t offset = AddTrigger(workSpace, index, name, condition);
//TRIGGER_LOGE("AddTrigger %u %s %u", offset, name, workSpace->area->currOffset);
TRIGGER_CHECK(offset > 0, return -1, "Failed to create trigger %s", name);
TriggerNode *trigger = GetTriggerByIndex(workSpace, offset);
PARAM_CHECK(CHECK_INDEX_VALID(workSpace, index), return -1, "Failed to get trigger index");
u_int32_t offset = 0;
TriggerNode *trigger = GetTriggerByName(workSpace, name, &offset);
if (trigger == NULL) {
offset = AddTrigger(workSpace, index, name, condition);
PARAM_CHECK(offset > 0, return -1, "Failed to create trigger %s", name);
trigger = GetTriggerByIndex(workSpace, offset);
} else {
if (condition != NULL) {
PARAM_LOGE("Warning parseTrigger %s %s", name, condition);
}
}
PARAM_LOGE("ParseTrigger %s %u", name, offset);
// 添加命令行
cJSON* cmdItems = cJSON_GetObjectItem(triggerItem, CMDS_ARR_NAME_IN_JSON);
TRIGGER_CHECK(cJSON_IsArray(cmdItems), return -1, "Command item must be array");
PARAM_CHECK(cJSON_IsArray(cmdItems), return -1, "Command item must be array");
int cmdLinesCnt = cJSON_GetArraySize(cmdItems);
TRIGGER_CHECK(cmdLinesCnt > 0, return -1, "Command array size must positive");
PARAM_CHECK(cmdLinesCnt > 0, return -1, "Command array size must positive %s", name);
for (int i = 0; i < cmdLinesCnt; ++i) {
char *cmdLineStr = cJSON_GetStringValue(cJSON_GetArrayItem(cmdItems, i));
TRIGGER_CHECK(cmdLinesCnt > 0, continue, "Command is null");
PARAM_CHECK(cmdLinesCnt > 0, continue, "Command is null");
size_t cmdLineLen = strlen(cmdLineStr);
const char *matchCmd = GetMatchCmd(cmdLineStr);
if (matchCmd == NULL && strncmp(cmdLineStr, TRIGGER_CMD, strlen(TRIGGER_CMD)) == 0) {
matchCmd = TRIGGER_CMD;
}
TRIGGER_CHECK(matchCmd != NULL, continue, "Command not support %s", cmdLineStr);
PARAM_CHECK(matchCmd != NULL, continue, "Command not support %s", cmdLineStr);
size_t matchLen = strlen(matchCmd);
if (matchLen == cmdLineLen) {
offset = AddCommand(workSpace, trigger, matchCmd, NULL);
} else {
offset = AddCommand(workSpace, trigger, matchCmd, cmdLineStr + matchLen);
}
//TRIGGER_LOGE("AddCommand %u %s %u", offset, cmdLineStr, workSpace->area->currOffset);
TRIGGER_CHECK(offset > 0, continue, "Failed to add command %s", cmdLineStr);
//PARAM_LOGE("AddCommand %u %s %u", offset, cmdLineStr, workSpace->area->currOffset);
PARAM_CHECK(offset > 0, continue, "Failed to add command %s", cmdLineStr);
}
return 0;
}
int ExecuteTrigger(TriggerWorkSpace *workSpace, TriggerNode *trigger, CMD_EXECUTE cmdExecuter)
{
TRIGGER_CHECK(workSpace != NULL && trigger != NULL && cmdExecuter != NULL, return -1, "Invalid param");
TRIGGER_LOGI("ExecuteCmds trigger %s", trigger->name);
PARAM_CHECK(workSpace != NULL && trigger != NULL && cmdExecuter != NULL, return -1, "Invalid param");
PARAM_LOGI("ExecuteCmds trigger %s", trigger->name);
CommandNode *cmd = GetCmdByIndex(workSpace, trigger, trigger->firstCmd);
while (cmd != NULL) {
cmdExecuter(trigger, cmd->name, cmd->content);
......@@ -279,7 +287,7 @@ int ExecuteTrigger(TriggerWorkSpace *workSpace, TriggerNode *trigger, CMD_EXECUT
int ExecuteQueuePush(TriggerWorkSpace *workSpace, TriggerNode *trigger, u_int32_t triggerIndex)
{
TRIGGER_CHECK(workSpace != NULL, return -1, "Invalid area");
PARAM_CHECK(workSpace != NULL, return -1, "Invalid area");
pthread_mutex_lock(&workSpace->executeQueue.mutex);
u_int32_t index = workSpace->executeQueue.endIndex++ % workSpace->executeQueue.queueCount;
workSpace->executeQueue.executeQueue[index] = triggerIndex;
......@@ -303,22 +311,22 @@ TriggerNode *ExecuteQueuePop(TriggerWorkSpace *workSpace)
int ExecuteQueueSize(TriggerWorkSpace *workSpace)
{
TRIGGER_CHECK(workSpace != NULL, return 0, "Invalid param");
PARAM_CHECK(workSpace != NULL, return 0, "Invalid param");
return workSpace->executeQueue.endIndex - workSpace->executeQueue.startIndex;
}
int CheckTrigger(TriggerWorkSpace *workSpace,
int type, void *content, u_int32_t contentSize, TRIGGER_CHECK_DONE triggerExecuter)
int type, void *content, u_int32_t contentSize, PARAM_CHECK_DONE triggerExecuter)
{
static TRIGGER_MATCH triggerCheckMatch[TRIGGER_MAX] = {
CheckBootTriggerMatch, NULL, NULL
};
TRIGGER_LOGI("ExecuteTrigger check content %s", (char*)content);
TRIGGER_CHECK(workSpace != NULL, return -1, "Trigger not init");
TRIGGER_CHECK(CHECK_INDEX_VALID(workSpace, type), return -1, "Invalid type %d", type);
TRIGGER_CHECK((u_int32_t)type < sizeof(triggerCheckMatch) / sizeof(triggerCheckMatch[0]),
PARAM_LOGI("ExecuteTrigger check content %s", (char*)content);
PARAM_CHECK(workSpace != NULL, return -1, "Trigger not init");
PARAM_CHECK(CHECK_INDEX_VALID(workSpace, type), return -1, "Invalid type %d", type);
PARAM_CHECK((u_int32_t)type < sizeof(triggerCheckMatch) / sizeof(triggerCheckMatch[0]),
return -1, "Failed to get check function");
TRIGGER_CHECK(triggerCheckMatch[type] != NULL, return 0, "Failed to get check function");
PARAM_CHECK(triggerCheckMatch[type] != NULL, return 0, "Failed to get check function");
u_int32_t index = workSpace->header[type].firstTrigger;
TriggerNode *trigger = GetTriggerByIndex(workSpace, workSpace->header[type].firstTrigger);
while (trigger != NULL) {
......@@ -331,26 +339,25 @@ int CheckTrigger(TriggerWorkSpace *workSpace,
return 0;
}
int CheckPropertyTrigger(TriggerWorkSpace *workSpace,
const char *content, u_int32_t contentSize, TRIGGER_CHECK_DONE triggerExecuter)
int CheckParamTrigger(TriggerWorkSpace *workSpace,
const char *content, u_int32_t contentSize, PARAM_CHECK_DONE triggerExecuter)
{
TRIGGER_CHECK(workSpace != NULL && content != NULL && triggerExecuter != NULL,
return -1, "Failed arg for property trigger");
PARAM_CHECK(workSpace != NULL && content != NULL && triggerExecuter != NULL,
return -1, "Failed arg for param trigger");
LogicCalculator calculator;
CalculatorInit(&calculator, 100, sizeof(LogicData), 1);
// 先解析content
int ret = GetValueFromContent(content, contentSize, 0, calculator.inputName, SUPPORT_DATA_BUFFER_MAX);
TRIGGER_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Failed parse content name");
PARAM_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Failed parse content name");
ret = GetValueFromContent(content, contentSize,
strlen(calculator.inputName) + 1, calculator.inputContent, SUPPORT_DATA_BUFFER_MAX);
TRIGGER_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Failed parse content value");
TRIGGER_LOGI("CheckPropertyTrigger content %s ", content);
PARAM_CHECK(ret == 0, CalculatorFree(&calculator); return -1, "Failed parse content value");
PARAM_LOGI("CheckParamTrigger content %s ", content);
u_int32_t index = workSpace->header[TRIGGER_PROPERTY].firstTrigger;
TriggerNode *trigger = GetTriggerByIndex(workSpace, workSpace->header[TRIGGER_PROPERTY].firstTrigger);
while (trigger != NULL) {
TRIGGER_LOGI("CheckPropertyTrigger name:%s condition \'%s\' ", trigger->name, trigger->condition);
ret = ComputeCondition(&calculator, trigger->condition);
if (ret == 1) {
triggerExecuter(trigger, index);
......@@ -364,7 +371,7 @@ int CheckPropertyTrigger(TriggerWorkSpace *workSpace,
TriggerNode *GetTriggerByName(TriggerWorkSpace *workSpace, const char *triggerName, u_int32_t *triggerIndex)
{
TRIGGER_CHECK(workSpace != NULL && triggerName != NULL, return NULL, "Invalid param");
PARAM_CHECK(workSpace != NULL && triggerName != NULL, return NULL, "Invalid param");
for (size_t i = 0; i < sizeof(workSpace->header) / sizeof(workSpace->header[0]); i++) {
u_int32_t index = workSpace->header[i].firstTrigger;
TriggerNode *trigger = GetTriggerByIndex(workSpace, workSpace->header[i].firstTrigger);
......
......@@ -18,70 +18,59 @@
#include <unistd.h>
#include "init_cmds.h"
#include "property_manager.h"
#include "param_manager.h"
#include "trigger_checker.h"
#include "uv.h"
#define LABEL "Trigger"
#define SYS_POWER_CTRL "sys.powerctrl."
static int g_triggerServiceStart = 0;
static TriggerWorkSpace g_triggerWorkSpace = {};
static int DoCmdExecute(TriggerNode *trigger, const char *cmdName, const char *command)
{
TRIGGER_CHECK(trigger != NULL && cmdName != NULL && command != NULL, return -1, "Invalid param");
PARAM_CHECK(trigger != NULL && cmdName != NULL && command != NULL, return -1, "Invalid param");
if (strncmp(cmdName, TRIGGER_CMD, strlen(TRIGGER_CMD)) == 0) {
u_int32_t triggerIndex = 0;
TriggerNode *node = GetTriggerByName(&g_triggerWorkSpace, command, &triggerIndex);
if (node != NULL && !TRIGGER_NODE_IN_QUEUE(node)) { // 不在队列中
TRIGGER_LOGI("DoCmdExecute trigger %s", node->name);
PARAM_LOGI("DoCmdExecute trigger %s", node->name);
TRIGGER_NODE_SET_QUEUE_FLAG(node);
ExecuteQueuePush(&g_triggerWorkSpace, node, triggerIndex);
}
return 0;
}
TRIGGER_LOGI("DoCmdExecute trigger %s cmd %s", trigger->name, cmdName);
PARAM_LOGI("DoCmdExecute trigger %s cmd %s %s", trigger->name, cmdName, command);
DoCmdByName(cmdName, command);
return 0;
}
static int DoTiggerCheckResult(TriggerNode *trigger, u_int32_t triggerIndex)
{
// 直接执行,不需要添加队列
if (!g_triggerServiceStart) {
TRIGGER_LOGI("DoTiggerExecute trigger %s", trigger->name);
ExecuteTrigger(&g_triggerWorkSpace, trigger, DoCmdExecute);
TRIGGER_NODE_CLEAR_QUEUE_FLAG(trigger);
}
// 已经在队列中了,则不执行 TODO
if (TRIGGER_NODE_IN_QUEUE(trigger)) {
TRIGGER_LOGI("DoTiggerExecute trigger %s has been waiting execute", trigger->name);
PARAM_LOGI("DoTiggerExecute trigger %s has been waiting execute", trigger->name);
return 0;
}
if (trigger->type == TRIGGER_BOOT) { // 立刻执行
TRIGGER_LOGI("DoTiggerExecute trigger %s", trigger->name);
ExecuteTrigger(&g_triggerWorkSpace, trigger, DoCmdExecute);
TRIGGER_NODE_CLEAR_QUEUE_FLAG(trigger);
} else {
TRIGGER_NODE_SET_QUEUE_FLAG(trigger);
TRIGGER_LOGI("DoTiggerExecute trigger %s", trigger->name);
ExecuteQueuePush(&g_triggerWorkSpace, trigger, triggerIndex);
}
TRIGGER_NODE_SET_QUEUE_FLAG(trigger);
PARAM_LOGI("Waiting to exec trigger %s", trigger->name);
ExecuteQueuePush(&g_triggerWorkSpace, trigger, triggerIndex);
return 0;
}
void ExecuteQueueWork()
void ExecuteQueueWork(u_int32_t maxCount)
{
int executeCount = 0;
PARAM_LOGI("ExecuteQueueWork %d %d", getpid(), gettid());
u_int32_t executeCount = 0;
TriggerNode *trigger = ExecuteQueuePop(&g_triggerWorkSpace);
while (trigger != NULL) {
ExecuteTrigger(&g_triggerWorkSpace, trigger, DoCmdExecute);
TRIGGER_NODE_CLEAR_QUEUE_FLAG(trigger);
executeCount++;
if (executeCount > 5) {
if (executeCount > maxCount) {
break;
}
PARAM_LOGI("ExecuteQueueWork %u", executeCount);
trigger = ExecuteQueuePop(&g_triggerWorkSpace);
}
}
......@@ -90,7 +79,7 @@ static void CheckTriggers(int type, void *content, u_int32_t contentLen)
{
switch (type) {
case EVENT_PROPERTY: {
CheckPropertyTrigger(&g_triggerWorkSpace, content, contentLen, DoTiggerCheckResult);
CheckParamTrigger(&g_triggerWorkSpace, content, contentLen, DoTiggerCheckResult);
break;
}
case EVENT_BOOT: {
......@@ -98,7 +87,7 @@ static void CheckTriggers(int type, void *content, u_int32_t contentLen)
break;
}
default:
TRIGGER_LOGI("CheckTriggers: %d", type);
PARAM_LOGI("CheckTriggers: %d", type);
break;
}
}
......@@ -106,7 +95,7 @@ static void CheckTriggers(int type, void *content, u_int32_t contentLen)
static void ProcessAfterEvent(uv_work_t *req, int status)
{
free(req);
ExecuteQueueWork();
ExecuteQueueWork(UINT32_MAX);
}
static void ProcessEvent(uv_work_t *req)
......@@ -119,12 +108,12 @@ static const char *GetCmdInfo(const char *content, u_int32_t contentSize, char *
{
char cmd[MAX_CMD_NAME_LEN + 1] = { 0 };
int ret = GetValueFromContent(content, contentSize, 0, cmd, sizeof(cmd));
TRIGGER_CHECK(ret == 0, return NULL, "Failed parse cmd");
PARAM_CHECK(ret == 0, return NULL, "Failed parse cmd");
u_int32_t cmdLen = strlen(cmd);
TRIGGER_CHECK(cmdLen < MAX_CMD_NAME_LEN, return NULL, "Failed parse cmd");
PARAM_CHECK(cmdLen < MAX_CMD_NAME_LEN, return NULL, "Failed parse cmd");
cmd[cmdLen] = ' ';
cmd[cmdLen + 1] = '\0';
*cmdParam = content + cmdLen + 1;
*cmdParam = (char *)content + cmdLen + 1;
return GetMatchCmd(cmd);
}
......@@ -137,70 +126,68 @@ static void SendTriggerEvent(TriggerDataEvent *event)
if (matchCmd != NULL) {
DoCmdByName(matchCmd, cmdParam);
} else {
TRIGGER_LOGE("SendTriggerEvent cmd %s not found", event->content);
PARAM_LOGE("SendTriggerEvent cmd %s not found", event->content);
}
free(event);
return;
}
if (event->type == EVENT_BOOT || g_triggerServiceStart == 0) {
CheckTriggers(EVENT_PROPERTY, event->content, event->contentSize);
free(event);
else if (event->type == EVENT_BOOT || g_triggerServiceStart == 0) {
CheckTriggers(event->type, event->content, event->contentSize);
ExecuteQueueWork(UINT32_MAX); // 需要立刻执行
} else {
uv_queue_work(uv_default_loop(), &event->request, ProcessEvent, ProcessAfterEvent);
event = NULL;
}
if (event != NULL) {
free(event);
}
}
void PostPropertyTrigger(const char *name, const char *value)
void PostParamTrigger(const char *name, const char *value)
{
TRIGGER_CHECK(name != NULL && value != NULL, return, "Invalid param");
TRIGGER_LOGI("PostPropertyTrigger %s ", name);
PARAM_CHECK(name != NULL && value != NULL, return, "Invalid param");
PARAM_LOGI("PostParamTrigger %s ", name);
int contentLen = strlen(name) + strlen(value) + 2;
TriggerDataEvent *event = (TriggerDataEvent *)malloc(sizeof(TriggerDataEvent) + contentLen);
TRIGGER_CHECK(event != NULL, return, "Failed to alloc memory");
PARAM_CHECK(event != NULL, return, "Failed to alloc memory");
event->type = EVENT_PROPERTY;
event->request.data = (char*)event + sizeof(uv_work_t);
event->contentSize = BuildPropertyContent(event->content, contentLen, name, value);
TRIGGER_CHECK(event->contentSize > 0, return, "Failed to copy porperty");
event->contentSize = BuildParamContent(event->content, contentLen, name, value);
PARAM_CHECK(event->contentSize > 0, return, "Failed to copy porperty");
SendTriggerEvent(event);
TRIGGER_LOGI("PostPropertyTrigger %s success", name);
PARAM_LOGI("PostParamTrigger %s success", name);
}
void PostTrigger(EventType type, void *content, u_int32_t contentLen)
{
TRIGGER_LOGI("PostTrigger %d", type);
TRIGGER_CHECK(content != NULL && contentLen > 0, return, "Invalid param");
if (type == EVENT_BOOT || g_triggerServiceStart == 0) {
CheckTriggers(type, content, contentLen);
} else {
TriggerDataEvent *event = (TriggerDataEvent *)malloc(sizeof(TriggerDataEvent) + contentLen + 1);
TRIGGER_CHECK(event != NULL, return, "Failed to alloc memory");
event->type = type;
event->request.data = (char*)event + sizeof(uv_work_t);
event->contentSize = contentLen;
memcpy_s(event->content, contentLen, content, contentLen);
event->content[contentLen] = '\0';
SendTriggerEvent(event);
}
TRIGGER_LOGI("PostTrigger %d success", type);
PARAM_LOGI("PostTrigger %d", type);
PARAM_CHECK(content != NULL && contentLen > 0, return, "Invalid param");
TriggerDataEvent *event = (TriggerDataEvent *)malloc(sizeof(TriggerDataEvent) + contentLen + 1);
PARAM_CHECK(event != NULL, return, "Failed to alloc memory");
event->type = type;
event->request.data = (char*)event + sizeof(uv_work_t);
event->contentSize = contentLen;
memcpy_s(event->content, contentLen, content, contentLen);
event->content[contentLen] = '\0';
SendTriggerEvent(event);
PARAM_LOGI("PostTrigger %d success", type);
}
void StartTriggerService()
{
TRIGGER_LOGI("StartTriggerService ");
PARAM_LOGI("StartTriggerService ");
g_triggerServiceStart = 1;
}
int ParseTriggerConfig(cJSON *fileRoot)
{
TRIGGER_CHECK(fileRoot != NULL, return -1, "Invalid file");
PARAM_CHECK(fileRoot != NULL, return -1, "Invalid file");
int ret = InitTriggerWorkSpace(&g_triggerWorkSpace);
TRIGGER_CHECK(ret == 0, return -1, "Failed to init trigger");
PARAM_CHECK(ret == 0, return -1, "Failed to init trigger");
cJSON *triggers = cJSON_GetObjectItemCaseSensitive(fileRoot, TRIGGER_ARR_NAME_IN_JSON);
TRIGGER_CHECK(cJSON_IsArray(triggers), return -1, "Trigger item must array");
PARAM_CHECK(cJSON_IsArray(triggers), return -1, "Trigger item must array");
int size = cJSON_GetArraySize(triggers);
TRIGGER_CHECK(size > 0, return -1, "Trigger array size must positive");
PARAM_CHECK(size > 0, return -1, "Trigger array size must positive");
for (int i = 0; i < size; ++i) {
cJSON *item = cJSON_GetArrayItem(triggers, i);
......@@ -211,12 +198,15 @@ int ParseTriggerConfig(cJSON *fileRoot)
void DoTriggerExec(const char *content)
{
TRIGGER_CHECK(content != NULL, return, "Invalid trigger content");
PARAM_CHECK(content != NULL, return, "Invalid trigger content");
u_int32_t triggerIndex = 0;
TriggerNode *trigger = GetTriggerByName(&g_triggerWorkSpace, content, &triggerIndex);
if (trigger != NULL) {
ExecuteTrigger(&g_triggerWorkSpace, trigger, DoCmdExecute);
if (trigger != NULL && !TRIGGER_NODE_IN_QUEUE(trigger)) { // 不在队列中
PARAM_LOGI("DoTriggerExec trigger %s", trigger->name);
TRIGGER_NODE_SET_QUEUE_FLAG(trigger);
ExecuteQueuePush(&g_triggerWorkSpace, trigger, triggerIndex);
}
ExecuteQueueWork(UINT32_MAX); // 需要立刻执行
}
TriggerWorkSpace *GetTriggerWorkSpace()
......
# Copyright (c) 2020 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.
import("//build/ohos.gni")
ohos_executable("reboot") {
sources = [
"init_cmd_reboot.c",
]
include_dirs = [
"//base/startup/init_lite/interfaces/innerkits/include",
"//base/startup/init_lite/services/include/param/",
"//third_party/bounds_checking_function/include",
]
deps = [
"//base/startup/init_lite/interfaces/innerkits/reboot:libreboot",
]
install_enable = true
part_name = "init"
}
/*
* 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 <stdio.h>
#include <string.h>
#include <unistd.h>
#include "init_reboot_api.h"
int main(int argc, char* argv[])
{
if (argc > 2) {
printf("usage: reboot shutdown\n reboot updater\n reboot updater[:options]\n reboot\n");
return 0;
}
if (argc == 2 && strcmp(argv[1], "shutdown") != 0 &&
strcmp(argv[1], "updater") != 0 &&
strncmp(argv[1], "updater:", strlen("updater:")) != 0 ) {
printf("usage: reboot shutdown\n reboot updater\n reboot updater[:options]\n reboot\n");
return 0;
}
int ret = 0;
if (argc == 2) {
ret = DoRebootApi(argv[1]);
} else {
ret = DoRebootApi("NoArgument");
}
if (ret != 0) {
printf("[reboot command] DoRebootApi return error\n");
} else {
printf("[reboot command] DoRebootApi return ok\n");
}
while (1) {
pause();
}
return 0;
}
......@@ -19,6 +19,8 @@
#include <sys/mount.h>
#include <sys/stat.h>
#include <sys/sysmacros.h>
#include <unistd.h>
#include "init_log.h"
#define DEFAULT_RW_MODE 0666
#define DEFAULT_NO_AUTHORITY_MODE 0600
......@@ -30,17 +32,17 @@
void MountBasicFs()
{
if (mount("tmpfs", "/dev", "tmpfs", MS_NOSUID, "mode=0755") != 0) {
printf("Mount tmpfs failed. %s\n", strerror(errno));
INIT_LOGE("Mount tmpfs failed. %s\n", strerror(errno));
}
if (mount("proc", "/proc", "proc", 0, "hidepid=2") != 0) {
printf("Mount procfs failed. %s\n", strerror(errno));
INIT_LOGE("Mount procfs failed. %s\n", strerror(errno));
}
if (mount("sysfs", "/sys", "sysfs", 0, NULL) != 0) {
printf("Mount sysfs failed. %s\n", strerror(errno));
INIT_LOGE("Mount sysfs failed. %s\n", strerror(errno));
}
#ifndef __LITEOS__
if (mount("selinuxfs", "/sys/fs/selinux", "selinuxfs", 0, NULL) != 0) {
printf("Mount selinuxfs failed. %s\n", strerror(errno));
INIT_LOGE("Mount selinuxfs failed. %s\n", strerror(errno));
}
#endif
}
......@@ -48,17 +50,17 @@ void MountBasicFs()
void CreateDeviceNode()
{
if (mknod("/dev/kmsg", S_IFCHR | DEFAULT_NO_AUTHORITY_MODE, makedev(1, DEVICE_ID_ELEVNTH)) != 0) {
printf("Create /dev/kmsg device node failed. %s\n", strerror(errno));
INIT_LOGE("Create /dev/kmsg device node failed. %s\n", strerror(errno));
}
if (mknod("/dev/null", S_IFCHR | DEFAULT_RW_MODE, makedev(1, DEVICE_ID_THIRD)) != 0) {
printf("Create /dev/null device node failed. %s\n", strerror(errno));
INIT_LOGE("Create /dev/null device node failed. %s\n", strerror(errno));
}
if (mknod("/dev/random", S_IFCHR | DEFAULT_RW_MODE, makedev(1, DEVICE_ID_EIGHTH)) != 0) {
printf("Create /dev/random device node failed. %s\n", strerror(errno));
INIT_LOGE("Create /dev/random device node failed. %s\n", strerror(errno));
}
if (mknod("/dev/urandom", S_IFCHR | DEFAULT_RW_MODE, makedev(1, DEVICE_ID_NINTH)) != 0) {
printf("Create /dev/urandom device node failed. %s\n", strerror(errno));
INIT_LOGE("Create /dev/urandom device node failed. %s\n", strerror(errno));
}
}
......@@ -66,12 +68,12 @@ int MakeSocketDir(const char *path, mode_t mode)
{
int rc = mkdir("/dev/unix/", mode);
if (rc < 0 && errno != EEXIST) {
printf("Create %s failed. %d\n", path, errno);
INIT_LOGE("Create %s failed. %d\n", path, errno);
return -1;
}
rc = mkdir("/dev/unix/socket/", mode);
if (rc < 0 && errno != EEXIST) {
printf("Create %s failed. %d\n", path, errno);
INIT_LOGE("Create %s failed. %d\n", path, errno);
return -1;
}
return rc;
......
......@@ -26,12 +26,13 @@
#ifdef __LINUX__
#include "init_signal_handler.h"
#endif
#include "init_log.h"
void RebootSystem()
{
int ret = reboot(RB_AUTOBOOT);
if (ret != 0) {
printf("[Init] reboot failed! syscall ret %d, err %d.\n", ret, errno);
INIT_LOGE("reboot failed! syscall ret %d, err %d.\n", ret, errno);
}
}
......@@ -39,7 +40,7 @@ int KeepCapability()
{
#if ((defined __LINUX__) || (!defined OHOS_LITE))
if (prctl(PR_SET_SECUREBITS, SECBIT_NO_SETUID_FIXUP | SECBIT_NO_SETUID_FIXUP_LOCKED)) {
printf("[Init] prctl PR_SET_SECUREBITS failed: %d\n", errno);
INIT_LOGE("prctl PR_SET_SECUREBITS failed: %d\n", errno);
return -1;
}
#endif
......@@ -50,7 +51,7 @@ int SetAmbientCapability(int cap)
{
#if ((defined __LINUX__) || (!defined OHOS_LITE))
if (prctl(PR_CAP_AMBIENT, PR_CAP_AMBIENT_RAISE, cap, 0, 0)) {
printf("[Init] prctl PR_CAP_AMBIENT failed: %d\n", errno);
INIT_LOGE("prctl PR_CAP_AMBIENT failed: %d\n", errno);
return -1;
}
#endif
......@@ -62,15 +63,15 @@ void ExecuteRcs()
#if (defined __LINUX__) && (defined NEED_EXEC_RCS_LINUX)
pid_t retPid = fork();
if (retPid < 0) {
printf("[Init] ExecuteRcs, fork failed! err %d.\n", errno);
INIT_LOGE("ExecuteRcs, fork failed! err %d.\n", errno);
return;
}
// child process
if (retPid == 0) {
printf("[Init] ExecuteRcs, child process id %d.\n", getpid());
INIT_LOGI("ExecuteRcs, child process id %d.\n", getpid());
if (execle("/bin/sh", "sh", "/etc/init.d/rcS", NULL, NULL) != 0) {
printf("[Init] ExecuteRcs, execle failed! err %d.\n", errno);
INIT_LOGE("ExecuteRcs, execle failed! err %d.\n", errno);
}
_exit(0x7f); // 0x7f: user specified
}
......@@ -78,14 +79,14 @@ void ExecuteRcs()
// init process
sem_t sem;
if (sem_init(&sem, 0, 0) != 0) {
printf("[Init] ExecuteRcs, sem_init failed, err %d.\n", errno);
INIT_LOGE("ExecuteRcs, sem_init failed, err %d.\n", errno);
return;
}
SignalRegWaitSem(retPid, &sem);
// wait until rcs process exited
if (sem_wait(&sem) != 0) {
printf("[Init] ExecuteRcs, sem_wait failed, err %d.\n", errno);
INIT_LOGE("ExecuteRcs, sem_wait failed, err %d.\n", errno);
}
#endif
}
......
......@@ -38,7 +38,7 @@ struct CapStrCapNum {
int CapNum;
};
static struct CapStrCapNum g_capStrCapNum[] = {
static const struct CapStrCapNum g_capStrCapNum[] = {
{"CHOWN", CAP_CHOWN},
{"DAC_OVERRIDE", CAP_DAC_OVERRIDE},
{"DAC_READ_SEARCH", CAP_DAC_READ_SEARCH},
......@@ -85,7 +85,7 @@ static int GetServiceStringCaps(const cJSON* filedJ, Service* curServ)
for (; i < curServ->servPerm.capsCnt; ++i) {
if (cJSON_GetArrayItem(filedJ, i) == NULL || !cJSON_GetStringValue(cJSON_GetArrayItem(filedJ, i))
|| strlen(cJSON_GetStringValue(cJSON_GetArrayItem(filedJ, i))) <= 0) { // check all errors
INIT_LOGE("[Init] GetServiceStringCaps, parse item[%d] as string, error.\n", i);
INIT_LOGE("GetServiceStringCaps, parse item[%d] as string, error.\n", i);
break;
}
char* fieldStr = cJSON_GetStringValue(cJSON_GetArrayItem(filedJ, i));
......@@ -99,12 +99,12 @@ static int GetServiceStringCaps(const cJSON* filedJ, Service* curServ)
if (j < mapSize) {
curServ->servPerm.caps[i] = g_capStrCapNum[j].CapNum;
} else {
INIT_LOGE("[Init] GetServiceStringCaps, fieldStr = %s, error.\n", fieldStr);
INIT_LOGE("GetServiceStringCaps, fieldStr = %s, error.\n", fieldStr);
break;
}
if (curServ->servPerm.caps[i] > CAP_LAST_CAP && curServ->servPerm.caps[i] != FULL_CAP) {
// resources will be released by function: ReleaseServiceMem
INIT_LOGE("[Init] GetServiceStringCaps, cap = %d, error.\n", curServ->servPerm.caps[i]);
INIT_LOGE("GetServiceStringCaps, cap = %d, error.\n", curServ->servPerm.caps[i]);
return SERVICE_FAILURE;
}
}
......@@ -118,11 +118,11 @@ int GetServiceCaps(const cJSON* curArrItem, Service* curServ)
curServ->servPerm.caps = NULL;
cJSON* filedJ = cJSON_GetObjectItem(curArrItem, "caps");
if (filedJ == NULL) {
INIT_LOGE("[Init] GetServiceCaps, caps is not found. but maybe ok.\n");
INIT_LOGE("GetServiceCaps, caps is not found. but maybe ok.\n");
return SERVICE_SUCCESS;
}
if (!cJSON_IsArray(filedJ)) {
INIT_LOGE("[Init] GetServiceCaps, caps is not a list, error.\n");
INIT_LOGE("GetServiceCaps, caps is not a list, error.\n");
return SERVICE_FAILURE;
}
// caps array does not exist, means do not need any capability
......@@ -131,13 +131,13 @@ int GetServiceCaps(const cJSON* curArrItem, Service* curServ)
return SERVICE_SUCCESS;
}
if (capsCnt > MAX_CAPS_CNT_FOR_ONE_SERVICE) {
INIT_LOGE("[Init] GetServiceCaps, too many caps[cnt %d] for one service, should not exceed %d.\n",
INIT_LOGE("GetServiceCaps, too many caps[cnt %d] for one service, should not exceed %d.\n",
capsCnt, MAX_CAPS_CNT_FOR_ONE_SERVICE);
return SERVICE_FAILURE;
}
curServ->servPerm.caps = (unsigned int*)malloc(sizeof(unsigned int) * capsCnt);
if (curServ->servPerm.caps == NULL) {
INIT_LOGE("[Init] GetServiceCaps, malloc error.\n");
INIT_LOGE("GetServiceCaps, malloc error.\n");
return SERVICE_FAILURE;
}
curServ->servPerm.capsCnt = capsCnt;
......@@ -146,13 +146,13 @@ int GetServiceCaps(const cJSON* curArrItem, Service* curServ)
cJSON* capJ = cJSON_GetArrayItem(filedJ, i);
if (!cJSON_IsNumber(capJ) || cJSON_GetNumberValue(capJ) < 0) {
// resources will be released by function: ReleaseServiceMem
INIT_LOGE("[Init] GetServiceCaps, capJ is not a number or capJ < 0, error.\n");
INIT_LOGE("GetServiceCaps, capJ is not a number or capJ < 0, error.\n");
break;
}
curServ->servPerm.caps[i] = (unsigned int)cJSON_GetNumberValue(capJ);
if (curServ->servPerm.caps[i] > CAP_LAST_CAP && curServ->servPerm.caps[i] != FULL_CAP) { // CAP_LAST_CAP = 37
// resources will be released by function: ReleaseServiceMem
INIT_LOGE("[Init] GetServiceCaps, caps = %d, error.\n", curServ->servPerm.caps[i]);
INIT_LOGE("GetServiceCaps, caps = %d, error.\n", curServ->servPerm.caps[i]);
return SERVICE_FAILURE;
}
}
......
......@@ -33,12 +33,12 @@
#include <sys/syscall.h>
#include "init_jobs.h"
#include "init_log.h"
#include "init_reboot.h"
#include "init_service_manager.h"
#include "init_utils.h"
#include "securec.h"
#ifndef OHOS_LITE
#include "property_service.h"
#include "trigger.h"
#include "init_param.h"
#endif
#define DEFAULT_DIR_MODE 0755 // mkdir, default mode
......@@ -79,7 +79,9 @@ static const char* g_supportedCmds[] = {
"reset ",
"copy ",
"setparam ",
"load_persist_props "
"load_persist_params ",
"load_param ",
"reboot ",
};
void ParseCmdLine(const char* cmdStr, CmdLine* resCmd)
......@@ -112,25 +114,26 @@ void ParseCmdLine(const char* cmdStr, CmdLine* resCmd)
}
if (!foundAndSucceed) {
printf("[Init][Debug], Cannot parse command: %s\n", cmdStr);
INIT_LOGE("Cannot parse command: %s\n", cmdStr);
(void)memset_s(resCmd, sizeof(*resCmd), 0, sizeof(*resCmd));
}
}
static void DoStart(const char* cmdContent)
{
printf("[init][Debug] DoStart %s \n", cmdContent);
INIT_LOGD("DoStart %s \n", cmdContent);
StartServiceByName(cmdContent);
}
static void DoStop(const char* cmdContent)
{
INIT_LOGD("DoStop %s \n", cmdContent);
StopServiceByName(cmdContent);
}
static void DoReset(const char* cmdContent)
{
INIT_LOGE("[init][Debug] DoReset %s \n", cmdContent);
INIT_LOGD("DoReset %s \n", cmdContent);
DoStop(cmdContent);
DoStart(cmdContent);
}
......@@ -146,18 +149,18 @@ static void DoCopy(const char* cmdContent)
struct stat fileStat = {0};
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL || ctx->argc != DEFAULT_COPY_ARGS_CNT) {
INIT_LOGE("[Init] DoCopy failed.\n");
INIT_LOGE("DoCopy failed.\n");
goto out;
}
srcFd = open(ctx->argv[0], O_RDONLY);
INIT_ERROR_CHECK(srcFd >= 0, goto out, "[Init] copy open %s fail %d! \n", ctx->argv[0], errno);
INIT_ERROR_CHECK(stat(ctx->argv[0], &fileStat) == 0, goto out, "[Init] stat fail \n");
INIT_ERROR_CHECK(srcFd >= 0, goto out, "copy open %s fail %d! \n", ctx->argv[0], errno);
INIT_ERROR_CHECK(stat(ctx->argv[0], &fileStat) == 0, goto out, "stat fail \n");
mode = fileStat.st_mode;
dstFd = open(ctx->argv[1], O_WRONLY | O_TRUNC | O_CREAT, mode);
INIT_ERROR_CHECK(dstFd >= 0, goto out, "[Init] copy open %s fail %d! \n", ctx->argv[1], errno);
INIT_ERROR_CHECK(dstFd >= 0, goto out, "copy open %s fail %d! \n", ctx->argv[1], errno);
while ((rdLen = read(srcFd, buf, sizeof(buf) - 1)) > 0) {
rtLen = write(dstFd, buf, rdLen);
INIT_ERROR_CHECK(rtLen == rdLen, goto out, "[Init] write %s file fail %d! \n", ctx->argv[1], errno);
INIT_ERROR_CHECK(rtLen == rdLen, goto out, "write %s file fail %d! \n", ctx->argv[1], errno);
}
fsync(dstFd);
out:
......@@ -175,7 +178,7 @@ static void DoChown(const char* cmdContent)
// format: chown owner group /xxx/xxx/xxx
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL || ctx->argc != 3) {
INIT_LOGE("[Init] DoChown failed.\n");
INIT_LOGE("DoChown failed.\n");
goto out;
}
......@@ -183,21 +186,21 @@ static void DoChown(const char* cmdContent)
gid_t group = (gid_t)-1;
if (isalpha(ctx->argv[0][0])) {
owner = DecodeUid(ctx->argv[0]);
INIT_ERROR_CHECK(owner != (uid_t)-1, goto out, "[Init] DoChown decode owner failed.\n");
INIT_ERROR_CHECK(owner != (uid_t)-1, goto out, "DoChown decode owner failed.\n");
} else {
owner = strtoul(ctx->argv[0], NULL, 0);
}
if (isalpha(ctx->argv[1][0])) {
group = DecodeUid(ctx->argv[1]);
INIT_ERROR_CHECK(group != (gid_t)-1, goto out, "[Init] DoChown decode group failed.\n");
INIT_ERROR_CHECK(group != (gid_t)-1, goto out, "DoChown decode group failed.\n");
} else {
group = strtoul(ctx->argv[1], NULL, 0);
}
int pathPos = 2;
if (chown(ctx->argv[pathPos], owner, group) != 0) {
INIT_LOGE("[Init] DoChown, failed for %s, err %d.\n", cmdContent, errno);
INIT_LOGE("DoChown, failed for %s, err %d.\n", cmdContent, errno);
}
out:
FreeCmd(&ctx);
......@@ -209,7 +212,7 @@ static void DoMkDir(const char* cmdContent)
// format: mkdir /xxx/xxx/xxx or mkdir /xxx/xxx/xxx mode owner group
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL || ctx->argc < 1) {
INIT_LOGE("[Init] DoMkDir failed.\n");
INIT_LOGE("DoMkDir failed.\n");
goto out;
}
......@@ -225,7 +228,7 @@ static void DoMkDir(const char* cmdContent)
}
if (access(ctx->argv[0], 0) != 0) {
if (mkdir(ctx->argv[0], mode) != 0 && errno != EEXIST) {
INIT_LOGE("[Init] DoMkDir %s failed, err %d.\n", ctx->argv[0], errno);
INIT_LOGE("DoMkDir %s failed, err %d.\n", ctx->argv[0], errno);
goto out;
}
}
......@@ -233,14 +236,14 @@ static void DoMkDir(const char* cmdContent)
if (ctx->argc > 1) {
mode = strtoul(ctx->argv[1], NULL, OCTAL_TYPE);
if (chmod(ctx->argv[0], mode) != 0) {
printf("[Init] DoMkDir failed for %s, err %d.\n", cmdContent, errno);
INIT_LOGE("DoMkDir failed for %s, err %d.\n", cmdContent, errno);
}
int ownerPos = 2;
int groupPos = 3;
char chownCmdContent[AUTHORITY_MAX_SIZE] = { 0 };
if (snprintf_s(chownCmdContent, AUTHORITY_MAX_SIZE, AUTHORITY_MAX_SIZE - 1, "%s %s %s",
ctx->argv[ownerPos], ctx->argv[groupPos], ctx->argv[0]) == -1) {
INIT_LOGE("[Init] DoMkDir snprintf failed.\n");
INIT_LOGE("DoMkDir snprintf failed.\n");
goto out;
}
DoChown(chownCmdContent);
......@@ -255,18 +258,18 @@ static void DoChmod(const char* cmdContent)
// format: chmod xxxx /xxx/xxx/xxx
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL || ctx->argc != 2) {
INIT_LOGE("[Init] DoChmod failed.\n");
INIT_LOGE("DoChmod failed.\n");
goto out;
}
mode_t mode = strtoul(ctx->argv[0], NULL, OCTAL_TYPE);
if (mode == 0) {
INIT_LOGE("[Init] DoChmod, strtoul failed for %s, er %d.\n", cmdContent, errno);
INIT_LOGE("DoChmod, strtoul failed for %s, er %d.\n", cmdContent, errno);
goto out;
}
if (chmod(ctx->argv[1], mode) != 0) {
printf("[Init] DoChmod, failed for %s, err %d.\n", cmdContent, errno);
INIT_LOGE("DoChmod, failed for %s, err %d.\n", cmdContent, errno);
}
out:
FreeCmd(&ctx);
......@@ -276,20 +279,20 @@ out:
static char* CopySubStr(const char* srcStr, size_t startPos, size_t endPos)
{
if (endPos <= startPos) {
printf("[Init] DoMount, invalid params<%zu, %zu> for %s.\n", endPos, startPos, srcStr);
INIT_LOGE("DoMount, invalid params<%zu, %zu> for %s.\n", endPos, startPos, srcStr);
return NULL;
}
size_t mallocLen = endPos - startPos + 1;
char* retStr = (char*)malloc(mallocLen);
if (retStr == NULL) {
printf("[Init] DoMount, malloc failed! malloc size %zu, for %s.\n", mallocLen, srcStr);
INIT_LOGE("DoMount, malloc failed! malloc size %zu, for %s.\n", mallocLen, srcStr);
return NULL;
}
const char* copyStart = srcStr + startPos;
if (memcpy_s(retStr, mallocLen, copyStart, endPos - startPos) != EOK) {
printf("[Init] DoMount, memcpy_s failed for %s.\n", srcStr);
INIT_LOGE("DoMount, memcpy_s failed for %s.\n", srcStr);
free(retStr);
return NULL;
}
......@@ -313,7 +316,7 @@ static void WaitForFile(const char *source)
count++;
} while ((stat(source, &sourceInfo) < 0) && (errno == ENOENT) && (count < maxCount));
if (count == maxCount) {
INIT_LOGE("[Init] wait for file:%s failed after %d.\n", source, maxCount * CONVERT_MICROSEC_TO_SEC(waitTime));
INIT_LOGE("wait for file:%s failed after %d.\n", source, maxCount * CONVERT_MICROSEC_TO_SEC(waitTime));
}
return;
}
......@@ -350,7 +353,7 @@ static int CountSpaces(const char* cmdContent, size_t* spaceCnt, size_t* spacePo
if (cmdContent[i] == ' ') {
++(*spaceCnt);
if ((*spaceCnt) > spacePosArrLen) {
printf("[Init] DoMount, too many spaces, bad format for %s.\n", cmdContent);
INIT_LOGE("DoMount, too many spaces, bad format for %s.\n", cmdContent);
return 0;
}
spacePosArr[(*spaceCnt) - 1] = i;
......@@ -360,14 +363,14 @@ static int CountSpaces(const char* cmdContent, size_t* spaceCnt, size_t* spacePo
if ((*spaceCnt) < SPACES_CNT_IN_CMD_MIN || // spaces count should not less than 2(at least 3 items)
spacePosArr[0] == 0 || // should not start with space
spacePosArr[(*spaceCnt) - 1] == strLen - 1) { // should not end with space
printf("[Init] DoMount, bad format for %s.\n", cmdContent);
INIT_LOGE("DoMount, bad format for %s.\n", cmdContent);
return 0;
}
// spaces should not be adjacent
for (size_t i = 1; i < (*spaceCnt); ++i) {
if (spacePosArr[i] == spacePosArr[i - 1] + 1) {
printf("[Init] DoMount, bad format for %s.\n", cmdContent);
INIT_LOGE("DoMount, bad format for %s.\n", cmdContent);
return 0;
}
}
......@@ -432,7 +435,7 @@ static void DoMount(const char* cmdContent)
}
if (mountRet != 0) {
printf("[Init] DoMount, failed for %s, err %d.\n", cmdContent, errno);
INIT_LOGE("DoMount, failed for %s, err %d.\n", cmdContent, errno);
}
free(fileSysType);
......@@ -472,13 +475,13 @@ static void DoInsmodInternal(const char *fileName, char *secondPtr, char *restPt
realPath = realpath(fileName, realPath);
int fd = open(realPath, O_RDONLY | O_NOFOLLOW | O_CLOEXEC);
if (fd < 0) {
printf("[Init] failed to open %s: %d\n", realPath, errno);
INIT_LOGE("failed to open %s: %d\n", realPath, errno);
free(realPath);
return;
}
int rc = syscall(__NR_finit_module, fd, options, flags);
if (rc == -1) {
printf("[Init] finit_module for %s failed: %d\n", realPath, errno);
INIT_LOGE("finit_module for %s failed: %d\n", realPath, errno);
}
if (fd >= 0) {
close(fd);
......@@ -498,28 +501,28 @@ static void DoInsmod(const char *cmdContent)
size_t count = strlen(cmdContent);
if (count > OPTIONS_SIZE) {
printf("[Init], options too long, maybe lost some of options\n");
INIT_LOGE("options too long, maybe lost some of options\n");
}
line = (char *)malloc(count + 1);
if (line == NULL) {
printf("[Init] Allocate memory failed.\n");
INIT_LOGE("Allocate memory failed.\n");
return;
}
if (memcpy_s(line, count, cmdContent, count) != EOK) {
printf("[Init] memcpy failed\n");
INIT_LOGE("memcpy failed\n");
free(line);
return;
}
line[count] = '\0';
do {
if ((p = strtok_r(line, " ", &restPtr)) == NULL) {
printf("[Init] debug, cannot get filename\n");
INIT_LOGE("debug, cannot get filename\n");
free(line);
return;
}
fileName = p;
printf("[Init] debug, fileName is [%s]\n", fileName);
INIT_LOGE("debug, fileName is [%s]\n", fileName);
if ((p = strtok_r(NULL, " ", &restPtr)) == NULL) {
break;
}
......@@ -538,11 +541,11 @@ static void DoSetParam(const char* cmdContent)
{
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL || ctx->argc != 2) {
INIT_LOGE("[Init] DoSetParam failed.\n");
INIT_LOGE("DoSetParam failed.\n");
goto out;
}
INIT_LOGE("[Init] param name: %s, value %s \n", ctx->argv[0], ctx->argv[1]);
INIT_ERROR_CHECK(SystemWriteParameter(ctx->argv[0], ctx->argv[1]) == 0, goto out, "setparam fail \n");
INIT_LOGE("param name: %s, value %s \n", ctx->argv[0], ctx->argv[1]);
SystemWriteParam(ctx->argv[0], ctx->argv[1]);
out:
FreeCmd(&ctx);
return;
......@@ -580,21 +583,21 @@ static void DoLoadCfg(const char *path)
return;
}
printf("[Init] DoLoadCfg cfg file %s\n", path);
INIT_LOGI("DoLoadCfg cfg file %s\n", path);
if (!CheckValidCfg(path)) {
printf("[Init] CheckCfg file %s Failed\n", path);
INIT_LOGE("CheckCfg file %s Failed\n", path);
return;
}
fp = fopen(path, "r");
if (fp == NULL) {
printf("[Init] open cfg error = %d\n", errno);
INIT_LOGE("open cfg error = %d\n", errno);
return;
}
cmdLine = (CmdLine *)malloc(sizeof(CmdLine));
if (cmdLine == NULL) {
printf("[Init] malloc cmdline error");
INIT_LOGE("malloc cmdline error");
fclose(fp);
return;
}
......@@ -624,20 +627,20 @@ static void DoWrite(const char *cmdContent)
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
int writeCmdNumber = 2;
if (ctx == NULL || ctx->argv == NULL || ctx->argc != writeCmdNumber) {
printf("[Init] DoWrite: invalid arguments\n");
INIT_LOGE("DoWrite: invalid arguments\n");
goto out;
}
int fd = open(ctx->argv[0], O_WRONLY | O_CREAT | O_NOFOLLOW | O_CLOEXEC, S_IRWXU |
S_IRGRP | S_IROTH);
if (fd == -1) {
printf("[Init] DoWrite: open %s failed: %d\n", ctx->argv[0], errno);
INIT_LOGE("DoWrite: open %s failed: %d\n", ctx->argv[0], errno);
goto out;
}
size_t ret = write(fd, ctx->argv[1], strlen(ctx->argv[1]));
if (ret < 0) {
printf("[Init] DoWrite: write to file %s failed: %d\n", ctx->argv[0], errno);
INIT_LOGE("DoWrite: write to file %s failed: %d\n", ctx->argv[0], errno);
close(fd);
goto out;
}
......@@ -652,13 +655,13 @@ static void DoRmdir(const char *cmdContent)
// format: rmdir path
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL || ctx->argc != 1) {
INIT_LOGE("[Init] DoRmdir: invalid arguments\n");
INIT_LOGE("DoRmdir: invalid arguments\n");
goto out;
}
int ret = rmdir(ctx->argv[0]);
if (ret == -1) {
INIT_LOGE("[Init] DoRmdir: remove %s failed: %d.\n", ctx->argv[0], errno);
INIT_LOGE("DoRmdir: remove %s failed: %d.\n", ctx->argv[0], errno);
goto out;
}
out:
......@@ -671,12 +674,12 @@ static void DoRm(const char *cmdContent)
// format: rm /xxx/xxx/xxx
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL || ctx->argc != 1) {
printf("[Init] DoRm: invalid arguments\n");
INIT_LOGE("DoRm: invalid arguments\n");
goto out;
}
int ret = unlink(ctx->argv[0]);
if (ret == -1) {
INIT_LOGE("[Init] DoRm: unlink %s failed: %d.\n", ctx->argv[0], errno);
INIT_LOGE("DoRm: unlink %s failed: %d.\n", ctx->argv[0], errno);
goto out;
}
out:
......@@ -689,12 +692,12 @@ static void DoExport(const char *cmdContent)
// format: export xxx /xxx/xxx/xxx
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL || ctx->argc != 2) {
printf("[Init] DoExport: invalid arguments\n");
INIT_LOGE("DoExport: invalid arguments\n");
goto out;
}
int ret = setenv(ctx->argv[0], ctx->argv[1], 1);
if (ret != 0) {
INIT_LOGE("[Init] DoExport: set %s with %s failed: %d\n", ctx->argv[0], ctx->argv[1], errno);
INIT_LOGE("DoExport: set %s with %s failed: %d\n", ctx->argv[0], ctx->argv[1], errno);
goto out;
}
out:
......@@ -705,29 +708,28 @@ out:
static void DoExec(const char *cmdContent)
{
// format: exec /xxx/xxx/xxx xxx
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL) {
INIT_LOGE("[Init] DoExec: invalid arguments\n");
goto out;
}
pid_t pid = fork();
if (pid < 0) {
INIT_LOGE("DoExec: failed to fork child process to exec \"%s\"\n", cmdContent);
return;
}
if (pid == 0) {
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
if (ctx == NULL || ctx->argv == NULL) {
INIT_LOGE("DoExec: invalid arguments\n");
_exit(0x7f);
}
#ifdef OHOS_LITE
int ret = execve(ctx->argv[0], ctx->argv, NULL);
#else
int ret = execv(ctx->argv[0], ctx->argv);
#endif
if (ret == -1) {
INIT_LOGE("[Init] DoExec: execute \"%s\" failed: %d.\n", cmdContent, errno);
goto out;
INIT_LOGE("DoExec: execute \"%s\" failed: %d.\n", cmdContent, errno);
}
} else {
int status = 0;
waitpid(pid, &status, 0);
INIT_LOGI("[Init] DoExec done.\n");
FreeCmd(&ctx);
_exit(0x7f);
}
out:
FreeCmd(&ctx);
return;
}
......@@ -738,13 +740,13 @@ static void DoSymlink(const char *cmdContent)
struct CmdArgs *ctx = GetCmd(cmdContent, " ");
int symlinkCmdNumber = 2;
if (ctx == NULL || ctx->argv == NULL || ctx->argc != symlinkCmdNumber) {
INIT_LOGE("[Init] DoSymlink: invalid arguments.\n");
INIT_LOGE("DoSymlink: invalid arguments.\n");
goto out;
}
int ret = symlink(ctx->argv[0], ctx->argv[1]);
if (ret != 0) {
INIT_LOGE("[Init] DoSymlink: link %s to %s failed: %d\n", ctx->argv[0], ctx->argv[1], errno);
INIT_LOGE("DoSymlink: link %s to %s failed: %d\n", ctx->argv[0], ctx->argv[1], errno);
goto out;
}
out:
......@@ -781,12 +783,12 @@ static void DoMakeNode(const char *cmdContent)
int decimal = 10;
int octal = 8;
if (ctx == NULL || ctx->argv == NULL || ctx->argc != mkNodeCmdNumber) {
INIT_LOGE("[Init] DoMakeNode: invalid arguments\n");
INIT_LOGE("DoMakeNode: invalid arguments\n");
goto out;
}
if (!access(ctx->argv[1], F_OK)) {
INIT_LOGE("[Init] DoMakeNode failed, path has not sexisted\n");
INIT_LOGE("DoMakeNode failed, path has not sexisted\n");
goto out;
}
mode_t deviceMode = GetDeviceMode(ctx->argv[deviceTypePos]);
......@@ -796,7 +798,7 @@ static void DoMakeNode(const char *cmdContent)
int ret = mknod(ctx->argv[0], deviceMode | authority, makedev(major, minor));
if (ret != 0) {
INIT_LOGE("[Init] DoMakeNode: path: %s failed: %d\n", ctx->argv[0], errno);
INIT_LOGE("DoMakeNode: path: %s failed: %d\n", ctx->argv[0], errno);
goto out;
}
out:
......@@ -811,14 +813,14 @@ static void DoMakeDevice(const char *cmdContent)
int makeDevCmdNumber = 2;
int decimal = 10;
if (ctx == NULL || ctx->argv == NULL || ctx->argc != makeDevCmdNumber) {
INIT_LOGE("[Init] DoMakedevice: invalid arugments\n");
INIT_LOGE("DoMakedevice: invalid arugments\n");
goto out;
}
unsigned int major = strtoul(ctx->argv[0], NULL, decimal);
unsigned int minor = strtoul(ctx->argv[1], NULL, decimal);
dev_t deviceId = makedev(major, minor);
if (deviceId < 0) {
INIT_LOGE("[Init] DoMakedevice \" %s \" failed :%d \n", cmdContent, errno);
INIT_LOGE("DoMakedevice \" %s \" failed :%d \n", cmdContent, errno);
goto out;
}
out:
......@@ -882,15 +884,19 @@ void DoCmdByName(const char *name, const char *cmdContent)
} else if (strncmp(name, "insmod ", strlen("insmod ")) == 0) {
DoInsmod(cmdContent);
} else if (strncmp(name, "trigger ", strlen("trigger ")) == 0) {
printf("[Init][Debug], ready to trigger job: %s\n", name);
INIT_LOGD("ready to trigger job: %s\n", name);
DoTriggerExec(cmdContent);
} else if (strncmp(name, "load_persist_props ", strlen("load_persist_props ")) == 0) {
LoadPersistProperties();
} else if (strncmp(name, "load_persist_params ", strlen("load_persist_params ")) == 0) {
LoadPersistParams();
} else if (strncmp(name, "setparam ", strlen("setparam ")) == 0) {
DoSetParam(cmdContent);
} else if (strncmp(name, "load_param ", strlen("load_param ")) == 0) {
LoadDefaultParams(cmdContent);
#endif
} else {
printf("[Init] DoCmd, unknown cmd name %s.\n", name);
} else if (strncmp(name, "reboot ", strlen("reboot ")) == 0) {
DoReboot(cmdContent);
} else {
INIT_LOGE("DoCmd, unknown cmd name %s.\n", name);
}
}
......
......@@ -15,7 +15,9 @@
#include "init_import.h"
#include <stdio.h>
#include <unistd.h>
#include "cJSON.h"
#include "init_log.h"
#include "init_read_cfg.h"
#define IMPORT_ARR_NAME_IN_JSON "import"
......@@ -25,7 +27,7 @@ void ParseAllImports(cJSON *root)
cJSON *importAttr = cJSON_GetObjectItemCaseSensitive(root, IMPORT_ARR_NAME_IN_JSON);
if (!cJSON_IsArray(importAttr)) {
printf("[Init] ParseAllImports, import item is not array!\n");
INIT_LOGE("ParseAllImports, import item is not array!\n");
return;
}
int importAttrSize = cJSON_GetArraySize(importAttr);
......@@ -33,17 +35,17 @@ void ParseAllImports(cJSON *root)
for (int i = 0; i < importAttrSize; i++) {
cJSON *importItem = cJSON_GetArrayItem(importAttr, i);
if (!cJSON_IsString(importItem)) {
printf("[Init] Invalid type of import item. should be string\n");
INIT_LOGE("Invalid type of import item. should be string\n");
return;
}
char *importFile = cJSON_GetStringValue(importItem);
if (importFile == NULL) {
printf("[Init] cannot get import config file\n");
INIT_LOGE("cannot get import config file\n");
return;
}
printf("[Init] [Debug], ready to import %s...\n", importFile);
INIT_LOGD("ready to import %s...\n", importFile);
ParseInitCfg(importFile);
}
printf("[Init] [Debug], parse import file done\n");
INIT_LOGD("parse import file done\n");
return;
}
\ No newline at end of file
}
......@@ -17,8 +17,10 @@
#include <stdio.h>
#include <string.h>
#include <unistd.h>
#include "init_cmds.h"
#include "init_log.h"
#include "securec.h"
......@@ -37,16 +39,16 @@ static int g_jobCnt = 0;
void DumpAllJobs()
{
printf("[Init][Debug], Ready to dump all jobs:\n");
INIT_LOGD("Ready to dump all jobs:\n");
for (int i = 0; i < g_jobCnt; i++) {
printf("\t[Init], job name: %s\n", g_jobs[i].name);
printf("\t[Init], list all commands:\n");
INIT_LOGD("\tjob name: %s\n", g_jobs[i].name);
INIT_LOGD("\tlist all commands:\n");
for (int j = 0; j < g_jobs[i].cmdLinesCnt; j++) {
printf("\t\t[Init], command name : %s, command options: %s\n",
INIT_LOGD("\t\tcommand name : %s, command options: %s\n",
g_jobs[i].cmdLines[j].name, g_jobs[i].cmdLines[j].cmdContent);
}
}
printf("[Init][Debug], To dump all jobs finished\n");
INIT_LOGD("To dump all jobs finished\n");
}
static int GetJobName(const cJSON* jobItem, Job* resJob)
......@@ -56,19 +58,8 @@ static int GetJobName(const cJSON* jobItem, Job* resJob)
return 0;
}
//size_t supportJobCnt = sizeof(g_supportedJobs) / sizeof(g_supportedJobs[0]);
//for (size_t i = 0; i < supportJobCnt; ++i) {
// if (strlen(g_supportedJobs[i]) == strlen(jobNameStr) &&
// strncmp(g_supportedJobs[i], jobNameStr, strlen(g_supportedJobs[i])) == 0) {
// if (memcpy_s(resJob->name, MAX_JOB_NAME_LEN, jobNameStr, strlen(jobNameStr)) != EOK) {
// return 0;
// }
// resJob->name[strlen(jobNameStr)] = '\0';
// return 1;
// }
//}
if (memcpy_s(resJob->name, MAX_JOB_NAME_LEN, jobNameStr, strlen(jobNameStr)) != EOK) {
printf("[Init], Get job name \"%s\" failed\n", jobNameStr);
INIT_LOGE("Get job name \"%s\" failed\n", jobNameStr);
return 0;
}
resJob->name[strlen(jobNameStr)] = '\0';
......@@ -78,33 +69,33 @@ static int GetJobName(const cJSON* jobItem, Job* resJob)
static void ParseJob(const cJSON* jobItem, Job* resJob)
{
if (!GetJobName(jobItem, resJob)) {
printf("[Init][Debug], get JobName failed\n");
INIT_LOGE("get JobName failed\n");
(void)memset_s(resJob, sizeof(*resJob), 0, sizeof(*resJob));
return;
}
cJSON* cmdsItem = cJSON_GetObjectItem(jobItem, CMDS_ARR_NAME_IN_JSON);
if (!cJSON_IsArray(cmdsItem)) {
printf("[Init][Debug], job %s is not an arrary\n", resJob->name);
INIT_LOGE("job %s is not an arrary\n", resJob->name);
return;
}
int cmdLinesCnt = cJSON_GetArraySize(cmdsItem);
if (cmdLinesCnt <= 0) { // empty job, no cmd
printf("[Init][Debug], empty job \"%s\"\n", resJob->name);
INIT_LOGE("empty job \"%s\"\n", resJob->name);
return;
}
printf("[Init][Debug], job = %s, cmdLineCnt = %d\n", resJob->name, cmdLinesCnt);
INIT_LOGD("job = %s, cmdLineCnt = %d\n", resJob->name, cmdLinesCnt);
if (cmdLinesCnt > MAX_CMD_CNT_IN_ONE_JOB) {
printf("[Init] ParseAllJobs, too many cmds[cnt %d] in one job, it should not exceed %d.\n",
INIT_LOGE("ParseAllJobs, too many cmds[cnt %d] in one job, it should not exceed %d.\n",
cmdLinesCnt, MAX_CMD_CNT_IN_ONE_JOB);
return;
}
resJob->cmdLines = (CmdLine*)malloc(cmdLinesCnt * sizeof(CmdLine));
if (resJob->cmdLines == NULL) {
printf("[Init][Debug], allocate memory for command line failed\n");
INIT_LOGE("allocate memory for command line failed\n");
return;
}
......@@ -124,32 +115,32 @@ static void ParseJob(const cJSON* jobItem, Job* resJob)
void ParseAllJobs(const cJSON* fileRoot)
{
if (fileRoot == NULL) {
printf("[Init] ParseAllJobs, input fileRoot is NULL!\n");
INIT_LOGE("ParseAllJobs, input fileRoot is NULL!\n");
return;
}
cJSON* jobArr = cJSON_GetObjectItemCaseSensitive(fileRoot, JOBS_ARR_NAME_IN_JSON);
if (!cJSON_IsArray(jobArr)) {
printf("[Init] ParseAllJobs, job item is not array!\n");
INIT_LOGE("ParseAllJobs, job item is not array!\n");
return;
}
int jobArrSize = cJSON_GetArraySize(jobArr);
if (jobArrSize <= 0 || jobArrSize > MAX_JOBS_COUNT) {
printf("[Init] ParseAllJobs, jobs count %d is invalid, should be positive and not exceeding %d.\n",
INIT_LOGE("ParseAllJobs, jobs count %d is invalid, should be positive and not exceeding %d.\n",
jobArrSize, MAX_JOBS_COUNT);
return;
}
Job* retJobs = (Job*)realloc(g_jobs, sizeof(Job) * (g_jobCnt + jobArrSize));
if (retJobs == NULL) {
printf("[Init] ParseAllJobs, malloc failed! job arrSize %d.\n", jobArrSize);
INIT_LOGE("ParseAllJobs, malloc failed! job arrSize %d.\n", jobArrSize);
return;
}
Job* tmp = retJobs + g_jobCnt;
if (memset_s(tmp, sizeof(Job) * jobArrSize, 0, sizeof(Job) * jobArrSize) != EOK) {
printf("[Init] ParseAllJobs, memset_s failed.\n");
INIT_LOGE("ParseAllJobs, memset_s failed.\n");
free(retJobs);
retJobs = NULL;
return;
......@@ -166,11 +157,11 @@ void ParseAllJobs(const cJSON* fileRoot)
void DoJob(const char* jobName)
{
if (jobName == NULL) {
printf("[Init] DoJob, input jobName NULL!\n");
INIT_LOGE("DoJob, input jobName NULL!\n");
return;
}
printf("[Init][Debug], Call job with name %s\n", jobName);
INIT_LOGD("Call job with name %s\n", jobName);
for (int i = 0; i < g_jobCnt; ++i) {
if (strncmp(jobName, g_jobs[i].name, strlen(g_jobs[i].name)) == 0) {
CmdLine* cmdLines = g_jobs[i].cmdLines;
......
......@@ -32,7 +32,7 @@
#include "init_utils.h"
#ifndef OHOS_LITE
#include "trigger.h"
#include "init_param.h"
#endif
#include "securec.h"
#ifndef __LINUX__
......@@ -61,21 +61,17 @@ static void ParseInitCfgContents(cJSON *root)
void ParseInitCfg(const char *configFile)
{
if (configFile == NULL || *configFile == '\0') {
printf("[Init] Invalid config file\n");
INIT_LOGE("Invalid config file\n");
return;
}
char *fileBuf = ReadFileToBuf(configFile);
//printf("[Init] start dump config file: \n");
//printf("%s", fileBuf);
//printf("[Init] end dump config file: \n");
cJSON* fileRoot = cJSON_Parse(fileBuf);
free(fileBuf);
fileBuf = NULL;
if (fileRoot == NULL) {
printf("[Init] InitReadCfg, parse failed! please check file %s format.\n", configFile);
INIT_LOGE("InitReadCfg, parse failed! please check file %s format.\n", configFile);
return;
}
ParseInitCfgContents(fileRoot);
......@@ -88,14 +84,14 @@ static void ReadCfgs(const char *dirPath)
{
DIR *pDir = opendir(dirPath);
if (pDir == NULL) {
INIT_LOGE("[Init], ParseCfgs open cfg dir :%s failed.%d\n", dirPath, errno);
INIT_LOGE("ParseCfgs open cfg dir :%s failed.%d\n", dirPath, errno);
return;
}
struct dirent *dp;
while ((dp = readdir(pDir)) != NULL) {
char fileName[FILE_NAME_MAX_SIZE];
if (snprintf_s(fileName, FILE_NAME_MAX_SIZE, FILE_NAME_MAX_SIZE - 1, "%s/%s", dirPath, dp->d_name) == -1) {
INIT_LOGE("[Init], ParseCfgs snprintf_s failed.\n");
INIT_LOGE("ParseCfgs snprintf_s failed.\n");
closedir(pDir);
return;
}
......@@ -104,7 +100,7 @@ static void ReadCfgs(const char *dirPath)
if (strstr(dp->d_name, ".cfg") == NULL) {
continue;
}
INIT_LOGE("[Init], fileName :%s.\n", fileName);
INIT_LOGE("fileName :%s.\n", fileName);
ParseInitCfg(fileName);
}
}
......@@ -120,9 +116,15 @@ static void ParseOtherCfgs()
void InitReadCfg()
{
#ifndef OHOS_LITE
InitParamService();
LoadDefaultParams("/system/etc/prop.default");
LoadDefaultParams("/system/build.prop");
LoadDefaultParams("/system/buildz.prop");
#endif
ParseInitCfg(INIT_CONFIGURATION_FILE);
ParseOtherCfgs();
printf("[init], Parse init config file done.\n");
INIT_LOGI("Parse init config file done.\n");
DumpAllServices();
// DumpAllJobs();
......
/*
* Copyright (c) 2020 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 "init_reboot.h"
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/mount.h>
#include <sys/prctl.h>
#include <sys/reboot.h>
#include "init_service.h"
#include "init_service_manager.h"
#include "init_log.h"
#define MAX_VALUE_LENGTH 500
#define MAX_COMMAND_SIZE 20
#define MAX_UPDATE_SIZE 100
struct RBMiscUpdateMessage {
char command[MAX_COMMAND_SIZE];
char update[MAX_UPDATE_SIZE];
};
static bool RBMiscWriteUpdaterMessage(const char *path, struct RBMiscUpdateMessage *boot)
{
FILE* fp = fopen(path, "rb+");
if (fp == NULL) {
INIT_LOGE("open %s failed", path);
return false;
}
size_t ret = fwrite(boot, sizeof(struct RBMiscUpdateMessage), 1, fp);
if (ret < 0) {
INIT_LOGE("write to misc failed\n");
fclose(fp);
return false;
}
fclose(fp);
return true;
}
static bool RBMiscReadUpdaterMessage(const char *path, struct RBMiscUpdateMessage *boot)
{
FILE* fp = fopen(path, "rb");
if (fp == NULL) {
INIT_LOGE("open %s failed", path);
return false;
}
size_t ret = fread(boot, 1, sizeof(struct RBMiscUpdateMessage), fp);
if (ret <= 0) {
INIT_LOGE("read to misc failed");
fclose(fp);
return false;
}
fclose(fp);
return true;
}
static int GetMountStatusForMountPoint(const char *mountPoint)
{
char buffer[512];
size_t n;
const char *mountFile = "/proc/mounts";
FILE *fp = fopen(mountFile, "r");
if (fp == NULL) {
INIT_LOGE("[init] DoReboot %s can't open.\n", mountPoint);
return 1;
}
while (fgets(buffer, sizeof(buffer), fp) != NULL) {
n = strlen(buffer);
if (buffer[n - 1] == '\n') {
buffer[n - 1] = '\0';
}
if (strstr(buffer, mountPoint) != NULL) {
fclose(fp);
return 1;
}
}
// Cannot find it from system.
fclose(fp);
return 0;
}
void DoReboot(const char *value)
{
if (value == NULL) {
INIT_LOGE("[init] DoReboot value = NULL\n");
return;
}
INIT_LOGI("[init] DoReboot value = %s\n", value);
if (strlen(value) > MAX_VALUE_LENGTH) {
INIT_LOGE("DoReboot reboot value error, value = %s.\n", value);
return;
}
if (GetMountStatusForMountPoint("/vendor")) {
if (umount("/vendor") != 0) {
INIT_LOGE("DoReboot umount vendor failed! errno = %d.\n", errno);
}
}
if (GetMountStatusForMountPoint("/data")) {
if (umount("/data") != 0) {
INIT_LOGE("DoReboot umount data failed! errno = %d.\n", errno);
}
}
StopAllServicesBeforeReboot();
// "shutdown"
if (strncmp(value, "shutdown", sizeof("shutdown")) == 0) {
int ret = reboot(RB_POWER_OFF);
if (ret != 0) {
INIT_LOGE("DoReboot reboot(RB_POWER_OFF) failed! syscall ret %d, err %d.\n", ret, errno);
}
return;
}
// "updater" or "updater:"
const char *miscFile = "/dev/block/platform/soc/10100000.himci.eMMC/by-name/misc";
struct RBMiscUpdateMessage msg;
bool ret = RBMiscReadUpdaterMessage(miscFile, &msg);
if(!ret) {
INIT_LOGE("[init] DoReboot RBMiscReadUpdaterMessage error.\n");
return;
}
const int commandSize = 12;
snprintf(msg.command, MAX_COMMAND_SIZE, "%s", "boot_updater");
msg.command[commandSize] = 0;
if (strlen(value) > strlen("updater:") && strncmp(value, "updater:", strlen("updater:")) == 0) {
const char *p = value + strlen("updater:");
if (snprintf(msg.update, MAX_UPDATE_SIZE, "%s", p) > MAX_UPDATE_SIZE) {
INIT_LOGE("[init] DoReboot updater: RBMiscWriteUpdaterMessage error\n");
return;
}
msg.update[MAX_UPDATE_SIZE - 1] = 0;
ret = RBMiscWriteUpdaterMessage(miscFile, &msg);
if(true != ret) {
INIT_LOGE("[init] DoReboot updater: RBMiscWriteUpdaterMessage error\n");
return;
}
ret = reboot(RB_AUTOBOOT);
if (ret != 0) {
INIT_LOGE("DoReboot updater: reboot(RB_AUTOBOOT) failed! syscall ret %d, err %d.\n", ret, errno);
}
return;
}
if (strlen(value) == strlen("updater") && strncmp(value, "updater", strlen("updater")) == 0) {
ret = RBMiscWriteUpdaterMessage(miscFile, &msg);
if(true != ret) {
INIT_LOGE("[init] DoReboot updater RBMiscWriteUpdaterMessage error\n");
return;
}
ret = reboot(RB_AUTOBOOT);
if (ret != 0) {
INIT_LOGE("DoReboot updater reboot(RB_AUTOBOOT) failed! syscall ret %d, err %d.\n", ret, errno);
}
return;
}
if (strlen(value) == strlen("NoArgument") && strncmp(value, "NoArgument", strlen("NoArgument")) == 0) {
ret = reboot(RB_AUTOBOOT);
if (ret != 0) {
INIT_LOGE("DoReboot updater: reboot(RB_AUTOBOOT) failed! syscall ret %d, err %d.\n", ret, errno);
}
return;
}
INIT_LOGE("DoReboot value = %s, error.\n", value);
return;
}
......@@ -61,13 +61,13 @@ static int SetPerms(const Service *service)
}
if (setgroups(service->servPerm.gIDCnt, service->servPerm.gIDArray) != 0) {
INIT_LOGE("[Init] SetPerms, setgroups failed. errno = %d, gIDCnt=%d\n", errno, service->servPerm.gIDCnt);
INIT_LOGE("SetPerms, setgroups failed. errno = %d, gIDCnt=%d\n", errno, service->servPerm.gIDCnt);
return SERVICE_FAILURE;
}
if (service->servPerm.uID != 0) {
if (setuid(service->servPerm.uID) != 0) {
printf("[Init] setuid of service: %s failed, uid = %d\n", service->name, service->servPerm.uID);
INIT_LOGE("setuid of service: %s failed, uid = %d\n", service->name, service->servPerm.uID);
return SERVICE_FAILURE;
}
}
......@@ -95,7 +95,7 @@ static int SetPerms(const Service *service)
}
if (capset(&capHeader, capData) != 0) {
printf("[Init][Debug], capset faild for service: %s, error: %d\n", service->name, errno);
INIT_LOGE("capset faild for service: %s, error: %d\n", service->name, errno);
return SERVICE_FAILURE;
}
for (unsigned int i = 0; i < service->servPerm.capsCnt; ++i) {
......@@ -103,7 +103,7 @@ static int SetPerms(const Service *service)
return SetAllAmbientCapability();
}
if (SetAmbientCapability(service->servPerm.caps[i]) != 0) {
printf("[Init][Debug], SetAmbientCapability faild for service: %s\n", service->name);
INIT_LOGE("SetAmbientCapability faild for service: %s\n", service->name);
return SERVICE_FAILURE;
}
}
......@@ -113,12 +113,12 @@ static int SetPerms(const Service *service)
int ServiceStart(Service *service)
{
if (service == NULL) {
printf("[Init] start service failed! null ptr.\n");
INIT_LOGE("start service failed! null ptr.\n");
return SERVICE_FAILURE;
}
if (service->attribute & SERVICE_ATTR_INVALID) {
printf("[Init] start service %s invalid.\n", service->name);
INIT_LOGE("start service %s invalid.\n", service->name);
return SERVICE_FAILURE;
}
......@@ -126,7 +126,7 @@ int ServiceStart(Service *service)
service->attribute &= (~(SERVICE_ATTR_NEED_RESTART | SERVICE_ATTR_NEED_STOP));
if (stat(service->pathArgs[0], &pathStat) != 0) {
service->attribute |= SERVICE_ATTR_INVALID;
printf("[Init] start service %s invalid, please check %s.\n",\
INIT_LOGE("start service %s invalid, please check %s.\n",\
service->name, service->pathArgs[0]);
return SERVICE_FAILURE;
}
......@@ -134,22 +134,23 @@ int ServiceStart(Service *service)
int pid = fork();
if (pid == 0) {
if (service->socketCfg != NULL) { // start socket service
printf("[init] Create socket \n");
INIT_LOGI("Create socket \n");
ret = DoCreateSocket(service->socketCfg);
if (ret < 0) {
return SERVICE_FAILURE;
INIT_LOGE("DoCreateSocket failed. \n");
_exit(0x7f); // 0x7f: user specified
}
}
// permissions
if (SetPerms(service) != SERVICE_SUCCESS) {
INIT_LOGE("[Init] service %s exit! set perms failed! err %d.\n", service->name, errno);
INIT_LOGE("service %s exit! set perms failed! err %d.\n", service->name, errno);
_exit(0x7f); // 0x7f: user specified
}
char pidString[MAX_PID_STRING_LENGTH]; // writepid
pid_t childPid = getpid();
if (snprintf(pidString, MAX_PID_STRING_LENGTH, "%d", childPid) <= 0) {
INIT_LOGE("[Init] start service writepid sprintf failed.\n");
return SERVICE_FAILURE;
INIT_LOGE("start service writepid sprintf failed.\n");
_exit(0x7f); // 0x7f: user specified
}
for (int i = 0; i < MAX_WRITEPID_FILES; i++) {
if (service->writepidFiles[i] == NULL) {
......@@ -157,44 +158,45 @@ int ServiceStart(Service *service)
}
FILE *fd = fopen(service->writepidFiles[i], "wb");
if (fd == NULL) {
INIT_LOGE("[Init] start service writepidFiles %s invalid.\n", service->writepidFiles[i]);
INIT_LOGE("start service writepidFiles %s invalid.\n", service->writepidFiles[i]);
continue;
}
if (fwrite(pidString, 1, strlen(pidString), fd) != strlen(pidString)) {
INIT_LOGE("[Init] start service writepid error.file:%s pid:%s\n", service->writepidFiles[i], pidString);
INIT_LOGE("start service writepid error.file:%s pid:%s\n", service->writepidFiles[i], pidString);
}
fclose(fd);
printf("[Init] ServiceStart writepid filename=%s, childPid=%s, ok\n", service->writepidFiles[i], pidString);
INIT_LOGE("ServiceStart writepid filename=%s, childPid=%s, ok\n", service->writepidFiles[i],
pidString);
}
printf("[init] service->name is %s \n", service->name);
INIT_LOGI("service->name is %s \n", service->name);
#ifndef OHOS_LITE
// L2 Can not be reset env
if (execv(service->pathArgs[0], service->pathArgs) != 0) {
printf("[Init] service %s execve failed! err %d.\n", service->name, errno);
INIT_LOGE("service %s execve failed! err %d.\n", service->name, errno);
}
#else
char* env[] = {"LD_LIBRARY_PATH=/storage/app/libs", NULL};
if (execve(service->pathArgs[0], service->pathArgs, env) != 0) {
printf("[Init] service %s execve failed! err %d.\n", service->name, errno);
INIT_LOGE("service %s execve failed! err %d.\n", service->name, errno);
}
#endif
_exit(0x7f); // 0x7f: user specified
} else if (pid < 0) {
printf("[Init] start service %s fork failed!\n", service->name);
INIT_LOGE("start service %s fork failed!\n", service->name);
return SERVICE_FAILURE;
}
service->pid = pid;
printf("[Init] start service %s succeed, pid %d.\n", service->name, service->pid);
INIT_LOGI("start service %s succeed, pid %d.\n", service->name, service->pid);
return SERVICE_SUCCESS;
}
int ServiceStop(Service *service)
{
if (service == NULL) {
printf("[Init] stop service failed! null ptr.\n");
INIT_LOGE("stop service failed! null ptr.\n");
return SERVICE_FAILURE;
}
......@@ -205,11 +207,11 @@ int ServiceStop(Service *service)
}
if (kill(service->pid, SIGKILL) != 0) {
printf("[Init] stop service %s pid %d failed! err %d.\n", service->name, service->pid, errno);
INIT_LOGE("stop service %s pid %d failed! err %d.\n", service->name, service->pid, errno);
return SERVICE_FAILURE;
}
printf("[Init] stop service %s, pid %d.\n", service->name, service->pid);
INIT_LOGI("stop service %s, pid %d.\n", service->name, service->pid);
return SERVICE_SUCCESS;
}
......@@ -228,7 +230,7 @@ void CheckCritical(Service *service)
} else {
++service->criticalCrashCnt;
if (service->criticalCrashCnt > CRITICAL_CRASH_COUNT_LIMIT) {
INIT_LOGE("[Init] reap critical service %s, crash too many times! Need reboot!\n", service->name);
INIT_LOGE("reap critical service %s, crash too many times! Need reboot!\n", service->name);
RebootSystem();
}
}
......@@ -237,13 +239,13 @@ void CheckCritical(Service *service)
static int ExecRestartCmd(const Service *service)
{
printf("[init] ExecRestartCmd \n");
INIT_LOGI("ExecRestartCmd \n");
if ((service == NULL) || (service->onRestart == NULL) || (service->onRestart->cmdLine == NULL)) {
return SERVICE_FAILURE;
}
for (int i = 0; i < service->onRestart->cmdNum; i++) {
printf("[init] SetOnRestart cmdLine->name %s cmdLine->cmdContent %s \n", service->onRestart->cmdLine[i].name,
INIT_LOGI("SetOnRestart cmdLine->name %s cmdLine->cmdContent %s \n", service->onRestart->cmdLine[i].name,
service->onRestart->cmdLine[i].cmdContent);
DoCmd(&service->onRestart->cmdLine[i]);
}
......@@ -255,7 +257,12 @@ static int ExecRestartCmd(const Service *service)
void ServiceReap(Service *service)
{
if (service == NULL) {
printf("[Init] reap service failed! null ptr.\n");
INIT_LOGE("reap service failed! null ptr.\n");
return;
}
if (service->attribute & SERVICE_ATTR_INVALID) {
INIT_LOGE("ServiceReap service %s invalid.\n", service->name);
return;
}
......@@ -290,7 +297,7 @@ void ServiceReap(Service *service)
} else {
++service->crashCnt;
if (service->crashCnt > CRASH_COUNT_LIMIT) {
printf("[Init] reap service %s, crash too many times!\n", service->name);
INIT_LOGE("reap service %s, crash too many times!\n", service->name);
return;
}
}
......@@ -301,12 +308,12 @@ void ServiceReap(Service *service)
if (service->onRestart != NULL) {
ret = ExecRestartCmd(service);
if (ret != SERVICE_SUCCESS) {
printf("[Init] SetOnRestart fail \n");
INIT_LOGE("SetOnRestart fail \n");
}
}
ret = ServiceStart(service);
if (ret != SERVICE_SUCCESS) {
INIT_LOGE("[Init] reap service %s start failed!\n", service->name);
INIT_LOGE("reap service %s start failed!\n", service->name);
}
service->attribute &= (~SERVICE_ATTR_NEED_RESTART);
......
......@@ -40,17 +40,17 @@ static int g_servicesCnt = 0;
void DumpAllServices()
{
printf("[Init] Ready to dump all services:\n");
printf("[Init] total service number: %d\n", g_servicesCnt);
INIT_LOGD("Ready to dump all services:\n");
INIT_LOGD("total service number: %d\n", g_servicesCnt);
for (int i = 0; i < g_servicesCnt; i++) {
printf("\tservice name: [%s]\n", g_services[i].name);
printf("\tpath :");
INIT_LOGD("\tservice name: [%s]\n", g_services[i].name);
INIT_LOGD("\tpath :");
for (int j = 0; j < g_services[i].pathArgsCnt; j++) {
printf(" %s", g_services[i].pathArgs[j]);
INIT_LOGD(" %s", g_services[i].pathArgs[j]);
}
printf("\n");
INIT_LOGD("\n");
}
printf("[Init] Dump all services finished\n");
INIT_LOGD("Dump all services finished\n");
}
void RegisterServices(Service* services, int servicesCnt)
......@@ -97,18 +97,18 @@ static int GetServiceName(const cJSON* curArrItem, Service* curServ)
{
char* fieldStr = cJSON_GetStringValue(cJSON_GetObjectItem(curArrItem, "name"));
if (fieldStr == NULL) {
INIT_LOGE("[init] GetServiceName cJSON_GetStringValue error\n");
INIT_LOGE("GetServiceName cJSON_GetStringValue error\n");
return SERVICE_FAILURE;
}
size_t strLen = strlen(fieldStr);
if (strLen == 0 || strLen > MAX_SERVICE_NAME) {
INIT_LOGE("[init] GetServiceName strLen = %d, error\n", strLen);
INIT_LOGE("GetServiceName strLen = %d, error\n", strLen);
return SERVICE_FAILURE;
}
if (memcpy_s(curServ->name, MAX_SERVICE_NAME, fieldStr, strLen) != EOK) {
INIT_LOGE("[init] GetServiceName memcpy_s error\n");
INIT_LOGE("GetServiceName memcpy_s error\n");
return SERVICE_FAILURE;
}
curServ->name[strLen] = '\0';
......@@ -142,7 +142,7 @@ static cJSON* GetArrItem(const cJSON* fileRoot, int* arrSize, const char* arrNam
{
cJSON* arrItem = cJSON_GetObjectItemCaseSensitive(fileRoot, arrName);
if (!cJSON_IsArray(arrItem)) {
printf("[Init] GetArrItem, item %s is not an array!\n", arrName);
INIT_LOGE("GetArrItem, item %s is not an array!\n", arrName);
return NULL;
}
......@@ -162,7 +162,7 @@ static int GetWritepidStrings(const cJSON *curArrItem, Service *curServ)
}
if (writepidCnt > MAX_WRITEPID_FILES) {
INIT_LOGE("[Init] GetWritepidStrings, too many writepid[cnt %d] for one service, should not exceed %d.\n",
INIT_LOGE("GetWritepidStrings, too many writepid[cnt %d] for one service, should not exceed %d.\n",
writepidCnt, MAX_WRITEPID_FILES);
return SERVICE_FAILURE;
}
......@@ -170,7 +170,7 @@ static int GetWritepidStrings(const cJSON *curArrItem, Service *curServ)
for (int i = 0; i < writepidCnt; ++i) {
if (!cJSON_GetArrayItem(filedJ, i) || !cJSON_GetStringValue(cJSON_GetArrayItem(filedJ, i))
|| strlen(cJSON_GetStringValue(cJSON_GetArrayItem(filedJ, i))) <= 0) { // check all errors
INIT_LOGE("[Init] GetWritepidStrings, parse item[%d] error.\n", i);
INIT_LOGE("GetWritepidStrings, parse item[%d] error.\n", i);
return SERVICE_FAILURE;
}
......@@ -178,11 +178,11 @@ static int GetWritepidStrings(const cJSON *curArrItem, Service *curServ)
size_t strLen = strlen(fieldStr);
curServ->writepidFiles[i] = (char *)malloc(sizeof(char) * strLen + 1);
if (curServ->writepidFiles[i] == NULL) {
INIT_LOGE("[Init] GetWritepidStrings, malloc item[%d] error.\n", i);
INIT_LOGE("GetWritepidStrings, malloc item[%d] error.\n", i);
return SERVICE_FAILURE;
}
if (memcpy_s(curServ->writepidFiles[i], strLen + 1, fieldStr, strLen) != EOK) {
INIT_LOGE("[Init] GetWritepidStrings, memcpy_s error.\n");
INIT_LOGE("GetWritepidStrings, memcpy_s error.\n");
return SERVICE_FAILURE;
}
curServ->writepidFiles[i][strLen] = '\0';
......@@ -195,13 +195,13 @@ static int GetGidOneItem(const cJSON *curArrItem, Service *curServ) // gi
{
cJSON* filedJ = cJSON_GetObjectItem(curArrItem, GID_STR_IN_CFG);
if (filedJ == NULL) {
INIT_LOGE("[Init] GetGidOneItem, gid is not an item.\n");
return SERVICE_FAILURE; // not found
INIT_LOGE("GetGidOneItem, gid is not found too, but ok.\n");
return SERVICE_SUCCESS; // not found
}
curServ->servPerm.gIDCnt = 1;
curServ->servPerm.gIDArray = (gid_t *)malloc(sizeof(gid_t));
if (curServ->servPerm.gIDArray == NULL) {
INIT_LOGE("[Init] GetGidOneItem, can't malloc, error.\n");
INIT_LOGE("GetGidOneItem, can't malloc, error.\n");
return SERVICE_FAILURE;
}
......@@ -209,7 +209,7 @@ static int GetGidOneItem(const cJSON *curArrItem, Service *curServ) // gi
char* fieldStr = cJSON_GetStringValue(filedJ);
gid_t gID = DecodeUid(fieldStr);
if (gID == (gid_t)(-1)) {
INIT_LOGE("[Init] GetGidOneItem, DecodeUid %s error.\n", fieldStr);
INIT_LOGE("GetGidOneItem, DecodeUid %s error.\n", fieldStr);
return SERVICE_FAILURE;
}
curServ->servPerm.gIDArray[0] = gID;
......@@ -219,14 +219,14 @@ static int GetGidOneItem(const cJSON *curArrItem, Service *curServ) // gi
if (cJSON_IsNumber(filedJ)) {
gid_t gID = (int)cJSON_GetNumberValue(filedJ);
if (gID < 0) {
INIT_LOGE("[Init] GetGidOneItem, gID = %d error.\n", gID);
INIT_LOGE("GetGidOneItem, gID = %d error.\n", gID);
return SERVICE_FAILURE;
}
curServ->servPerm.gIDArray[0] = gID;
return SERVICE_SUCCESS;
}
INIT_LOGE("[Init] GetGidOneItem, this gid is neither a string nor a number, error.\n");
INIT_LOGE("GetGidOneItem, this gid is neither a string nor a number, error.\n");
return SERVICE_FAILURE;
}
......@@ -235,19 +235,19 @@ static int GetGidArray(const cJSON *curArrItem, Service *curServ) // gid
int gIDCnt = 0;
cJSON* filedJ = GetArrItem(curArrItem, &gIDCnt, GID_STR_IN_CFG); // "gid" must have 1 item.
if (gIDCnt <= 0) { // not a array, but maybe a item?
INIT_LOGE("[Init] GetGidArray, gid is not a list.\n");
INIT_LOGE("GetGidArray, gid is not a list.\n");
return GetGidOneItem(curArrItem, curServ);
}
if (gIDCnt > NGROUPS_MAX + 1) {
INIT_LOGE("[Init] GetGidArray, too many gids[cnt %d] for one service, should not exceed %d.\n",
INIT_LOGE("GetGidArray, too many gids[cnt %d] for one service, should not exceed %d.\n",
gIDCnt, NGROUPS_MAX + 1);
return SERVICE_FAILURE;
}
curServ->servPerm.gIDArray = (gid_t *)malloc(sizeof(gid_t) * gIDCnt);
if (curServ->servPerm.gIDArray == NULL) {
INIT_LOGE("[init] GetGidArray malloc error\n");
INIT_LOGE("GetGidArray malloc error\n");
return SERVICE_FAILURE;
}
curServ->servPerm.gIDCnt = gIDCnt;
......@@ -255,13 +255,13 @@ static int GetGidArray(const cJSON *curArrItem, Service *curServ) // gid
for (; i < gIDCnt; ++i) {
if (cJSON_GetArrayItem(filedJ, i) == NULL || !cJSON_GetStringValue(cJSON_GetArrayItem(filedJ, i))
|| strlen(cJSON_GetStringValue(cJSON_GetArrayItem(filedJ, i))) <= 0) { // check all errors
INIT_LOGE("[Init] GetGidArray, parse item[%d] as string, error.\n", i);
INIT_LOGE("GetGidArray, parse item[%d] as string, error.\n", i);
break;
}
char* fieldStr = cJSON_GetStringValue(cJSON_GetArrayItem(filedJ, i));
gid_t gID = DecodeUid(fieldStr);
if ((gID) == (gid_t)(-1)) {
INIT_LOGE("[Init] GetGidArray, DecodeUid item[%d] error.\n", i);
INIT_LOGE("GetGidArray, DecodeUid item[%d] error.\n", i);
return SERVICE_FAILURE;
}
curServ->servPerm.gIDArray[i] = gID;
......@@ -271,12 +271,12 @@ static int GetGidArray(const cJSON *curArrItem, Service *curServ) // gid
}
for (i = 0; i < gIDCnt; ++i) {
if (cJSON_GetArrayItem(filedJ, i) == NULL || !cJSON_IsNumber(cJSON_GetArrayItem(filedJ, i))) {
INIT_LOGE("[Init] GetGidArray, parse item[%d] as number, error.\n", i);
INIT_LOGE("GetGidArray, parse item[%d] as number, error.\n", i);
break;
}
gid_t gID = (int)cJSON_GetNumberValue(cJSON_GetArrayItem(filedJ, i));
if (gID < 0) {
INIT_LOGE("[init] GetGidArray gID = %d, error\n", gID);
INIT_LOGE("GetGidArray gID = %d, error\n", gID);
break;
}
curServ->servPerm.gIDArray[i] = gID;
......@@ -289,19 +289,19 @@ static int GetServicePathAndArgs(const cJSON* curArrItem, Service* curServ)
{
cJSON* pathItem = cJSON_GetObjectItem(curArrItem, "path");
if (!cJSON_IsArray(pathItem)) {
INIT_LOGE("[init] GetServicePathAndArgs path item not found or not a array\n");
INIT_LOGE("GetServicePathAndArgs path item not found or not a array\n");
return SERVICE_FAILURE;
}
int arrSize = cJSON_GetArraySize(pathItem);
if (arrSize <= 0 || arrSize > MAX_PATH_ARGS_CNT) { // array size invalid
INIT_LOGE("[init] GetServicePathAndArgs arrSize = %d, error\n", arrSize);
INIT_LOGE("GetServicePathAndArgs arrSize = %d, error\n", arrSize);
return SERVICE_FAILURE;
}
curServ->pathArgs = (char**)malloc((arrSize + 1) * sizeof(char*));
if (curServ->pathArgs == NULL) {
INIT_LOGE("[init] GetServicePathAndArgs malloc 1 error\n");
INIT_LOGE("GetServicePathAndArgs malloc 1 error\n");
return SERVICE_FAILURE;
}
for (int i = 0; i < arrSize + 1; ++i) {
......@@ -314,16 +314,16 @@ static int GetServicePathAndArgs(const cJSON* curArrItem, Service* curServ)
if (curParam == NULL || strlen(curParam) > MAX_ONE_ARG_LEN) {
// resources will be released by function: ReleaseServiceMem
if (curParam == NULL) {
INIT_LOGE("[init] GetServicePathAndArgs curParam == NULL, error\n");
INIT_LOGE("GetServicePathAndArgs curParam == NULL, error\n");
} else {
INIT_LOGE("[init] GetServicePathAndArgs strlen = %d, error\n", strlen(curParam));
INIT_LOGE("GetServicePathAndArgs strlen = %d, error\n", strlen(curParam));
}
return SERVICE_FAILURE;
}
if (i == 0 && IsForbidden(curParam)) {
// resources will be released by function: ReleaseServiceMem
INIT_LOGE("[init] GetServicePathAndArgs i == 0 && IsForbidden, error\n");
INIT_LOGE("GetServicePathAndArgs i == 0 && IsForbidden, error\n");
return SERVICE_FAILURE;
}
......@@ -331,13 +331,13 @@ static int GetServicePathAndArgs(const cJSON* curArrItem, Service* curServ)
curServ->pathArgs[i] = (char*)malloc(paramLen + 1);
if (curServ->pathArgs[i] == NULL) {
// resources will be released by function: ReleaseServiceMem
INIT_LOGE("[init] GetServicePathAndArgs i == 0 && IsForbidden, error\n");
INIT_LOGE("GetServicePathAndArgs i == 0 && IsForbidden, error\n");
return SERVICE_FAILURE;
}
if (memcpy_s(curServ->pathArgs[i], paramLen + 1, curParam, paramLen) != EOK) {
// resources will be released by function: ReleaseServiceMem
INIT_LOGE("[init] GetServicePathAndArgs malloc 2 error.\n");
INIT_LOGE("GetServicePathAndArgs malloc 2 error.\n");
return SERVICE_FAILURE;
}
curServ->pathArgs[i][paramLen] = '\0';
......@@ -356,7 +356,7 @@ static int GetServiceNumber(const cJSON* curArrItem, Service* curServ, const cha
}
if (!cJSON_IsNumber(filedJ)) {
INIT_LOGE("[Init] GetServiceNumber, %s is null or is not a number, error.\n", targetField);
INIT_LOGE("GetServiceNumber, %s is null or is not a number, error.\n", targetField);
return SERVICE_FAILURE;
}
......@@ -364,7 +364,7 @@ static int GetServiceNumber(const cJSON* curArrItem, Service* curServ, const cha
// important value allow < 0
if (strncmp(targetField, IMPORTANT_STR_IN_CFG, strlen(IMPORTANT_STR_IN_CFG)) != 0) {
if (value < 0) {
INIT_LOGE("[Init] GetServiceNumber, value = %d, error.\n", value);
INIT_LOGE("GetServiceNumber, value = %d, error.\n", value);
return SERVICE_FAILURE;
}
}
......@@ -388,7 +388,7 @@ static int GetServiceNumber(const cJSON* curArrItem, Service* curServ, const cha
curServ->attribute |= SERVICE_ATTR_DISABLED;
}
} else {
INIT_LOGE("[Init] GetServiceNumber, item = %s, not expected, error.\n", targetField);
INIT_LOGE("GetServiceNumber, item = %s, not expected, error.\n", targetField);
return SERVICE_FAILURE;
}
return SERVICE_SUCCESS;
......@@ -398,15 +398,15 @@ static int GetUidStringNumber(const cJSON *curArrItem, Service *curServ)
{
cJSON* filedJ = cJSON_GetObjectItem(curArrItem, UID_STR_IN_CFG);
if (filedJ == NULL) {
INIT_LOGE("[Init] GetUidStringNumber, %s not found, error.\n", UID_STR_IN_CFG);
return SERVICE_FAILURE; // not found
INIT_LOGE("GetUidStringNumber, %s not found, but ok.\n", UID_STR_IN_CFG);
return SERVICE_SUCCESS; // uID not found, but ok.
}
if (cJSON_IsString(filedJ)) {
char* fieldStr = cJSON_GetStringValue(filedJ);
int uID = DecodeUid(fieldStr);
if (uID < 0) {
INIT_LOGE("[Init] GetUidStringNumber, DecodeUid %s error.\n", fieldStr);
INIT_LOGE("GetUidStringNumber, DecodeUid %s error.\n", fieldStr);
return SERVICE_FAILURE;
}
curServ->servPerm.uID = uID;
......@@ -416,14 +416,14 @@ static int GetUidStringNumber(const cJSON *curArrItem, Service *curServ)
if (cJSON_IsNumber(filedJ)) {
int uID = (int)cJSON_GetNumberValue(filedJ);
if (uID < 0) {
INIT_LOGE("[Init] GetUidStringNumber, uID = %d error.\n", uID);
INIT_LOGE("GetUidStringNumber, uID = %d error.\n", uID);
return SERVICE_FAILURE;
}
curServ->servPerm.uID = uID;
return SERVICE_SUCCESS;
}
INIT_LOGE("[Init] GetUidStringNumber, this uid is neither a string nor a number, error.\n");
INIT_LOGE("GetUidStringNumber, this uid is neither a string nor a number, error.\n");
return SERVICE_FAILURE;
}
......@@ -442,9 +442,8 @@ static int SplitString(char *srcPtr, char **dstPtr)
}
dstPtr[i] = "\0";
int num = i;
for (int j = 0; j < num; j++)
{
printf("dstPtr[%d] is %s \n", j, dstPtr[j]);
for (int j = 0; j < num; j++) {
INIT_LOGI("dstPtr[%d] is %s \n", j, dstPtr[j]);
}
return num;
}
......@@ -463,7 +462,7 @@ enum SockOptionTab
static int ParseServiceSocket(char **opt, const int optNum, struct ServiceSocket *sockopt)
{
printf("[init] ParseServiceSocket\n");
INIT_LOGI("ParseServiceSocket\n");
if (optNum != SOCK_OPT_NUMS) {
return -1;
}
......@@ -474,7 +473,6 @@ static int ParseServiceSocket(char **opt, const int optNum, struct ServiceSocket
if (opt[SERVICE_SOCK_NAME] == NULL) {
return -1;
}
printf("[init] ParseServiceSocket SERVICE_SOCK_NAME is %s \n", opt[SERVICE_SOCK_NAME]);
int ret = memcpy_s(sockopt->name, MAX_SOCK_NAME_LEN, opt[SERVICE_SOCK_NAME], MAX_SOCK_NAME_LEN - 1);
if (ret != 0) {
return -1;
......@@ -483,7 +481,6 @@ static int ParseServiceSocket(char **opt, const int optNum, struct ServiceSocket
if (opt[SERVICE_SOCK_TYPE] == NULL) {
return -1;
}
printf("[init] ParseServiceSocket SERVICE_SOCK_TYPE is %s \n", opt[SERVICE_SOCK_TYPE]);
sockopt->type =
strncmp(opt[SERVICE_SOCK_TYPE], "stream", strlen(opt[SERVICE_SOCK_TYPE])) == 0 ? SOCK_STREAM :
(strncmp(opt[SERVICE_SOCK_TYPE], "dgram", strlen(opt[SERVICE_SOCK_TYPE])) == 0 ? SOCK_DGRAM : SOCK_SEQPACKET);
......@@ -491,35 +488,29 @@ static int ParseServiceSocket(char **opt, const int optNum, struct ServiceSocket
if (opt[SERVICE_SOCK_PERM] == NULL) {
return -1;
}
printf("[init] ParseServiceSocket SERVICE_SOCK_PERM is %s \n", opt[SERVICE_SOCK_PERM]);
sockopt->perm = strtoul(opt[SERVICE_SOCK_PERM], 0, 8); //a??a8????
sockopt->perm = strtoul(opt[SERVICE_SOCK_PERM], 0, 8); //¡Áa?¡¥?a8????
if (opt[SERVICE_SOCK_UID] == NULL) {
return -1;
}
printf("[init] ParseServiceSocket SERVICE_SOCK_UID is %s \n", opt[SERVICE_SOCK_UID]);
int uuid = DecodeUid(opt[SERVICE_SOCK_UID]);
if (uuid < 0) {
return -1;
}
sockopt->uid = uuid;
printf("[init] ParseServiceSocket uuid is %d \n", uuid);
if (opt[SERVICE_SOCK_GID] == NULL) {
return -1;
}
printf("[init] ParseServiceSocket SERVICE_SOCK_GID is %s \n", opt[SERVICE_SOCK_GID]);
int ggid = DecodeUid(opt[SERVICE_SOCK_GID]);
if (ggid < 0) {
return -1;
}
sockopt->gid = ggid;
printf("[init] ParseServiceSocket ggid is %d \n", ggid);
if (opt[SERVICE_SOCK_SETOPT] == NULL) {
return -1;
}
printf("[init] ParseServiceSocket SERVICE_SOCK_SETOPT is %s \n", opt[SERVICE_SOCK_SETOPT]);
sockopt->passcred = strncmp(opt[SERVICE_SOCK_SETOPT], "passcred", strlen(opt[SERVICE_SOCK_SETOPT])) == 0 ? true : false;
sockopt->next = NULL;
return 0;
......@@ -527,7 +518,7 @@ static int ParseServiceSocket(char **opt, const int optNum, struct ServiceSocket
static int GetServiceSocket(const cJSON* curArrItem, Service* curServ)
{
printf("[init] GetServiceSocket \n");
INIT_LOGI("GetServiceSocket \n");
cJSON* filedJ = cJSON_GetObjectItem(curArrItem, "socket");
if (!cJSON_IsArray(filedJ)) {
return SERVICE_FAILURE;
......@@ -537,7 +528,6 @@ static int GetServiceSocket(const cJSON* curArrItem, Service* curServ)
if (sockCnt <= 0) {
return SERVICE_FAILURE;
}
printf("[init] GetServiceSocket sockCnt is %d \n", sockCnt);
curServ->socketCfg = NULL;
for (int i = 0; i < sockCnt; ++i) {
cJSON* sockJ = cJSON_GetArrayItem(filedJ, i);
......@@ -550,12 +540,10 @@ static int GetServiceSocket(const cJSON* curArrItem, Service* curServ)
if (num != SOCK_OPT_NUMS) {
return SERVICE_FAILURE;
}
printf("[init] GetServiceSocket num is %d \n", num);
struct ServiceSocket *socktmp = (struct ServiceSocket *)calloc(1, sizeof(struct ServiceSocket));
if (!socktmp) {
return SERVICE_FAILURE;
}
printf("[init] ParseServiceSocket\n");
int ret = ParseServiceSocket(tmpStr, SOCK_OPT_NUMS, socktmp);
if (ret < 0) {
return SERVICE_FAILURE;
......@@ -572,7 +560,7 @@ static int GetServiceSocket(const cJSON* curArrItem, Service* curServ)
static int GetServiceOnRestart(const cJSON* curArrItem, Service* curServ)
{
printf("[init] GetServiceOnRestart \n");
INIT_LOGI("GetServiceOnRestart \n");
cJSON* filedJ = cJSON_GetObjectItem(curArrItem, "onrestart");
if (!cJSON_IsArray(filedJ)) {
return SERVICE_FAILURE;
......@@ -597,8 +585,6 @@ static int GetServiceOnRestart(const cJSON* curArrItem, Service* curServ)
}
char *cmdStr = cJSON_GetStringValue(cmdJ);
ParseCmdLine(cmdStr, &curServ->onRestart->cmdLine[i]);
printf("[init] SetOnRestart cmdLine->name %s cmdLine->cmdContent %s \n", curServ->onRestart->cmdLine[i].name,
curServ->onRestart->cmdLine[i].cmdContent);
}
return SERVICE_SUCCESS;
}
......@@ -626,7 +612,7 @@ static int CheckServiceKeyName(const cJSON* curService)
if(i < keyListSize) {
child = child->next;
} else {
INIT_LOGE("[Init] CheckServiceKeyName, key name %s is not found. error.\n", child->string);
INIT_LOGE("CheckServiceKeyName, key name %s is not found. error.\n", child->string);
return SERVICE_FAILURE;
}
}
......@@ -638,20 +624,20 @@ void ParseAllServices(const cJSON* fileRoot)
int servArrSize = 0;
cJSON* serviceArr = GetArrItem(fileRoot, &servArrSize, SERVICES_ARR_NAME_IN_JSON);
if (serviceArr == NULL) {
printf("[Init] InitReadCfg, get array %s failed.\n", SERVICES_ARR_NAME_IN_JSON);
INIT_LOGE("ParseAllServices, get array %s failed.\n", SERVICES_ARR_NAME_IN_JSON);
return;
}
printf("[Init] servArrSize is %d \n", servArrSize);
INIT_LOGI("servArrSize is %d \n", servArrSize);
if (servArrSize > MAX_SERVICES_CNT_IN_FILE) {
printf("[Init] InitReadCfg, too many services[cnt %d] detected, should not exceed %d.\n",
INIT_LOGE("ParseAllServices, too many services[cnt %d] detected, should not exceed %d.\n",
servArrSize, MAX_SERVICES_CNT_IN_FILE);
return;
}
Service* retServices = (Service*)realloc(g_services, sizeof(Service) * (g_servicesCnt + servArrSize));
if (retServices == NULL) {
printf("[Init] InitReadCfg, realloc for %s arr failed! %d.\n", SERVICES_ARR_NAME_IN_JSON, servArrSize);
INIT_LOGE("ParseAllServices, realloc for %s arr failed! %d.\n", SERVICES_ARR_NAME_IN_JSON, servArrSize);
return;
}
// Skip already saved services,
......@@ -669,7 +655,6 @@ void ParseAllServices(const cJSON* fileRoot)
tmp[i].attribute |= SERVICE_ATTR_INVALID;
continue;
}
tmp[i].servPerm.uID = (uid_t)(-1); // set 0xffffffff as init value
int ret1 = GetServiceName(curItem, &tmp[i]);
int ret2 = GetServicePathAndArgs(curItem, &tmp[i]);
int ret3 = GetUidStringNumber(curItem, &tmp[i]); // uid in string or number form
......@@ -685,22 +670,12 @@ void ParseAllServices(const cJSON* fileRoot)
// release resources if it fails
ReleaseServiceMem(&tmp[i]);
tmp[i].attribute |= SERVICE_ATTR_INVALID;
printf("[Init] InitReadCfg, parse information for service %d failed. ", i);
printf("service name = [%s]\n", tmp[i].name);
printf("ret1=%d,ret2=%d,ret3=%d,ret4=%d,ret5=%d,ret6=%d,ret7=%d,ret8=%d,ret9=%d,reta=%d,",
ret1, ret2, ret3, ret4, ret5, ret6, ret7, ret8, ret9, reta);
INIT_LOGE("ParseAllServices, parse information for service %s failed. ", tmp[i].name);
continue;
} else {
printf("[init] ParseAllServices ParseAllServices Service[%d] name=%s, uid=%d, critical=%d, disabled=%d\n",
INIT_LOGD("ParseAllServices ParseAllServices Service[%d] name=%s, uid=%d, critical=%d, disabled=%d\n",
i, tmp[i].name, tmp[i].servPerm.uID, tmp[i].attribute & SERVICE_ATTR_CRITICAL ? 1 : 0,
tmp[i].attribute & SERVICE_ATTR_DISABLED ? 1 : 0);
for(int j = 0; j < tmp[i].servPerm.gIDCnt; j++) {
printf("\t\tgIDArray[%d] = %d\n", j, tmp[i].servPerm.gIDArray[j]);
}
for(int j = 0; j < MAX_WRITEPID_FILES; j++) {
if(tmp[i].writepidFiles[j])
printf("\t\twritepidFiles[%d] = %s\n", j, tmp[i].writepidFiles[j]);
}
}
if (GetServiceSocket(curItem, &tmp[i]) != SERVICE_SUCCESS) {
// free list
......@@ -733,12 +708,12 @@ void StartServiceByName(const char* servName)
// find service by name
int servIdx = FindServiceByName(servName);
if (servIdx < 0) {
printf("[Init] StartServiceByName, cannot find service %s.\n", servName);
INIT_LOGE("StartServiceByName, cannot find service %s.\n", servName);
return;
}
if (ServiceStart(&g_services[servIdx]) != SERVICE_SUCCESS) {
printf("[Init] StartServiceByName, service %s start failed!\n", g_services[servIdx].name);
INIT_LOGE("StartServiceByName, service %s start failed!\n", g_services[servIdx].name);
}
return;
......@@ -749,12 +724,12 @@ void StopServiceByName(const char* servName)
// find service by name
int servIdx = FindServiceByName(servName);
if (servIdx < 0) {
INIT_LOGE("[Init] StopServiceByName, cannot find service %s.\n", servName);
INIT_LOGE("StopServiceByName, cannot find service %s.\n", servName);
return;
}
if (ServiceStop(&g_services[servIdx]) != SERVICE_SUCCESS) {
INIT_LOGE("[Init] StopServiceByName, service %s start failed!\n", g_services[servIdx].name);
INIT_LOGE("StopServiceByName, service %s start failed!\n", g_services[servIdx].name);
}
return;
......@@ -764,7 +739,17 @@ void StopAllServices()
{
for (int i = 0; i < g_servicesCnt; i++) {
if (ServiceStop(&g_services[i]) != SERVICE_SUCCESS) {
printf("[Init] StopAllServices, service %s stop failed!\n", g_services[i].name);
INIT_LOGE("StopAllServices, service %s stop failed!\n", g_services[i].name);
}
}
}
void StopAllServicesBeforeReboot()
{
for (int i = 0; i < g_servicesCnt; i++) {
g_services[i].attribute |= SERVICE_ATTR_INVALID;
if (ServiceStop(&g_services[i]) != SERVICE_SUCCESS) {
INIT_LOGE("StopAllServicesBeforeReboot, service %s stop failed!\n", g_services[i].name);
}
}
}
......
......@@ -23,6 +23,7 @@
#include <sys/stat.h>
#include <sys/uio.h>
#include <sys/un.h>
#include "init_log.h"
#define HOS_SOCKET_DIR "/dev/unix/socket"
#define HOS_SOCKET_ENV_PREFIX "OHOS_SOCKET_"
......@@ -32,10 +33,10 @@ static int CreateSocket(struct ServiceSocket *sockopt)
if (!sockopt || !sockopt->name) {
return -1;
}
printf("[init] CreateSocket\n");
int sockFd = socket(PF_UNIX, sockopt->type, 0);
if (sockFd < 0) {
printf("[init] socket fail %d \n", errno);
INIT_LOGE("socket fail %d \n", errno);
return -1;
}
......@@ -44,9 +45,8 @@ static int CreateSocket(struct ServiceSocket *sockopt)
addr.sun_family = AF_UNIX;
snprintf(addr.sun_path, sizeof(addr.sun_path), HOS_SOCKET_DIR"/%s",
sockopt->name);
printf("[init] addr.sun_path is %s \n", addr.sun_path);
if (access(addr.sun_path, F_OK)) {
printf("[init] %s already exist, remove it\n", addr.sun_path);
INIT_LOGE("%s already exist, remove it\n", addr.sun_path);
unlink(addr.sun_path);
}
if (sockopt->passcred) {
......@@ -59,41 +59,38 @@ static int CreateSocket(struct ServiceSocket *sockopt)
}
if (bind(sockFd, (struct sockaddr *)&addr, sizeof(addr))) {
printf("[Init] Create socket for service %s failed: %d\n", sockopt->name, errno);
INIT_LOGE("Create socket for service %s failed: %d\n", sockopt->name, errno);
unlink(addr.sun_path);
close(sockFd);
return -1;
}
printf("[init] bind socket success\n");
if (lchown(addr.sun_path, sockopt->uid, sockopt->gid)) {
unlink(addr.sun_path);
close(sockFd);
printf("[init] lchown fail %d \n", errno);
INIT_LOGE("lchown fail %d \n", errno);
return -1;
}
if (fchmodat(AT_FDCWD, addr.sun_path, sockopt->perm, AT_SYMLINK_NOFOLLOW)) {
unlink(addr.sun_path);
close(sockFd);
printf("[Init] fchmodat fail %d \n", errno);
INIT_LOGE("fchmodat fail %d \n", errno);
return -1;
}
printf("[Init] CreateSocket success \n");
INIT_LOGI("CreateSocket success \n");
return sockFd;
}
static int SetSocketEnv(int fd, char *name)
{
printf("[init] SetSocketEnv\n");
char pubName[64] = {0};
char val[16] = {0};
snprintf(pubName, sizeof(pubName), HOS_SOCKET_ENV_PREFIX"%s", name);
printf("[init] pubName is %s \n", pubName);
snprintf(val, sizeof(val), "%d", fd);
printf("[init] val is %s \n", val);
int ret = setenv(pubName, val, 1);
if (ret < 0) {
printf("[init] setenv fail %d \n", errno);
INIT_LOGE("setenv fail %d \n", errno);
return -1;
}
fcntl(fd, F_SETFD, 0);
......@@ -105,10 +102,8 @@ int DoCreateSocket(struct ServiceSocket *sockopt)
if (!sockopt) {
return -1;
}
printf("[init] DoCreateSocket \n");
struct ServiceSocket *tmpSock = sockopt;
while (tmpSock) {
printf("[init] tmpSock %p \n", tmpSock);
int fd = CreateSocket(tmpSock);
if (fd < 0) {
return -1;
......
......@@ -23,8 +23,13 @@
#include <sys/types.h>
#endif /* __LINUX__ */
#include "init_log.h"
#include "init_service_manager.h"
#ifndef OHOS_LITE
#include "init_param.h"
#include "uv.h"
#endif
#ifdef __LINUX__
static pid_t g_waitPid = -1;
......@@ -40,7 +45,7 @@ static void CheckWaitPid(pid_t sigPID)
{
if (g_waitPid == sigPID && g_waitSem != NULL) {
if (sem_post(g_waitSem) != 0) {
printf("[Init] CheckWaitPid, sem_post failed, errno %d.\n", errno);
INIT_LOGE("CheckWaitPid, sem_post failed, errno %d.\n", errno);
}
g_waitPid = -1;
g_waitSem = NULL;
......@@ -59,7 +64,7 @@ static void SigHandler(int sig)
if (sigPID <= 0) {
break;
}
printf("[Init] SigHandler, SIGCHLD received, sigPID = %d.\n", sigPID);
INIT_LOGI("SigHandler, SIGCHLD received, sigPID = %d.\n", sigPID);
#ifdef __LINUX__
CheckWaitPid(sigPID);
#endif /* __LINUX__ */
......@@ -68,16 +73,23 @@ static void SigHandler(int sig)
break;
}
case SIGTERM: {
printf("[Init] SigHandler, SIGTERM received.\n");
INIT_LOGI("SigHandler, SIGTERM received.\n");
StopAllServices();
break;
}
case SIGINT:
#ifndef OHOS_LITE
StopParamService();
#endif
exit(0);
break;
default:
printf("[Init] SigHandler, unsupported signal %d.\n", sig);
INIT_LOGI("SigHandler, unsupported signal %d.\n", sig);
break;
}
}
#ifdef OHOS_LITE
void SignalInitModule()
{
struct sigaction act;
......@@ -88,4 +100,34 @@ void SignalInitModule()
sigaction(SIGCHLD, &act, NULL);
sigaction(SIGTERM, &act, NULL);
}
#else // L2 or above, use signal event in libuv
uv_signal_t g_sigchldHandler;
uv_signal_t g_sigtermHandler;
uv_signal_t g_sigintHandler;
static void UVSignalHandler(uv_signal_t* handle, int signum)
{
SigHandler(signum);
}
void SignalInitModule()
{
int ret = uv_signal_init(uv_default_loop(), &g_sigchldHandler);
ret |= uv_signal_init(uv_default_loop(), &g_sigtermHandler);
ret |= uv_signal_init(uv_default_loop(), &g_sigintHandler);
if (ret != 0) {
INIT_LOGW("initialize signal handler failed\n");
return;
}
if (uv_signal_start(&g_sigchldHandler, UVSignalHandler, SIGCHLD) != 0) {
INIT_LOGW("start SIGCHLD handler failed\n");
}
if (uv_signal_start(&g_sigtermHandler, UVSignalHandler, SIGTERM) != 0) {
INIT_LOGW("start SIGTERM handler failed\n");
}
if (uv_signal_start(&g_sigintHandler, UVSignalHandler, SIGINT) != 0) {
INIT_LOGW("start SIGTERM handler failed\n");
}
}
#endif
......@@ -69,7 +69,7 @@ struct CmdArgs* GetCmd(const char *cmdContent, const char *delim)
FreeCmd(&ctx);
return NULL);
if (ctx->argc > MAX_CMD_NAME_LEN - 1) {
INIT_LOGE("[Init] GetCmd failed, max cmd number is 10.\n");
INIT_LOGE("GetCmd failed, max cmd number is 10.\n");
FreeCmd(&ctx);
return NULL;
}
......@@ -92,7 +92,7 @@ void FreeCmd(struct CmdArgs **cmd)
return;
}
void Logger(StatupLogLevel level, const char *format, ...)
void Logger(InitLogLevel level, const char *format, ...)
{
FILE* pFile = fopen(LOG_FILE_NAME, "a");
static char *logLeveInfo[] = { "VERBOSE", "INFO", "WARN", "ERROR", "FATAL" };
......
文件模式从 100755 更改为 100644
......@@ -25,6 +25,7 @@
#include <unistd.h>
#include "init_adapter.h"
#include "init_log.h"
#include "init_read_cfg.h"
#include "init_signal_handler.h"
#ifdef OHOS_LITE
......@@ -33,8 +34,7 @@
#ifndef OHOS_LITE
#include "device.h"
#include "property.h"
#include "property_service.h"
#include "init_param.h"
#endif
static const pid_t INIT_PROCESS_PID = 1;
......@@ -44,10 +44,10 @@ static void PrintSysInfo()
#ifdef OHOS_LITE
const char* sysInfo = GetVersionId();
if (sysInfo != NULL) {
printf("[Init] %s\n", sysInfo);
INIT_LOGE("%s\n", sysInfo);
return;
}
printf("[Init] main, GetVersionId failed!\n");
INIT_LOGE("main, GetVersionId failed!\n");
#endif
}
......@@ -68,12 +68,12 @@ int main(int argc, char * const argv[])
#ifdef OHOS_DEBUG
struct timespec tmEnter;
if (clock_gettime(CLOCK_REALTIME, &tmEnter) != 0) {
printf("[Init] main, enter, get time failed! err %d.\n", errno);
INIT_LOGE("main, enter, get time failed! err %d.\n", errno);
}
#endif // OHOS_DEBUG
if (getpid() != INIT_PROCESS_PID) {
printf("[Init] main, current process id is %d not %d, failed!\n", getpid(), INIT_PROCESS_PID);
INIT_LOGE("main, current process id is %d not %d, failed!\n", getpid(), INIT_PROCESS_PID);
return 0;
}
......@@ -85,8 +85,6 @@ int main(int argc, char * const argv[])
MountBasicFs();
CreateDeviceNode();
MakeSocketDir("/dev/unix/socket/", 0755);
InitPropertyService();
#endif
// 3. signal register
......@@ -95,7 +93,7 @@ int main(int argc, char * const argv[])
#ifdef OHOS_DEBUG
struct timespec tmSysInfo;
if (clock_gettime(CLOCK_REALTIME, &tmSysInfo) != 0) {
printf("[Init] main, after sysinfo, get time failed! err %d.\n", errno);
INIT_LOGE("main, after sysinfo, get time failed! err %d.\n", errno);
}
#endif // OHOS_DEBUG
......@@ -105,36 +103,27 @@ int main(int argc, char * const argv[])
#ifdef OHOS_DEBUG
struct timespec tmRcs;
if (clock_gettime(CLOCK_REALTIME, &tmRcs) != 0) {
printf("[Init] main, after rcs, get time failed! err %d.\n", errno);
INIT_LOGE("main, after rcs, get time failed! err %d.\n", errno);
}
#endif // OHOS_DEBUG
// 5. read configuration file and do jobs
InitReadCfg();
#ifndef OHOS_LITE
LoadDefaultProperty("/system/build.prop");
LoadDefaultProperty("/system/buildz.prop");
LoadDefaultProperty("/vendor/build.prop");
LoadDefaultProperty("/vendor/default.prop");
LoadDefaultProperty("/vendor/odm/etc/build.prop");
LoadDefaultProperty("/system/etc/prop.default");
#endif // OHOS_LITE
#ifdef OHOS_DEBUG
struct timespec tmCfg;
if (clock_gettime(CLOCK_REALTIME, &tmCfg) != 0) {
printf("[Init] main, after cfg, get time failed! err %d.\n", errno);
INIT_LOGE("main, after cfg, get time failed! err %d.\n", errno);
}
#endif // OHOS_DEBUG
// 6. keep process alive
#ifdef OHOS_DEBUG
printf("[Init] main, time used: sigInfo %ld ms, rcs %ld ms, cfg %ld ms.\n", \
INIT_LOGI("main, time used: sigInfo %ld ms, rcs %ld ms, cfg %ld ms.\n", \
TimeDiffMs(&tmEnter, &tmSysInfo), TimeDiffMs(&tmSysInfo, &tmRcs), TimeDiffMs(&tmRcs, &tmCfg));
#endif
printf("[Init] main, entering wait.\n");
INIT_LOGI("main, entering wait.\n");
#ifndef OHOS_LITE
StartPropertyService();
StartParamService();
#endif
while (1) {
// pause only returns when a signal was caught and the signal-catching function returned.
......
......@@ -28,6 +28,7 @@
#include <sys/sysmacros.h>
#include <sys/un.h>
#include <unistd.h>
#include "init_log.h"
#include "list.h"
#include "securec.h"
......@@ -148,7 +149,7 @@ void Trigger(const char *sysPath)
static void RetriggerUevent()
{
if (access(g_trigger, F_OK) == 0) {
printf("Skip trigger uevent, alread done\n");
INIT_LOGI("Skip trigger uevent, alread done\n");
return;
}
Trigger("/sys/class");
......@@ -158,7 +159,7 @@ static void RetriggerUevent()
if (fd >= 0) {
close(fd);
}
printf("Re-trigger uevent done\n");
INIT_LOGI("Re-trigger uevent done\n");
}
static void UeventSockInit()
......@@ -176,7 +177,7 @@ static void UeventSockInit()
int sockfd = socket(PF_NETLINK, SOCK_DGRAM | SOCK_CLOEXEC, NETLINK_KOBJECT_UEVENT);
if (sockfd < 0) {
printf("Create socket failed. %d\n", errno);
INIT_LOGE("Create socket failed. %d\n", errno);
return;
}
......@@ -184,7 +185,7 @@ static void UeventSockInit()
setsockopt(sockfd, SOL_SOCKET, SO_PASSCRED, &on, sizeof(on));
if (bind(sockfd, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
printf("Bind socket failed. %d\n", errno);
INIT_LOGE("Bind socket failed. %d\n", errno);
close(sockfd);
return;
}
......@@ -288,7 +289,7 @@ static int MakeDir(const char *path, mode_t mode)
{
int rc = mkdir(path, mode);
if (rc < 0 && errno != EEXIST) {
printf("Create %s failed. %d\n", path, errno);
INIT_LOGE("Create %s failed. %d\n", path, errno);
}
return rc;
}
......@@ -352,7 +353,7 @@ static char **ParsePlatformBlockDevice(const struct Uevent *uevent)
p = strdup(uevent->partitionName);
CheckValidPartitionName(p);
if (strcmp(uevent->partitionName, p)) {
printf("Linking partition '%s' as '%s'\n", uevent->partitionName, p);
INIT_LOGI("Linking partition '%s' as '%s'\n", uevent->partitionName, p);
}
if (asprintf(&links[linkNum], "%s/by-name/%s", linkPath, p) > 0) {
linkNum++;
......@@ -388,7 +389,7 @@ static void MakeDevice(const char *devpath, const char *path, int block, int maj
setegid(gid);
if (mknod(devpath, mode, dev) != 0) {
if (errno != EEXIST) {
printf("Make device node[%d, %d] failed. %d\n", major, minor, errno);
INIT_LOGE("Make device node[%d, %d] failed. %d\n", major, minor, errno);
}
}
}
......@@ -410,7 +411,7 @@ int MkdirRecursive(const char *pathName, mode_t mode)
continue;
}
if ((unsigned int)width > sizeof(buf) - 1) {
printf("path too long for MkdirRecursive\n");
INIT_LOGE("path too long for MkdirRecursive\n");
return -1;
}
if (memcpy_s(buf, width, pathName, width) != 0) {
......@@ -461,11 +462,11 @@ static void MakeLink(const char *oldPath, const char *newPath)
buf[width] = 0;
int ret = MkdirRecursive(buf, DEFAULT_DIR_MODE);
if (ret) {
printf("Failed to create directory %s: %s (%d)\n", buf, strerror(errno), errno);
INIT_LOGE("Failed to create directory %s: %s (%d)\n", buf, strerror(errno), errno);
}
ret = symlink(oldPath, newPath);
if (ret && errno != EEXIST) {
printf("Failed to symlink %s to %s: %s (%d)\n", oldPath, newPath, strerror(errno), errno);
INIT_LOGE("Failed to symlink %s to %s: %s (%d)\n", oldPath, newPath, strerror(errno), errno);
}
}
......@@ -536,7 +537,7 @@ static void AddPlatformDevice(const char *path)
name += DEV_PLAT_FORM;
}
}
printf("adding platform device %s (%s)\n", name, path);
INIT_LOGI("adding platform device %s (%s)\n", name, path);
struct PlatformNode *bus = calloc(1, sizeof(struct PlatformNode));
if (!bus) {
return;
......@@ -556,7 +557,7 @@ static void RemovePlatformDevice(const char *path)
for (node = (&g_platformNames)->prev; node != &g_platformNames; node = node->prev) {
bus = (struct PlatformNode *)(((char*)(node)) - offsetof(struct PlatformNode, list));
if (!strcmp(path, bus->path)) {
printf("removing platform device %s\n", bus->name);
INIT_LOGI("removing platform device %s\n", bus->name);
free(bus->path);
ListRemove(node);
free(bus);
......@@ -693,7 +694,7 @@ static void HandleDeviceEvent(struct Uevent *event, char *devpath, int len, cons
links = GetCharacterDeviceSymlinks(event);
if (!devpath[0]) {
if (snprintf_s(devpath, len, len - 1, "%s%s", base, name) == -1) {
printf("[Init] snprintf_s err \n");
INIT_LOGE("snprintf_s err \n");
goto err;
}
}
......@@ -804,7 +805,7 @@ void UeventInit()
int main(const int argc, const char **argv)
{
printf("Uevent demo starting...\n");
INIT_LOGI("Uevent demo starting...\n");
UeventInit();
return 0;
}
......@@ -22,21 +22,25 @@ if (defined(ohos_lite)) {
"-lpthread",
"-lm",
]
defines = ["OHOS_LITE"]
defines = [ "OHOS_LITE" ]
if (storage_type == "emmc") {
defines += [ "USE_EMMC_STORAGE" ]
}
include_dirs = [ "//base/startup/init_lite/services/include" ]
include_dirs = [
"//base/startup/init_lite/services/include",
"//base/startup/init_lite/services/log",
]
sources = [
"//base/startup/init_lite/services/src/init_adapter.c",
"//base/startup/init_lite/services/src/init_cmds.c",
"//base/startup/init_lite/services/src/init_jobs.c",
"//base/startup/init_lite/services/src/init_service.c",
"//base/startup/init_lite/services/src/init_utils.c",
"//base/startup/init_lite/services/src/init_service_manager.c",
"//base/startup/init_lite/services/src/init_signal_handler.c",
"//base/startup/init_lite/services/src/init_utils.c",
"//base/startup/init_lite/services/src/init_reboot.c",
"cmd_func_test.cpp",
]
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册