diff --git a/initsync/BUILD.gn b/initsync/BUILD.gn index 86b0ad0703058e33e629ee37434573bf07ead162..2a2d1f2613058391fb3878cfdaec9ca17e5363c2 100644 --- a/initsync/BUILD.gn +++ b/initsync/BUILD.gn @@ -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" ] } diff --git a/initsync/src/init_sync.c b/initsync/src/init_sync.c index 24aa1cdd951b83e2fa1087bd086a4d79978c71ca..9eca4edfefc18b67773abb6123ece566ec9c1fd7 100644 --- a/initsync/src/init_sync.c +++ b/initsync/src/init_sync.c @@ -24,19 +24,19 @@ #include #include #include - +#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); diff --git a/interfaces/innerkits/include/init_reboot_api.h b/interfaces/innerkits/include/init_reboot_api.h new file mode 100644 index 0000000000000000000000000000000000000000..7495d15498b03b52b7b7b791ac61046d20a216b6 --- /dev/null +++ b/interfaces/innerkits/include/init_reboot_api.h @@ -0,0 +1,22 @@ +/* + * 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 + diff --git a/interfaces/innerkits/include/init_socket_api.h b/interfaces/innerkits/include/init_socket_api.h old mode 100755 new mode 100644 diff --git a/interfaces/innerkits/reboot/BUILD.gn b/interfaces/innerkits/reboot/BUILD.gn new file mode 100644 index 0000000000000000000000000000000000000000..5730e133f9a782c76b06b11807bf98a0b45d1b20 --- /dev/null +++ b/interfaces/innerkits/reboot/BUILD.gn @@ -0,0 +1,33 @@ +# 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", + ] +} + diff --git a/interfaces/innerkits/reboot/init_reboot_api.c b/interfaces/innerkits/reboot/init_reboot_api.c new file mode 100644 index 0000000000000000000000000000000000000000..5d8b1f54838790c637d468edcdf306fbb46b647c --- /dev/null +++ b/interfaces/innerkits/reboot/init_reboot_api.c @@ -0,0 +1,49 @@ +/* + * 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 +#include +#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; +} + diff --git a/interfaces/innerkits/socket/BUILD.gn b/interfaces/innerkits/socket/BUILD.gn old mode 100755 new mode 100644 diff --git a/interfaces/innerkits/socket/init_socket_api.c b/interfaces/innerkits/socket/init_socket_api.c old mode 100755 new mode 100644 index 1e32b61cf643e939f6e450cc7cdea2051009144a..7126f9191b8d87a26460c7c3ef8bcf55c8d561f9 --- a/interfaces/innerkits/socket/init_socket_api.c +++ b/interfaces/innerkits/socket/init_socket_api.c @@ -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; } diff --git a/ohos.build b/ohos.build old mode 100755 new mode 100644 diff --git a/services/BUILD.gn b/services/BUILD.gn index 4ba148f7a628a29d5b5647006c5fffbe5d2515e7..81fca681b88baad7ebd0bdd9257a411bb72a9f44 100644 --- a/services/BUILD.gn +++ b/services/BUILD.gn @@ -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", ] } } diff --git a/services/include/device.h b/services/include/device.h old mode 100755 new mode 100644 diff --git a/services/include/init_adapter.h b/services/include/init_adapter.h old mode 100755 new mode 100644 diff --git a/services/include/init_capability.h b/services/include/init_capability.h old mode 100755 new mode 100644 diff --git a/services/include/init_import.h b/services/include/init_import.h old mode 100755 new mode 100644 diff --git a/services/include/init_perms.h b/services/include/init_perms.h old mode 100755 new mode 100644 diff --git a/services/include/init_reboot.h b/services/include/init_reboot.h new file mode 100644 index 0000000000000000000000000000000000000000..181d811327ea1f4dfeb1bbf2c32b95ea8527687f --- /dev/null +++ b/services/include/init_reboot.h @@ -0,0 +1,21 @@ +/* + * 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 diff --git a/services/include/init_service.h b/services/include/init_service.h old mode 100755 new mode 100644 diff --git a/services/include/init_service_manager.h b/services/include/init_service_manager.h index 0040f74df6bf3d8cd0e4f675283126b5098bf215..33a8c7608bd348fc2582f9616e64a02dffa35cbf 100644 --- a/services/include/init_service_manager.h +++ b/services/include/init_service_manager.h @@ -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(); diff --git a/services/include/init_service_socket.h b/services/include/init_service_socket.h old mode 100755 new mode 100644 diff --git a/services/include/init_utils.h b/services/include/init_utils.h old mode 100755 new mode 100644 diff --git a/services/include/list.h b/services/include/list.h old mode 100755 new mode 100644 diff --git a/services/include/param/init_param.h b/services/include/param/init_param.h new file mode 100644 index 0000000000000000000000000000000000000000..34fb66f1d6e2c8a0ab9e064e58d170f0b6329822 --- /dev/null +++ b/services/include/param/init_param.h @@ -0,0 +1,136 @@ +/* + * 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 BASE_STARTUP_INIT_PARAM_H +#define BASE_STARTUP_INIT_PARAM_H +#include +#include "cJSON.h" +#include "sys_param.h" + +#ifdef __cplusplus +#if __cplusplus +extern "C" { +#endif +#endif + +typedef enum { + EVENT_PROPERTY, // 参数修改事件 + EVENT_BOOT +} EventType; + +/** + * Init 接口 + * 初始化参数服务 + * + */ +void InitParamService(); + +/** + * 对Init接口 + * 启动trigger服务。 + * + */ +void StartTriggerService(); + +/** + * Init 接口 + * 启动参数服务,在main启动的最后调用,阻赛当前线程 + * + */ +int StartParamService(); + +/** + * Init 接口 + * 停止参数服务 + * + */ +void StopParamService(); + +/** + * Init 接口 + * 加载默认的参数值 + * + */ +int LoadDefaultParams(const char *fileName); + +/** + * Init 接口 + * 安全使用,加载参数的信息,包括selinux label 等 + * + */ +int LoadParamInfos(const char *fileName); + +/** + * Init 接口 + * 加载默认参数。 + * + */ +int LoadPersistParams(); + +/** + * Init 接口 + * 设置参数,主要用于其他进程使用,通过管道修改参数 + * + */ +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 SystemTraversalParam(void (*traversalParameter)(ParamHandle handle, void* cookie), void* cookie); + +#ifdef __cplusplus +#if __cplusplus +} +#endif +#endif +#endif \ No newline at end of file diff --git a/services/include/property/property.h b/services/include/param/sys_param.h old mode 100755 new mode 100644 similarity index 53% rename from services/include/property/property.h rename to services/include/param/sys_param.h index 537641b6334cbeadd0374ba2fd451303556b4539..5500a5077e786a895d37ad9f5f693f609ae7876c --- a/services/include/property/property.h +++ b/services/include/param/sys_param.h @@ -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 #include #include @@ -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 } diff --git a/services/log/BUILD.gn b/services/log/BUILD.gn new file mode 100644 index 0000000000000000000000000000000000000000..e89c7b4b86739bd3d1e64666fe5e1c7abec42e16 --- /dev/null +++ b/services/log/BUILD.gn @@ -0,0 +1,34 @@ +# 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" + } +} diff --git a/services/src/init_log.c b/services/log/init_log.c old mode 100755 new mode 100644 similarity index 66% rename from services/src/init_log.c rename to services/log/init_log.c index bcde16fbfaf2b121a73438deafaf80a5b3cf4a0c..83c4b00d9cf19f611296d89d05469175b8cad348 --- a/services/src/init_log.c +++ b/services/log/init_log.c @@ -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); } diff --git a/services/include/init_log.h b/services/log/init_log.h old mode 100755 new mode 100644 similarity index 58% rename from services/include/init_log.h rename to services/log/init_log.h index 0a352b5c92e0fe86495e986817e346fb1c368ca0..81ddc316d7bc6a3e233892557094cbb53bcb9c3c --- a/services/include/init_log.h +++ b/services/log/init_log.h @@ -18,6 +18,7 @@ #include #include #include +#include #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 diff --git a/services/param/BUILD.gn b/services/param/BUILD.gn new file mode 100644 index 0000000000000000000000000000000000000000..fae535a04b7c4705699ecb6c1038facc59c5ee13 --- /dev/null +++ b/services/param/BUILD.gn @@ -0,0 +1,108 @@ +# 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" +} diff --git a/services/param/client/param_request.c b/services/param/client/param_request.c new file mode 100644 index 0000000000000000000000000000000000000000..bf8af8094667ea75d0d3021441abd7174e61bd97 --- /dev/null +++ b/services/param/client/param_request.c @@ -0,0 +1,160 @@ +/* + * 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 "param_request.h" + +#include +#include +#include + +#include "param_manager.h" +#include "uv.h" + +#define LABEL "Client" +#define BUFFER_SIZE 200 +#define ParamEntry(ptr, type, member) (type *)((char *)(ptr) - offsetof(type, member)) + +static ParamWorkSpace g_paramWorkSpaceReadOnly = {ATOMIC_VAR_INIT(0), {}, {}, {}}; + +static void OnWrite(uv_write_t *req, int 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 = 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 = 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); + 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_PARAM: + req->result = response->result; + break; + default: + PARAM_LOGE("not supported the command: %d", response->type); + break; + } + PARAM_LOGE("Close handle %p", handle); + free(buf->base); + uv_close((uv_handle_t*)handle, NULL); + uv_stop(req->loop); +} + +static void OnConnection(uv_connect_t *connect, int status) +{ + 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(&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); + PARAM_CHECK(ret >= 0, return, "Failed to uv_read_start response"); +} + +static int StartRequest(int cmd, RequestNode *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; +} + +int SystemSetParameter(const char *name, const char *value) +{ + PARAM_CHECK(name != NULL && value != NULL, return -1, "Invalid param"); + int ret = CheckParamName(name, 0); + PARAM_CHECK(ret == 0, return ret, "Illegal param name"); + + PARAM_LOGI("StartRequest %s", name); + u_int32_t msgSize = sizeof(RequestMsg) + strlen(name) + strlen(value) + 2; + RequestNode *request = (RequestNode *)malloc(sizeof(RequestNode) + msgSize); + PARAM_CHECK(request != NULL, return -1, "Failed to malloc for connect"); + + memset_s(request, sizeof(RequestNode), 0, sizeof(RequestNode)); + // 带字符串结束符 + 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_PARAM, request); +} + +int SystemGetParameter(const char *name, char *value, unsigned int *len) +{ + PARAM_CHECK(name != NULL && len != NULL, return -1, "The name or value is null"); + InitParamWorkSpace(&g_paramWorkSpaceReadOnly, 1, NULL); + + 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(ParamHandle handle, char *name, unsigned int 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(ParamHandle handle, char *value, unsigned int *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)(ParamHandle handle, void* cookie), void* cookie) +{ + PARAM_CHECK(traversalParameter != NULL, return -1, "The param is null"); + InitParamWorkSpace(&g_paramWorkSpaceReadOnly, 1, NULL); + return TraversalParam(&g_paramWorkSpaceReadOnly, traversalParameter, cookie); +} + +const char *SystemDetectParamChange(ParamCache *cache, + ParamEvaluatePtr evaluate, u_int32_t count, const char *parameters[][2]) +{ + PARAM_CHECK(cache != NULL && evaluate != NULL && parameters != NULL, return NULL, "The param is null"); + return DetectParamChange(&g_paramWorkSpaceReadOnly, cache, evaluate, count, parameters); +} diff --git a/services/property/cmd/property_get.c b/services/param/cmd/param_get.c old mode 100755 new mode 100644 similarity index 77% rename from services/property/cmd/property_get.c rename to services/param/cmd/param_get.c index f2d49d7be6e7adacd668cc90eb129487c11a56a4..bba06fcdf3068e54226e2dd87c0b51059775f825 --- a/services/property/cmd/property_get.c +++ b/services/param/cmd/param_get.c @@ -15,17 +15,17 @@ #include #include -#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); } + } diff --git a/services/property/cmd/property_set.c b/services/param/cmd/param_set.c old mode 100755 new mode 100644 similarity index 75% rename from services/property/cmd/property_set.c rename to services/param/cmd/param_set.c index 173a2e6aaa27dc160977e17629cab49039f95554..3c3943df95ad2df4048cecf61777cacc77536050 --- a/services/property/cmd/property_set.c +++ b/services/param/cmd/param_set.c @@ -16,24 +16,24 @@ #include #include -#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]); } } diff --git a/services/param/include/param_manager.h b/services/param/include/param_manager.h new file mode 100644 index 0000000000000000000000000000000000000000..96e754341dfc6c2757d3dd27c0e80ae308f9f012 --- /dev/null +++ b/services/param/include/param_manager.h @@ -0,0 +1,159 @@ +/* + * 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 BASE_STARTUP_PARAM_MANAGER_H +#define BASE_STARTUP_PARAM_MANAGER_H +#include +#include + +#include "init_log.h" +#include "sys_param.h" +#include "param_trie.h" +#include "securec.h" +#ifdef __cplusplus +#if __cplusplus +extern "C" { +#endif +#endif + +typedef enum { + 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/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/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 +#define SUBSTR_INFO_LABEL 1 +#define SUBSTR_INFO_TYPE 2 +#define SUBSTR_INFO_MAX 4 + +#define WORKSPACE_FLAGS_INIT 0x01 +#define WORKSPACE_FLAGS_LOADED 0x02 + +#define PARAM_LOGI(fmt, ...) STARTUP_LOGI(LABEL, fmt, ##__VA_ARGS__) +#define PARAM_LOGE(fmt, ...) STARTUP_LOGE(LABEL, fmt, ##__VA_ARGS__) + +#define PARAM_CHECK(retCode, exper, ...) \ + if (!(retCode)) { \ + PARAM_LOGE(__VA_ARGS__); \ + exper; \ + } + +#define futex(addr1, op, val, rel, addr2, val3) \ + syscall(SYS_futex, addr1, op, val, rel, addr2, val3) +#define futex_wait_always(addr1) \ + syscall(SYS_futex, addr1, FUTEX_WAIT, *(int*)(addr1), 0, 0, 0) +#define futex_wake_single(addr1) \ + syscall(SYS_futex, addr1, FUTEX_WAKE, 1, 0, 0, 0) + +typedef struct UserCred { + pid_t pid; + uid_t uid; + gid_t gid; +} UserCred; + +typedef struct { + char label[LABEL_STRING_LEN]; + UserCred cred; +} ParamSecurityLabel; + +typedef struct ParamAuditData { + const UserCred *cr; + const char *name; +} ParamAuditData; + +typedef struct { + atomic_uint_least32_t flags; + WorkSpace paramLabelSpace; + WorkSpace paramSpace; + ParamSecurityLabel label; +} ParamWorkSpace; + +typedef struct { + atomic_uint_least32_t flags; + WorkSpace persistWorkSpace; +} ParamPersistWorkSpace; + +typedef struct { + char value[128]; +} SubStringInfo; + +int InitParamWorkSpace(ParamWorkSpace *workSpace, int onlyRead, const char *context); +void CloseParamWorkSpace(ParamWorkSpace *workSpace); + +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 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 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(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 BuildParamContent(char *content, u_int32_t contentSize, const char *name, const char *value); +ParamWorkSpace *GetParamWorkSpace(); + +typedef void (*TraversalParamPtr)(ParamHandle handle, void* context); +typedef struct { + TraversalParamPtr traversalParamPtr; + void *context; +} ParamTraversalContext; +int TraversalParam(ParamWorkSpace *workSpace, TraversalParamPtr walkFunc, void *cookie); + +const char *DetectParamChange(ParamWorkSpace *workSpace, ParamCache *cache, + ParamEvaluatePtr evaluate, u_int32_t count, const char *parameters[][2]); + +#ifdef __cplusplus +#if __cplusplus +} +#endif +#endif +#endif \ No newline at end of file diff --git a/services/property/include/property_request.h b/services/param/include/param_request.h old mode 100755 new mode 100644 similarity index 81% rename from services/property/include/property_request.h rename to services/param/include/param_request.h index 4b85810c41e53892e89b208d087354d827a4652a..d2ed318d6b17c3583b863d2e1f69ac48c2412ea7 --- a/services/property/include/property_request.h +++ b/services/param/include/param_request.h @@ -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 -#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; diff --git a/services/include/trigger/trigger.h b/services/param/include/param_service.h old mode 100755 new mode 100644 similarity index 61% rename from services/include/trigger/trigger.h rename to services/param/include/param_service.h index d974ccfce1c58b446a4975db04ccb6fd5bd542af..8a0d8554937c2b103626963113db0b6364832152 --- a/services/include/trigger/trigger.h +++ b/services/param/include/param_service.h @@ -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 -#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 diff --git a/services/property/include/property_trie.h b/services/param/include/param_trie.h old mode 100755 new mode 100644 similarity index 93% rename from services/property/include/property_trie.h rename to services/param/include/param_trie.h index fe9d86a9163d2476343714499748f5aff1e70bb6..8c3e3f9848e10b76d58ac90c1f23f8561ab15385 --- a/services/property/include/property_trie.h +++ b/services/param/include/param_trie.h @@ -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 #include #include @@ -22,7 +22,7 @@ #include #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 diff --git a/services/trigger/trigger_checker.h b/services/param/include/trigger_checker.h old mode 100755 new mode 100644 similarity index 100% rename from services/trigger/trigger_checker.h rename to services/param/include/trigger_checker.h diff --git a/services/trigger/trigger_manager.h b/services/param/include/trigger_manager.h old mode 100755 new mode 100644 similarity index 76% rename from services/trigger/trigger_manager.h rename to services/param/include/trigger_manager.h index 0fc47633893c332e1d51740a200e526d3cb9137c..4dcbf6e03769bba04b934ba866cf403580554e3c --- a/services/trigger/trigger_manager.h +++ b/services/param/include/trigger_manager.h @@ -15,7 +15,6 @@ #ifndef STARTUP_TRIGER_MANAGER_H #define STARTUP_TRIGER_MANAGER_H - #include #include #include @@ -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 diff --git a/services/trigger/trigger_processor.h b/services/param/include/trigger_processor.h old mode 100755 new mode 100644 similarity index 91% rename from services/trigger/trigger_processor.h rename to services/param/include/trigger_processor.h index 94ed8ff28ce6952516562018548d317070071f85..b57822889aaeba64a825b64946b89ca72d0718a1 --- a/services/trigger/trigger_processor.h +++ b/services/param/include/trigger_processor.h @@ -18,8 +18,8 @@ #include -#include "property.h" -#include "trigger.h" +#include "sys_param.h" +#include "init_param.h" #include "trigger_manager.h" #include "uv.h" diff --git a/services/param/manager/param_cache.c b/services/param/manager/param_cache.c new file mode 100644 index 0000000000000000000000000000000000000000..690de37e869cb0a8777f1a275013d02da97d8aae --- /dev/null +++ b/services/param/manager/param_cache.c @@ -0,0 +1,148 @@ +/* + * 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 "sys_param.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "param_manager.h" + +#define LABEL "Manager" +#define MAX_PROPERT_IN_WATCH 5 +#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) +{ + 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); + 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); + PARAM_LOGI("InitNormalMemory success, currOffset %u firstNode %u dataSize %u", + workSpace->area->currOffset, workSpace->area->firstNode, workSpace->area->dataSize); + return 0; +} + +static ParamCacheNode *AllocParamCacheNode(WorkSpace *workSpace, u_int32_t size) +{ + 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); + ParamCacheNode *cache = (ParamCacheNode *)(workSpace->area->data + workSpace->area->currOffset); + workSpace->area->currOffset += size; + return cache; +} + +static int CreateParamCache(ParamCache *cache, ParamWorkSpace *workSpace, ParamEvaluatePtr evaluate) +{ + PARAM_CHECK(cache != NULL && evaluate != NULL, return -1, "Invalid param"); + if (cache->cacheNode != NULL) { + return 0; + } + 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->paramSpace); + cache->cacheCount = 0; + cache->evaluate = evaluate; + 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 AddParamNode(ParamCache *cache, ParamWorkSpace *workSpace, const char *name, const char *defValue) +{ + PARAM_CHECK(cache != NULL && name != NULL, return -1, "Invalid param"); + PARAM_CHECK(cache->cacheCount < MAX_PROPERT_IN_WATCH, return -1, "Full param in cache"); + + ParamCacheNode *cacheNode = &cache->cacheNode[cache->cacheCount++]; + int ret = memcpy_s(cacheNode->value, sizeof(cacheNode->value), defValue, strlen(defValue)); + PARAM_CHECK(ret == 0, return -1, "Failed to copy default value"); + + 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(ParamWorkSpace *workSpace, ParamCacheNode *cacheNode) +{ + return cacheNode && ReadParamSerial(workSpace, cacheNode->handle) != cacheNode->serial; +} + +static void RefreshCacheNode(ParamWorkSpace *workSpace, ParamCacheNode *cacheNode) +{ + cacheNode->serial = ReadParamSerial(workSpace, cacheNode->handle); + u_int32_t len = sizeof(cacheNode->value); + ReadParamValue(workSpace, cacheNode->handle, cacheNode->value, &len); +} + +static const char *TestParamCache(ParamCache *cache, ParamWorkSpace *workSpace) +{ + int changeDetected = 0; + if (pthread_mutex_trylock(&cache->lock)) { + return cache->evaluate(cache->cacheCount, cache->cacheNode); + } + if (GetWorkSpaceSerial(&workSpace->paramSpace) != cache->serial) { + changeDetected = 1; + } + for (u_int32_t i = 0; (i < cache->cacheCount) && changeDetected == 0; i++) { + changeDetected = CheckCacheNode(workSpace, &cache->cacheNode[i]); + } + if (changeDetected) { + for (u_int32_t i = 0; i < cache->cacheCount; i++) { + RefreshCacheNode(workSpace, &cache->cacheNode[i]); + } + cache->serial = GetWorkSpaceSerial(&workSpace->paramSpace); + } + pthread_mutex_unlock(&cache->lock); + + return cache->evaluate(cache->cacheCount, cache->cacheNode); +} + +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 = CreateParamCache(cache, workSpace, evaluate); + PARAM_CHECK(ret == 0, break, "Failed to create cache"); + for (u_int32_t i = 0; i < count; i++) { + ret = AddParamNode(cache, workSpace, parameters[i][0], parameters[i][1]); + PARAM_CHECK(ret == 0, break, "Failed to add param cache"); + } + PARAM_CHECK(ret == 0, break, "Failed to add param cache"); + } + pthread_mutex_unlock(&cacheLock); + return TestParamCache(cache, workSpace); +} diff --git a/services/param/manager/param_manager.c b/services/param/manager/param_manager.c new file mode 100644 index 0000000000000000000000000000000000000000..20f079e6cbe7ddfab518ed396dfeb96a179f1d59 --- /dev/null +++ b/services/param/manager/param_manager.c @@ -0,0 +1,527 @@ +/* + * 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 "param_manager.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define LABEL "Manager" + +#ifdef PARAM_SUPPORT_SELINUX +static int SelinuxAuditCallback(void *data, + __attribute__((unused))security_class_t class, char *msgBuf, size_t msgSize) +{ + 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 InitParamWorkSpace(ParamWorkSpace *workSpace, int onlyRead, const char *context) +{ + u_int32_t flags = atomic_load_explicit(&workSpace->flags, memory_order_relaxed); + if ((flags & WORKSPACE_FLAGS_INIT) == WORKSPACE_FLAGS_INIT) { + return 0; + } + +#ifdef PARAM_SUPPORT_SELINUX + union selinux_callback cb; + cb.func_audit = SelinuxAuditCallback; + selinux_set_callback(SELINUX_CB_AUDIT, cb); +#endif + +#ifdef PARAM_SUPPORT_SELINUX + if (context && fsetxattr(fd, XATTR_NAME_SELINUX, context, strlen(context) + 1, 0) != 0) { + PARAM_LOGI("fsetxattr context %s fail", context); + } +#endif + 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 CloseParamWorkSpace(ParamWorkSpace *workSpace) +{ + CloseWorkSpace(&workSpace->paramSpace); + CloseWorkSpace(&workSpace->paramLabelSpace); + atomic_store_explicit(&workSpace->flags, 0, memory_order_release); +} + +int WriteParamInfo(ParamWorkSpace *workSpace, SubStringInfo *info, int subStrNumber) +{ + 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; + if (subStrNumber >= SUBSTR_INFO_LABEL) { + label = info[SUBSTR_INFO_LABEL].value; + } else { + label = "u:object_r:default_prop:s0"; + } + if (subStrNumber >= SUBSTR_INFO_TYPE) { + type = info[SUBSTR_INFO_TYPE].value; + } else { + type = "string"; + } + + int ret = CheckParamName(name, 1); + PARAM_CHECK(ret == 0, return ret, "Illegal param name %s", name); + + // 先保存标签值 + 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 + PARAM_LOGE("Has been set label %s old label %s new label: %s", name, entry->key, label); + } + SaveIndex(&dataNode->labelIndex, offset); + return 0; +} + +int AddParam(WorkSpace *workSpace, const char *name, const char *value) +{ + PARAM_CHECK(workSpace != NULL && name != NULL && value != NULL, + return PARAM_CODE_INVALID_PARAM, "Failed to check param"); + + TrieDataNode *node = AddTrieDataNode(workSpace, name, strlen(name)); + 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)); + 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); + } + 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 0; +} + +int UpdateParam(WorkSpace *workSpace, u_int32_t *dataIndex, const char *name, const char *value) +{ + PARAM_CHECK(workSpace != NULL && name != NULL && value != NULL, + return PARAM_CODE_INVALID_PARAM, "Failed to check param"); + + DataEntry *entry = (DataEntry *)GetTrieNode(workSpace, dataIndex); + 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); + 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) { + 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 *FindParam(WorkSpace *workSpace, const char *name) +{ + 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) { + return (DataEntry *)GetTrieNode(workSpace, &node->dataIndex); + } + return NULL; +} + +int WriteParamWithCheck(ParamWorkSpace *workSpace, + const ParamSecurityLabel *srcLabel, const char *name, const char *value) +{ + 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 PARAM_CODE_NOT_INIT; + } + + 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 WriteParam(WorkSpace *workSpace, const char *name, const char *value) +{ + 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 = 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 AddParam(workSpace, name, value); +} + +int ReadParamWithCheck(ParamWorkSpace *workSpace, const char *name, ParamHandle *handle) +{ + 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 PARAM_CODE_NOT_INIT; + } + + *handle = 0; + // 取最长匹配 + 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->paramSpace, name, strlen(name), 0); + if (node != NULL && node->dataIndex != 0) { + //PARAM_LOGI("ReadParamWithCheck trie %p dataIndex %u name %s", node, node->dataIndex, name); + *handle = node->dataIndex; + return 0; + } + return PARAM_CODE_NOT_FOUND_PROP; +} + +int ReadParamValue(ParamWorkSpace *workSpace, ParamHandle handle, char *value, u_int32_t *len) +{ + 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 PARAM_CODE_NOT_INIT; + } + DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->paramSpace, &handle); + if (entry == NULL) { + return -1; + } + + if (value == NULL) { + *len = DATA_ENTRY_DATA_LEN(entry);; + return 0; + } + + while (1) { + u_int32_t serial = GetDataSerial(entry); + int ret = GetDataValue(entry, value, *len); + 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; + } + } + return 0; +} + +int ReadParamName(ParamWorkSpace *workSpace, ParamHandle handle, char *name, u_int32_t len) +{ + 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 GetDataName(entry, name, len); +} + +u_int32_t ReadParamSerial(ParamWorkSpace *workSpace, ParamHandle 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 CheckControlParamPerms(ParamWorkSpace *workSpace, + const ParamSecurityLabel *srcLabel, const char *name, const char *value) +{ + PARAM_CHECK(srcLabel != NULL && name != NULL && value != NULL, + return PARAM_CODE_INVALID_PARAM, "Invalid param"); + + char * ctrlName[] = { + "ctl.start", "ctl.stop", "ctl.restart" + }; + size_t size1 = strlen("ctl.") + strlen(value); + size_t size2 = strlen(name) + strlen(value) + 1; + size_t size = ((size1 > size2) ? size1 : size2) + 1; + char *legacyName = (char*)malloc(size); + PARAM_CHECK(legacyName != NULL, return PARAM_CODE_INVALID_PARAM, "Failed to alloc memory"); + + // 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. parameters have their name ctl. 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. to + // check permissions. + int n = snprintf_s(legacyName, size, size, "ctl.%s", value); + PARAM_CHECK(n > 0, free(legacyName); return PARAM_CODE_INVALID_PARAM, "Failed to snprintf value"); + legacyName[n] = '\0'; + + 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); + return 0; + } + break; + } + } + int n = snprintf_s(legacyName, size, size, "%s$%s", name, value); + PARAM_CHECK(n > 0, free(legacyName); return PARAM_CODE_INVALID_PARAM, "Failed to snprintf value"); + + 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 CheckParamName(const char *name, int info) +{ + size_t nameLen = strlen(name); + if (nameLen >= PARAM_VALUE_LEN_MAX) { + return PARAM_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 param name */ + for (size_t i = 0; i < nameLen; i++) { + if (name[i] == '.') { + if (name[i - 1] == '.') { + return PARAM_CODE_INVALID_NAME; + } + continue; + } + if (name[i] == '_' || name[i] == '-' || name[i] == '@' || name[i] == ':') { + continue; + } + if (isalnum(name[i])) { + continue; + } + return PARAM_CODE_INVALID_NAME; + } + return 0; +} + +int CheckParamValue(WorkSpace *workSpace, const TrieDataNode *node, const char *name, const char *value) +{ + if (IS_READY_ONLY(name)) { + if (node != NULL && node->dataIndex != 0) { + PARAM_LOGE("Read-only param was already set %s", name); + return PARAM_CODE_READ_ONLY_PROPERTY; + } + } else { + // 限制非read only的参数,防止参数值修改后,原空间不能保存 + PARAM_CHECK(strlen(value) < PARAM_VALUE_LEN_MAX, + return PARAM_CODE_INVALID_VALUE, "Illegal param value"); + } + return 0; +} + +int CheckMacPerms(ParamWorkSpace *workSpace, + const ParamSecurityLabel *srcLabel, const char *name, u_int32_t labelIndex) +{ +#ifdef PARAM_SUPPORT_SELINUX + ParamAuditData auditData; + auditData.name = name; + auditData.cr = &srcLabel->cred; + + int ret = 0; + TrieNode *node = (TrieNode *)GetTrieNode(&workSpace->paramLabelSpace, &labelIndex); + if (node != 0) { // 已经存在label + ret = selinux_check_access(srcLabel, node->key, "param_service", "set", &auditData); + } else { + ret = selinux_check_access(srcLabel, "u:object_r:default_prop:s0", "param_service", "set", &auditData); + } + return ret == 0 ? 0 : PARAM_CODE_PERMISSION_DENIED; +#else + return 0; +#endif +} + +int CanWriteParam(ParamWorkSpace *workSpace, + const ParamSecurityLabel *srcLabel, const TrieDataNode *node, const char *name, const char *value) +{ + 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 CheckControlParamPerms(workSpace, srcLabel, name, value); + } + + int ret = CheckMacPerms(workSpace, srcLabel, name, node == NULL ? 0 : node->labelIndex); + PARAM_CHECK(ret == 0, return ret, "SELinux permission check failed"); + return 0; +} + +int CanReadParam(ParamWorkSpace *workSpace, u_int32_t labelIndex, const char *name) +{ + 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->paramLabelSpace, &labelIndex); + if (node != 0) { // 已经存在label + 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 : PARAM_CODE_PERMISSION_DENIED; +#else + return 0; +#endif +} + +int GetSubStringInfo(const char *buff, u_int32_t buffLen, char delimiter, SubStringInfo *info, int subStrNumber) +{ + size_t i = 0; + // 去掉开始的空格 + for (; i < strlen(buff); i++) { + if (!isspace(buff[i])) { + break; + } + } + // 过滤掉注释 + if (buff[i] == '#') { + return -1; + } + // 分割字符串 + int spaceIsValid = 0; + int curr = 0; + int valueCurr = 0; + for (; i < buffLen; i++) { + if (buff[i] == '\n' || buff[i] == '\r') { + break; + } + if (buff[i] == delimiter && valueCurr != 0) { + info[curr].value[valueCurr] = '\0'; + valueCurr = 0; + curr++; + spaceIsValid = 1; + } else { + if (!spaceIsValid && isspace(buff[i])) { + continue; + } + if ((valueCurr + 1) >= (int)sizeof(info[curr].value)) { + continue; + } + info[curr].value[valueCurr++] = buff[i]; + } + if (curr >= subStrNumber) { + break; + } + } + if (valueCurr > 0) { + info[curr].value[valueCurr] = '\0'; + valueCurr = 0; + curr++; + } + return curr; +} + +int BuildParamContent(char *content, u_int32_t contentSize, const char *name, const char *value) +{ + 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); + 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); + offset += nameLen; + ret |= memcpy_s(content + offset, contentSize - offset, "=", 1); + offset += 1; + ret |= memcpy_s(content + offset, contentSize - offset, value, valueLen); + offset += valueLen; + content[offset] = '\0'; + PARAM_CHECK(ret == 0, return -1, "Failed to copy porperty"); + offset += 1; + return offset; +} + +int ProcessParamTraversal(WorkSpace *workSpace, TrieNode *node, void *cookie) +{ + ParamTraversalContext *context = (ParamTraversalContext *)cookie; + TrieDataNode *current = (TrieDataNode *)node; + if (current == NULL) { + return 0; + } + if (current->dataIndex == 0) { + return 0; + } + context->traversalParamPtr(current->dataIndex, context->context); + return 0; +} + +int TraversalParam(ParamWorkSpace *workSpace, TraversalParamPtr walkFunc, void *cookie) +{ + ParamTraversalContext context = { + walkFunc, cookie + }; + return TraversalTrieDataNode(&workSpace->paramSpace, + (TrieDataNode *)workSpace->paramSpace.rootNode, ProcessParamTraversal, &context); +} \ No newline at end of file diff --git a/services/property/manager/property_trie.c b/services/param/manager/param_trie.c old mode 100755 new mode 100644 similarity index 73% rename from services/property/manager/property_trie.c rename to services/param/manager/param_trie.c index a7995a9ae8b677515e8459e98b62aa4dc8923b40..b8b3b67a9b343e315fe47080aee41676a1c148a0 --- a/services/property/manager/property_trie.c +++ b/services/param/manager/param_trie.c @@ -13,7 +13,7 @@ * limitations under the License. */ -#include "property_trie.h" +#include "param_trie.h" #include #include @@ -28,21 +28,21 @@ #include #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(¤t->child, offset); current = (TrieDataNode*)GetTrieNode(workSpace, ¤t->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, ¤t->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(¤t->left, offset); return GetTrieNode(workSpace, ¤t->left); } @@ -324,7 +327,7 @@ TrieNode *AddTrieNode(WorkSpace *workSpace, TrieNode *root, const char *key, u_i next = GetTrieNode(workSpace, ¤t->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(¤t->right, offset); return GetTrieNode(workSpace, ¤t->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; } diff --git a/services/property/service/property_persist.c b/services/param/service/param_persist.c old mode 100755 new mode 100644 similarity index 60% rename from services/property/service/property_persist.c rename to services/param/service/param_persist.c index 39dd410ec7a27b6818925311f02a55718bfa3854..d538dd5351ab65d31daf810fef2bf6c226239189 --- a/services/property/service/property_persist.c +++ b/services/param/service/param_persist.c @@ -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 #include @@ -26,8 +26,8 @@ #include #include -#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); } diff --git a/services/param/service/param_service.c b/services/param/service/param_service.c new file mode 100644 index 0000000000000000000000000000000000000000..bea25c1d0998a896e49eb2853d6f277246e66dbd --- /dev/null +++ b/services/param/service/param_service.c @@ -0,0 +1,276 @@ +/* + * 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 "param_service.h" + +#include +#include +#include +#include + +#include "sys_param.h" +#include "param_manager.h" +#include "param_request.h" +#include "init_param.h" + +#include "uv.h" + +#define BUFFER_SIZE 256 +#define LABEL "Server" + +static char *g_initContext = ""; +static ParamWorkSpace g_paramWorkSpace = {ATOMIC_VAR_INIT(0), {}, {}, {}}; + +void InitParamService() +{ + int ret = InitParamWorkSpace(&g_paramWorkSpace, 0, g_initContext); + PARAM_CHECK(ret == 0, return, "Init parameter workspace fail"); +} + +int LoadDefaultParams(const char *fileName) +{ + u_int32_t flags = atomic_load_explicit(&g_paramWorkSpace.flags, memory_order_relaxed); + if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) { + return PARAM_CODE_NOT_INIT; + } + + FILE *fp = fopen(fileName, "r"); + 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), '=', info, SUBSTR_INFO_LABEL + 1); + if (subStrNumber <= SUBSTR_INFO_LABEL) { + continue; + } + + if (strncmp(info[0].value, "ctl.", strlen("ctl.")) == 0) { + PARAM_LOGE("Do not set ctl. parameters from init %s", info[0].value); + continue; + } + if (strcmp(info[0].value, "selinux.restorecon_recursive") == 0) { + PARAM_LOGE("Do not set selinux.restorecon_recursive from init %s", info[0].value); + continue; + } + int ret = CheckParamName(info[0].value, 0); + PARAM_CHECK(ret == 0, continue, "Illegal param name %s", info[0].value); + + 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); + PARAM_LOGI("LoadDefaultParams proterty success %s", fileName); + return 0; +} + +int LoadParamInfos(const char *fileName) +{ + u_int32_t flags = atomic_load_explicit(&g_paramWorkSpace.flags, memory_order_relaxed); + if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) { + return PARAM_CODE_NOT_INIT; + } + FILE *fp = fopen(fileName, "r"); + PARAM_CHECK(fp != NULL, return -1, "Open file %s fail", fileName); + SubStringInfo *info = malloc(sizeof(SubStringInfo) * SUBSTR_INFO_MAX); + char buff[BUFFER_SIZE]; + 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 = WriteParamInfo(&g_paramWorkSpace, info, subStrNumber); + PARAM_CHECK(ret == 0, continue, "Failed to write param info %d %s", ret, buff); + infoCount++; + } + fclose(fp); + free(info); + PARAM_LOGI("Load parameter info %d success %s", infoCount, fileName); + return 0; +} + +static int ProcessParamSet(RequestMsg *msg) +{ + 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])); + 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; +} + +static void OnClose(uv_handle_t *handle) +{ + free(handle); +} + +static void OnReceiveAlloc(uv_handle_t *handle, size_t suggestedSize, uv_buf_t* buf) +{ + // 这里需要按实际消息的大小申请内存,取最大消息的长度 + buf->len = sizeof(RequestMsg) + BUFFER_SIZE * 2; + buf->base = (char *)malloc(buf->len); +} + +static void OnWriteResponse(uv_write_t *req, int status) +{ + // 发送成功,释放请求内存 + PARAM_LOGI("OnWriteResponse status %d", status); + ResponseNode *node = (ResponseNode*)req; + free(node); +} + +static void SendResponse(uv_stream_t *handle, RequestType type, int result, void *content, int size) +{ + int ret = 0; + // 申请整块内存,用于回复数据和写请求 + ResponseNode *response = (ResponseNode *)malloc(sizeof(ResponseNode) + size); + 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); + 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); + 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) +{ + if (nread <= 0 || buf == NULL || buf->base == NULL) { + uv_close((uv_handle_t*)handle, OnClose); + free(buf->base); + return; + } + int freeHandle = 1; + RequestMsg *msg = (RequestMsg *)buf->base; + switch (msg->type) { + case SET_PARAM: { + freeHandle = 0; + int ret = ProcessParamSet(msg); + SendResponse(handle, SET_PARAM, ret, NULL, 0); + break; + } + default: + PARAM_LOGE("not supported the command: %d", msg->type); + break; + } + free(buf->base); + uv_close((uv_handle_t*)handle, OnClose); +} + +static void OnConnection(uv_stream_t *server, int status) +{ + 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)); + PARAM_CHECK(stream != NULL, return, "Failed to alloc stream"); + + int ret = uv_pipe_init(uv_default_loop(), (uv_pipe_t*)stream, 1); + 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); + 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); + PARAM_CHECK(ret == 0, uv_close((uv_handle_t*)stream, NULL); free(stream); + return, "Failed to uv_read_start %d", ret); +} + +void StopParamService() +{ + 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."); +} + +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); + PARAM_CHECK(ret == 0, return ret, "Failed to uv_pipe_init %d", ret); + ret = uv_pipe_bind(&pipeServer, PIPE_NAME); + 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); + 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); + PARAM_LOGI("Start service exit."); + return 0; +} + +int SystemWriteParam(const char *name, const char *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 = WritePersistParam(name, value); + PARAM_CHECK(ret == 0, return ret, "Failed to set param"); + } else { + PARAM_LOGE("Failed to set param %d name %s %s", ret, name, value); + } + // notify event to process trigger + PostParamTrigger(name, value); + return 0; +} + +int SystemReadParam(const char *name, char *value, unsigned int *len) +{ + 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 = ReadParamValue(&g_paramWorkSpace, handle, value, len); + } + return ret; +} + +ParamWorkSpace *GetParamWorkSpace() +{ + return &g_paramWorkSpace; +} + +int LoadPersistParams() +{ + return RefreshPersistParams(&g_paramWorkSpace, g_initContext); +} + +int SystemTraversalParam(void (*traversalParameter)(ParamHandle handle, void* cookie), void* cookie) +{ + PARAM_CHECK(traversalParameter != NULL, return -1, "The param is null"); + return TraversalParam(&g_paramWorkSpace, traversalParameter, cookie); +} \ No newline at end of file diff --git a/services/trigger/trigger_checker.c b/services/param/trigger/trigger_checker.c old mode 100755 new mode 100644 similarity index 74% rename from services/trigger/trigger_checker.c rename to services/param/trigger/trigger_checker.c index 948c64607dd67ee1b4157a96a5d0df155357d993..618641545c946c4a1fb1f25a0e6857b712d8b54c --- a/services/trigger/trigger_checker.c +++ b/services/param/trigger/trigger_checker.c @@ -16,18 +16,19 @@ #include "trigger_checker.h" #include #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'; diff --git a/services/trigger/trigger_manager.c b/services/param/trigger/trigger_manager.c old mode 100755 new mode 100644 similarity index 73% rename from services/trigger/trigger_manager.c rename to services/param/trigger/trigger_manager.c index cd47145af4af51521acf9fcad17728eb7b0400b4..3b187d7449450bfee990283b3aff398279a435e3 --- a/services/trigger/trigger_manager.c +++ b/services/param/trigger/trigger_manager.c @@ -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); diff --git a/services/trigger/trigger_processor.c b/services/param/trigger/trigger_processor.c old mode 100755 new mode 100644 similarity index 56% rename from services/trigger/trigger_processor.c rename to services/param/trigger/trigger_processor.c index 83e16c015d2dea10831645f2a03a58d6d9cd1206..de154b5e13c9948131b693414859a9e401dac6d7 --- a/services/trigger/trigger_processor.c +++ b/services/param/trigger/trigger_processor.c @@ -18,70 +18,59 @@ #include #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() diff --git a/services/property/BUILD.gn b/services/property/BUILD.gn deleted file mode 100755 index 92c6a37a503217c36c11cf6b7945b4f7c777b7cb..0000000000000000000000000000000000000000 --- a/services/property/BUILD.gn +++ /dev/null @@ -1,106 +0,0 @@ -# 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" -} diff --git a/services/property/client/property_request.c b/services/property/client/property_request.c deleted file mode 100755 index 22e55fb84ad6d38368add421d6e79a91d16529b8..0000000000000000000000000000000000000000 --- a/services/property/client/property_request.c +++ /dev/null @@ -1,156 +0,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. - */ - -#include "property_request.h" - -#include -#include -#include - -#include "property_manager.h" -#include "uv.h" - -#define LABEL "Client" -#define BUFFER_SIZE 200 -#define PropertyEntry(ptr, type, member) (type *)((char *)(ptr) - offsetof(type, member)) - -static PropertyWorkSpace g_propertyWorkSpaceReadOnly = {ATOMIC_VAR_INIT(0), {}, {}, {}}; - -static void OnWrite(uv_write_t* req, int status) -{ - PROPERTY_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); -} - -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); - 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); - switch (response->type) { - case SET_PROPERTY: - req->result = response->result; - break; - default: - PROPERTY_LOGE("not supported the command: %d", response->type); - break; - } - - PROPERTY_LOGE("Close handle %p", handle); - free(buf->base); - uv_close((uv_handle_t*)handle, NULL); - uv_stop(req->loop); -} - -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)); - 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"); - - // read result - ret = uv_read_start((uv_stream_t*)&(request->handle), OnReceiveAlloc, OnReceiveResponse); - PROPERTY_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"); - 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); - int result = request->result; - free(request); - return result; -} - -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"); - - PROPERTY_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"); - - // 带字符串结束符 - int contentSize = BuildPropertyContent(request->msg.content, msgSize - sizeof(RequestMsg), name, value); - PROPERTY_CHECK(contentSize > 0, return -1, "Failed to copy porperty"); - request->msg.contentSize = contentSize; - return StartRequest(SET_PROPERTY, 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); - - 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); -} - -int SystemGetParameterName(PropertyHandle 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); -} - -int SystemGetParameterValue(PropertyHandle 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); -} - -int SystemTraversalParameter(void (*traversalParameter)(PropertyHandle 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); -} - -const char *SystemDetectPropertyChange(PropertyCache *cache, - PropertyEvaluatePtr evaluate, u_int32_t count, const char *properties[][2]) -{ - PROPERTY_CHECK(cache != NULL && evaluate != NULL && properties != NULL, return NULL, "The param is null"); - return DetectPropertyChange(&g_propertyWorkSpaceReadOnly, cache, evaluate, count, properties); -} diff --git a/services/property/include/property_manager.h b/services/property/include/property_manager.h deleted file mode 100755 index 8324b08cb42d78d0fe8a5f7570a6507f8417d71c..0000000000000000000000000000000000000000 --- a/services/property/include/property_manager.h +++ /dev/null @@ -1,165 +0,0 @@ -/* - * 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 BASE_STARTUP_PROPERTY_MANAGER_H -#define BASE_STARTUP_PROPERTY_MANAGER_H -#include -#include - -#include "init_log.h" -#include "property.h" -#include "property_trie.h" -#include "securec.h" - -#ifdef __cplusplus -#if __cplusplus -extern "C" { -#endif -#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; - -#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" -#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" -#endif - -#define SUBSTR_INFO_NAME 0 -#define SUBSTR_INFO_LABEL 1 -#define SUBSTR_INFO_TYPE 2 -#define SUBSTR_INFO_MAX 4 - -#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 PROPERTY_CHECK(retCode, exper, ...) \ - if (!(retCode)) { \ - PROPERTY_LOGE(__VA_ARGS__); \ - exper; \ - } - -#define futex(addr1, op, val, rel, addr2, val3) \ - syscall(SYS_futex, addr1, op, val, rel, addr2, val3) -#define futex_wait_always(addr1) \ - syscall(SYS_futex, addr1, FUTEX_WAIT, *(int*)(addr1), 0, 0, 0) -#define futex_wake_single(addr1) \ - syscall(SYS_futex, addr1, FUTEX_WAKE, 1, 0, 0, 0) - -typedef struct UserCred { - pid_t pid; - uid_t uid; - gid_t gid; -} UserCred; - -typedef struct { - char label[LABEL_STRING_LEN]; - UserCred cred; -} PropertySecurityLabel; - -typedef struct PropertyAuditData { - const UserCred *cr; - const char *name; -} PropertyAuditData; - -typedef struct { - atomic_uint_least32_t flags; - WorkSpace propertyLabelSpace; - WorkSpace propertySpace; - PropertySecurityLabel label; -} PropertyWorkSpace; - -typedef struct { - atomic_uint_least32_t flags; - WorkSpace persistWorkSpace; -} PropertyPersistWorkSpace; - -typedef struct { - char value[128]; -} SubStringInfo; - -int InitPropertyWorkSpace(PropertyWorkSpace *workSpace, int onlyRead, const char *context); -void ClosePropertyWorkSpace(PropertyWorkSpace *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 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 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 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 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(); - -typedef void (*TraversalParamPtr)(PropertyHandle 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); - -const char *DetectPropertyChange(PropertyWorkSpace *workSpace, PropertyCache *cache, - PropertyEvaluatePtr evaluate, u_int32_t count, const char *properties[][2]); - -#ifdef __cplusplus -#if __cplusplus -} -#endif -#endif -#endif \ No newline at end of file diff --git a/services/property/include/property_service.h b/services/property/include/property_service.h deleted file mode 100755 index f5925f72a51bd5fb01b7c1cc2325d8174a22b96d..0000000000000000000000000000000000000000 --- a/services/property/include/property_service.h +++ /dev/null @@ -1,87 +0,0 @@ -/* - * 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 BASE_STARTUP_PROPERTY_SERVICE_H -#define BASE_STARTUP_PROPERTY_SERVICE_H -#include -#include "property.h" -#ifdef __cplusplus -#if __cplusplus -extern "C" { -#endif -#endif - -/** - * Init 接口 - * 初始化属性服务 - * - */ -void InitPropertyService(); - -/** - * Init 接口 - * 加载默认的属性值 - * - */ -int LoadDefaultProperty(const char *fileName); - -/** - * Init 接口 - * 安全使用,加载属性的信息,包括selinux label 等 - * - */ -int LoadPropertyInfo(const char *fileName); - -/** - * Init 接口 - * 启动属性服务,在main启动的最后调用,阻赛当前线程 - * - */ -int StartPropertyService(); - -/** - * Init 接口 - * 设置属性,主要用于其他进程使用,通过管道修改属性 - * - */ -int SystemWriteParameter(const char *name, const char *value); - -/** - * Init 接口 - * 查询属性。 - * - */ -int SystemReadParameter(const char *name, char *value, unsigned int *len); - -/** - * Init 接口 - * 遍历属性。 - * - */ -int SystemTraversalParameters(void (*traversalParameter)(PropertyHandle handle, void* cookie), void* cookie); - -/** - * Init 接口 - * 加载默认属性。 - * - */ -int LoadPersistProperties(); - -#ifdef __cplusplus -#if __cplusplus -} -#endif -#endif -#endif \ No newline at end of file diff --git a/services/property/manager/property_cache.c b/services/property/manager/property_cache.c deleted file mode 100755 index 82f6e236e73f4d6dfc8a7aaa3c9edbf6098de25e..0000000000000000000000000000000000000000 --- a/services/property/manager/property_cache.c +++ /dev/null @@ -1,148 +0,0 @@ -/* - * 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 "property.h" - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "property_manager.h" - -#define LABEL "Manager" -#define MAX_PROPERT_IN_WATCH 5 -#define NORMAL_MEMORY_FOR_PROPERTY_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"); - 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)); - 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", - workSpace->area->currOffset, workSpace->area->firstNode, workSpace->area->dataSize); - return 0; -} - -static PropertyCacheNode *AllocPropertyCacheNode(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, - "Failed to allocate currOffset %d, dataSize %d", workSpace->area->currOffset, workSpace->area->dataSize); - PropertyCacheNode *cache = (PropertyCacheNode *)(workSpace->area->data + workSpace->area->currOffset); - workSpace->area->currOffset += size; - return cache; -} - -static int CreatePropertyCache(PropertyCache *cache, PropertyWorkSpace *workSpace, PropertyEvaluatePtr evaluate) -{ - PROPERTY_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"); - pthread_mutex_init(&cache->lock, NULL); - cache->serial = GetWorkSpaceSerial(&workSpace->propertySpace); - 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"); - return 0; -} - -static int AddPropertyNode(PropertyCache *cache, PropertyWorkSpace *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"); - - PropertyCacheNode *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"); - - ret = ReadPropertyWithCheck(workSpace, name, &cacheNode->handle); - PROPERTY_CHECK(ret == 0, return -1, "Failed to read property"); - cacheNode->serial = ReadPropertySerial(workSpace, cacheNode->handle); - return ret; -} - -static int CheckCacheNode(PropertyWorkSpace *workSpace, PropertyCacheNode *cacheNode) -{ - return cacheNode && ReadPropertySerial(workSpace, cacheNode->handle) != cacheNode->serial; -} - -static void RefreshCacheNode(PropertyWorkSpace *workSpace, PropertyCacheNode *cacheNode) -{ - cacheNode->serial = ReadPropertySerial(workSpace, cacheNode->handle); - u_int32_t len = sizeof(cacheNode->value); - ReadPropertyValue(workSpace, cacheNode->handle, cacheNode->value, &len); -} - -static const char *TestPropertyCache(PropertyCache *cache, PropertyWorkSpace *workSpace) -{ - int changeDetected; - if (pthread_mutex_trylock(&cache->lock)) { - return cache->evaluate(cache->cacheCount, cache->cacheNode); - } - if (GetWorkSpaceSerial(&workSpace->propertySpace) != cache->serial) { - changeDetected = 1; - } - for (u_int32_t i = 0; (i < cache->cacheCount) && changeDetected == 0; i++) { - changeDetected = CheckCacheNode(workSpace, &cache->cacheNode[i]); - } - if (changeDetected) { - for (u_int32_t i = 0; i < cache->cacheCount; i++) { - RefreshCacheNode(workSpace, &cache->cacheNode[i]); - } - cache->serial = GetWorkSpaceSerial(&workSpace->propertySpace); - } - 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]) -{ - pthread_mutex_lock(&cacheLock); - while (cache->cacheCount == 0) { - int ret = CreatePropertyCache(cache, workSpace, evaluate); - PROPERTY_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"); - } - PROPERTY_CHECK(ret == 0, break, "Failed to add property cache"); - } - pthread_mutex_unlock(&cacheLock); - return TestPropertyCache(cache, workSpace); -} diff --git a/services/property/manager/property_manager.c b/services/property/manager/property_manager.c deleted file mode 100755 index 64b6229086020589358aaa6e017b0a885f910c36..0000000000000000000000000000000000000000 --- a/services/property/manager/property_manager.c +++ /dev/null @@ -1,532 +0,0 @@ -/* - * 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 "property_manager.h" - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#define LABEL "Manager" - -#ifdef PROPERTY_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", - auditData->name, auditData->cr->pid, auditData->cr->uid, auditData->cr->gid); - return 0; -} -#endif - -int InitPropertyWorkSpace(PropertyWorkSpace *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 - union selinux_callback cb; - cb.func_audit = SelinuxAuditCallback; - selinux_set_callback(SELINUX_CB_AUDIT, cb); -#endif - -#ifdef PROPERTY_SUPPORT_SELINUX - if (context && fsetxattr(fd, XATTR_NAME_SELINUX, context, strlen(context) + 1, 0) != 0) { - PROPERTY_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); - atomic_store_explicit(&workSpace->flags, WORKSPACE_FLAGS_INIT, memory_order_release); - return ret; -} - -void ClosePropertyWorkSpace(PropertyWorkSpace *workSpace) -{ - CloseWorkSpace(&workSpace->propertySpace); - CloseWorkSpace(&workSpace->propertyLabelSpace); - atomic_store_explicit(&workSpace->flags, 0, memory_order_release); -} - -int WritePropertyInfo(PropertyWorkSpace *workSpace, SubStringInfo *info, int subStrNumber) -{ - PROPERTY_CHECK(workSpace != NULL && info != NULL && subStrNumber > SUBSTR_INFO_NAME, - return PROPERTY_CODE_INVALID_PARAM, "Failed to check param"); - const char *name = info[SUBSTR_INFO_NAME].value; - char *label = NULL; - char *type = NULL; - if (subStrNumber >= SUBSTR_INFO_LABEL) { - label = info[SUBSTR_INFO_LABEL].value; - } else { - label = "u:object_r:default_prop:s0"; - } - if (subStrNumber >= SUBSTR_INFO_TYPE) { - type = info[SUBSTR_INFO_TYPE].value; - } else { - type = "string"; - } - - int ret = CheckPropertyName(name, 1); - PROPERTY_CHECK(ret == 0, return ret, "Illegal property 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); - if (entry != 0) { // 已经存在label - PROPERTY_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) -{ - PROPERTY_CHECK(workSpace != NULL && name != NULL && value != NULL, - return PROPERTY_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"); - DataEntry *entry = (DataEntry *)GetTrieNode(workSpace, &node->dataIndex); - 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); - SaveIndex(&node->dataIndex, 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); - futex_wake(&workSpace->area->serial, INT_MAX); - return 0; -} - -int UpdateProperty(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"); - - DataEntry *entry = (DataEntry *)GetTrieNode(workSpace, dataIndex); - if (entry == NULL) { - PROPERTY_LOGE("Failed to update property value %s %u", name, *dataIndex); - return -1; - } - 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); - - 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); - } - 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) -{ - PROPERTY_CHECK(workSpace != NULL, return NULL, "Failed to check param"); - PROPERTY_CHECK(name != NULL, return NULL, "Invalid param size"); - - TrieDataNode *node = FindTrieDataNode(workSpace, name, strlen(name), 0); - if (node != NULL) { - return (DataEntry *)GetTrieNode(workSpace, &node->dataIndex); - } - return NULL; -} - -int WritePropertyWithCheck(PropertyWorkSpace *workSpace, - const PropertySecurityLabel *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"); - - 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; - } - - 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 WriteProperty(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"); - - 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); - } - return AddProperty(workSpace, name, value); -} - -int ReadPropertyWithCheck(PropertyWorkSpace *workSpace, const char *name, PropertyHandle *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"); - 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; - } - - *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 *node = FindTrieDataNode(&workSpace->propertySpace, name, strlen(name), 0); - if (node != NULL && node->dataIndex != 0) { - PROPERTY_LOGI("ReadPropertyWithCheck trie %p dataIndex %u name %s", node, node->dataIndex, name); - *handle = node->dataIndex; - return 0; - } - return PROPERTY_CODE_NOT_FOUND_PROP; -} - -int ReadPropertyValue(PropertyWorkSpace *workSpace, PropertyHandle handle, char *value, u_int32_t *len) -{ - PROPERTY_CHECK(workSpace != NULL, return PROPERTY_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; - } - DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->propertySpace, &handle); - if (entry == NULL) { - return -1; - } - - if (value == NULL) { - *len = DATA_ENTRY_DATA_LEN(entry);; - return 0; - } - - while (1) { - u_int32_t serial = GetDataSerial(entry); - int ret = GetDataValue(entry, value, *len); - PROPERTY_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; - } - } - return 0; -} - -int ReadPropertyName(PropertyWorkSpace *workSpace, PropertyHandle 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); - if (entry == NULL) { - return -1; - } - return GetDataValue(entry, name, len); -} - -u_int32_t ReadPropertySerial(PropertyWorkSpace *workSpace, PropertyHandle handle) -{ - PROPERTY_CHECK(workSpace != NULL, return 0, "Invalid param"); - DataEntry *entry = (DataEntry *)GetTrieNode(&workSpace->propertySpace, &handle); - if (entry == NULL) { - return 0; - } - return GetDataSerial(entry); -} - -int CheckControlPropertyPerms(PropertyWorkSpace *workSpace, - const PropertySecurityLabel *srcLabel, const char *name, const char *value) -{ - PROPERTY_CHECK(srcLabel != NULL && name != NULL && value != NULL, - return PROPERTY_CODE_INVALID_PARAM, "Invalid param"); - - char * ctrlName[] = { - "ctl.start", "ctl.stop", "ctl.restart" - }; - size_t size1 = strlen("ctl.") + strlen(value); - 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"); - - // 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. - 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. 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. 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"); - legacyName[n] = '\0'; - - TrieDataNode *node = FindTrieDataNode(&workSpace->propertySpace, legacyName, strlen(legacyName), 1); - int ret = CheckMacPerms(workSpace, srcLabel, legacyName, node == NULL ? 0 : node->labelIndex); - if (ret == 0) { - free(legacyName); - return 0; - } - break; - } - } - 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"); - - TrieDataNode *node = FindTrieDataNode(&workSpace->propertySpace, 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) -{ - size_t nameLen = strlen(name); - if (nameLen >= PROPERTY_VALUE_LEN_MAX) { - return PROPERTY_CODE_INVALID_NAME; - } - - if (nameLen < 1 || name[0] == '.' || (!propInfo && name[nameLen - 1] == '.')) { - PROPERTY_LOGE("CheckPropertyName %s %d", name, propInfo); - return PROPERTY_CODE_INVALID_NAME; - } - - /* Only allow alphanumeric, plus '.', '-', '@', ':', or '_' */ - /* Don't allow ".." to appear in a property name */ - for (size_t i = 0; i < nameLen; i++) { - if (name[i] == '.') { - if (name[i - 1] == '.') { - return PROPERTY_CODE_INVALID_NAME; - } - continue; - } - if (name[i] == '_' || name[i] == '-' || name[i] == '@' || name[i] == ':') { - continue; - } - if (isalnum(name[i])) { - continue; - } - return PROPERTY_CODE_INVALID_NAME; - } - return 0; -} - -int CheckPropertyValue(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; - } - } else { - // 限制非read only的属性,防止属性值修改后,原空间不能保存 - PROPERTY_CHECK(strlen(value) < PROPERTY_VALUE_LEN_MAX, - return PROPERTY_CODE_INVALID_VALUE, "Illegal property value"); - } - return 0; -} - -int CheckMacPerms(PropertyWorkSpace *workSpace, - const PropertySecurityLabel *srcLabel, const char *name, u_int32_t labelIndex) -{ -#ifdef PROPERTY_SUPPORT_SELINUX - PropertyAuditData auditData; - auditData.name = name; - auditData.cr = &srcLabel->cred; - - int ret = 0; - TrieNode *node = (TrieNode *)GetTrieNode(&workSpace->propertyLabelSpace, &labelIndex); - if (node != 0) { // 已经存在label - ret = selinux_check_access(srcLabel, node->key, "property_service", "set", &auditData); - } else { - ret = selinux_check_access(srcLabel, "u:object_r:default_prop:s0", "property_service", "set", &auditData); - } - return ret == 0 ? 0 : PROPERTY_CODE_PERMISSION_DENIED; -#else - return 0; -#endif -} - -int CanWriteProperty(PropertyWorkSpace *workSpace, - const PropertySecurityLabel *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"); - - if (strncmp(name, "ctl.", strlen("ctl.")) == 0) { // 处理ctrl TODO - return CheckControlPropertyPerms(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"); - return 0; -} - -int CanReadProperty(PropertyWorkSpace *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; - auditData.name = name; - UserCred cr = {.pid = 0, .uid = 0, .gid = 0}; - auditData.cr = &cr; - - int ret = 0; - TrieNode *node = (TrieNode *)GetTrieNode(&workSpace->propertyLabelSpace, &labelIndex); - if (node != 0) { // 已经存在label - ret = selinux_check_access(&workSpace->context, node->key, "property_service", "read", &auditData); - } else { - ret = selinux_check_access(&workSpace->context, "selinux_check_access", "file", "read", &auditData); - } - return ret == 0 ? 0 : PROPERTY_CODE_PERMISSION_DENIED; -#else - return 0; -#endif -} - -int GetSubStringInfo(const char *buff, u_int32_t buffLen, char delimiter, SubStringInfo *info, int subStrNumber) -{ - size_t i = 0; - // 去掉开始的空格 - for (; i < strlen(buff); i++) { - if (!isspace(buff[i])) { - break; - } - } - // 过滤掉注释 - if (buff[i] == '#') { - return -1; - } - // 分割字符串 - int curr = 0; - int valueCurr = 0; - for (; i < buffLen; i++) { - if (buff[i] == '\n' || buff[i] == '\r') { - break; - } - if (buff[i] == delimiter && valueCurr != 0) { - info[curr].value[valueCurr] = '\0'; - valueCurr = 0; - curr++; - } else if (isspace(buff[i])) { // 无效字符,进行过滤 - continue; - } else { - if ((valueCurr + 1) >= (int)sizeof(info[curr].value)) { - continue; - } - info[curr].value[valueCurr++] = buff[i]; - } - if (curr >= subStrNumber) { - break; - } - } - if (valueCurr > 0) { - info[curr].value[valueCurr] = '\0'; - valueCurr = 0; - curr++; - } - return curr; -} - -int BuildPropertyContent(char *content, u_int32_t contentSize, const char *name, const char *value) -{ - PROPERTY_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); - - int offset = 0; - int ret = memcpy_s(content + offset, contentSize - offset, name, nameLen); - offset += nameLen; - ret |= memcpy_s(content + offset, contentSize - offset, "=", 1); - offset += 1; - ret |= memcpy_s(content + offset, contentSize - offset, value, valueLen); - offset += valueLen; - content[offset] = '\0'; - PROPERTY_CHECK(ret == 0, return -1, "Failed to copy porperty"); - offset += 1; - return offset; -} - -int ProcessPropertTraversal(WorkSpace *workSpace, TrieNode *node, void *cookie) -{ - PropertyTraversalContext *context = (PropertyTraversalContext *)cookie; - TrieDataNode *current = (TrieDataNode *)node; - if (current == NULL) { - return 0; - } - if (current->dataIndex == 0) { - return 0; - } - context->traversalParamPtr(current->dataIndex, context->context); - return 0; -} - -int TraversalProperty(PropertyWorkSpace *workSpace, TraversalParamPtr walkFunc, void *cookie) -{ - PropertyTraversalContext context = { - walkFunc, cookie - }; - return TraversalTrieDataNode(&workSpace->propertySpace, - (TrieDataNode *)workSpace->propertySpace.rootNode, ProcessPropertTraversal, &context); -} \ No newline at end of file diff --git a/services/property/service/property_service.c b/services/property/service/property_service.c deleted file mode 100755 index 8cdf02c747aad6b8df5ca9dfe69198ca56292f43..0000000000000000000000000000000000000000 --- a/services/property/service/property_service.c +++ /dev/null @@ -1,282 +0,0 @@ -/* - * 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 "property_service.h" - -#include -#include -#include -#include - -#include "property.h" -#include "property_manager.h" -#include "property_request.h" -#include "trigger.h" - -#include "uv.h" - -#define BUFFER_SIZE 256 -#define LABEL "Server" - -static char *g_initContext = ""; -static PropertyWorkSpace g_propertyWorkSpace = {ATOMIC_VAR_INIT(0), {}, {}, {}}; - -void InitPropertyService() -{ - int ret = InitPropertyWorkSpace(&g_propertyWorkSpace, 0, g_initContext); - PROPERTY_CHECK(ret == 0, return, "Init propert workspace fail"); -} - -int LoadDefaultProperty(const char *fileName) -{ - u_int32_t flags = atomic_load_explicit(&g_propertyWorkSpace.flags, memory_order_relaxed); - if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) { - return PROPERTY_CODE_NOT_INIT; - } - - FILE *fp = fopen(fileName, "r"); - PROPERTY_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); - 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); - continue; - } - if (strcmp(info[0].value, "selinux.restorecon_recursive") == 0) { - PROPERTY_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); - - 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); - } - fclose(fp); - free(info); - PROPERTY_LOGI("LoadDefaultProperty proterty success %s", fileName); - return 0; -} - -int LoadPropertyInfo(const char *fileName) -{ - u_int32_t flags = atomic_load_explicit(&g_propertyWorkSpace.flags, memory_order_relaxed); - if ((flags & WORKSPACE_FLAGS_INIT) != WORKSPACE_FLAGS_INIT) { - return PROPERTY_CODE_NOT_INIT; - } - FILE *fp = fopen(fileName, "r"); - PROPERTY_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; - 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++; - } - fclose(fp); - free(info); - PROPERTY_LOGI("Load proterty info %d success %s", propInfoCount, fileName); - return 0; -} - -static int ProcessPropertySet(RequestMsg *msg) -{ - PROPERTY_CHECK(msg != NULL, return PROPERTY_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"); - - // notify event to process trigger - PostTrigger(EVENT_PROPERTY, msg->content, msg->contentSize); - return 0; -} - -static void OnClose(uv_handle_t *handle) -{ - free(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; -} - -static void OnWriteResponse(uv_write_t *req, int status) -{ - // 发送成功,释放请求内存 - PROPERTY_LOGI("OnWriteResponse status %d", status); - ResponseNode *node = (ResponseNode*)req; - free(node); -} - -static void SendResponse(uv_stream_t *handle, RequestType type, int result, void *content, int size) -{ - int ret = 0; - // 申请整块内存,用于回复数据和写请求 - ResponseNode *response = (ResponseNode *)malloc(sizeof(ResponseNode) + size); - PROPERTY_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"); - } - 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)); -} - -static void OnReceiveRequest(uv_stream_t *handle, ssize_t nread, const uv_buf_t *buf) -{ - if (nread <= 0 || buf == NULL || buf->base == NULL) { - uv_close((uv_handle_t*)handle, OnClose); - free(buf->base); - return; - } - int freeHandle = 1; - RequestMsg *msg = (RequestMsg *)buf->base; - switch (msg->type) { - case SET_PROPERTY: { - freeHandle = 0; - int ret = ProcessPropertySet(msg); - SendResponse(handle, SET_PROPERTY, ret, NULL, 0); - break; - } - default: - PROPERTY_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"); - uv_pipe_t *stream = (uv_pipe_t*)malloc(sizeof(uv_pipe_t)); - PROPERTY_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); - - stream->data = server; - ret = uv_accept(server, (uv_stream_t *)stream); - PROPERTY_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); - return, "Failed to uv_read_start %d", ret); -} - -int StartPropertyService() -{ - PROPERTY_LOGI("StartPropertyService."); - uv_fs_t req; - uv_fs_unlink(uv_default_loop(), &req, PIPE_NAME, NULL); - - signal(SIGINT, RemoveSocket); - - 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); - 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)); - 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)); - - uv_run(uv_default_loop(), UV_RUN_DEFAULT); - PROPERTY_LOGI("Start service exit."); - return 0; -} - -int SystemWriteParameter(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); - if (ret == 0) { - ret = WritePersistProperty(name, value); - PROPERTY_CHECK(ret == 0, return ret, "Failed to set property"); - } else { - PROPERTY_LOGE("Failed to set property %d name %s %s", ret, name, value); - } - // notify event to process trigger - PostPropertyTrigger(name, value); - return 0; -} - -int SystemReadParameter(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); - if (ret == 0) { - ret = ReadPropertyValue(&g_propertyWorkSpace, handle, value, len); - } - return ret; -} - -int SystemTraversalParameters(void (*traversalParameter)(PropertyHandle handle, void* cookie), void* cookie) -{ - PROPERTY_CHECK(traversalParameter != NULL, return -1, "The param is null"); - return TraversalProperty(&g_propertyWorkSpace, traversalParameter, cookie); -} - -PropertyWorkSpace *GetPropertyWorkSpace() -{ - return &g_propertyWorkSpace; -} - -int LoadPersistProperties() -{ - return RefreshPersistProperties(&g_propertyWorkSpace, g_initContext); -} diff --git a/services/reboot/BUILD.gn b/services/reboot/BUILD.gn new file mode 100644 index 0000000000000000000000000000000000000000..724a5cfc46eb439e6cfa1599b2b336e59e4cdf67 --- /dev/null +++ b/services/reboot/BUILD.gn @@ -0,0 +1,30 @@ +# 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" +} diff --git a/services/reboot/init_cmd_reboot.c b/services/reboot/init_cmd_reboot.c new file mode 100644 index 0000000000000000000000000000000000000000..bf6dba27fabc6826ea82011654e89f010cab63b8 --- /dev/null +++ b/services/reboot/init_cmd_reboot.c @@ -0,0 +1,49 @@ +/* + * Copyright (c) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include +#include +#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; +} + diff --git a/services/src/device.c b/services/src/device.c old mode 100755 new mode 100644 index af969a83d236e150c89c6a966a16650b2060f7ac..d9e9dfffe0c2da92b7540e42f07e5312a1606d7b --- a/services/src/device.c +++ b/services/src/device.c @@ -19,6 +19,8 @@ #include #include #include +#include +#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; diff --git a/services/src/init_adapter.c b/services/src/init_adapter.c index 5aa53c5dceea379a612db84fba034bfa7bc59fa8..c27bc9c79194ce6fea942f7223a581ff7da942ca 100644 --- a/services/src/init_adapter.c +++ b/services/src/init_adapter.c @@ -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 } diff --git a/services/src/init_capability.c b/services/src/init_capability.c old mode 100755 new mode 100644 index 14cdbc66c29818cac87347e6ae8710fd7a447066..093396b728dfec07c5f549fe036d127f4c318409 --- a/services/src/init_capability.c +++ b/services/src/init_capability.c @@ -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; } } diff --git a/services/src/init_cmds.c b/services/src/init_cmds.c index 61bdd9236f1cef943e8e6d80276dfaf4628e9a05..8af044e9891d5de9b3f42e6bbabd95fef300d1cb 100644 --- a/services/src/init_cmds.c +++ b/services/src/init_cmds.c @@ -33,12 +33,12 @@ #include #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); } } diff --git a/services/src/init_import.c b/services/src/init_import.c old mode 100755 new mode 100644 index c2eac20a49cfcbbd6323979c7b19f74d50e84734..68751635266cd22d7d81aae5b78b224daeb73211 --- a/services/src/init_import.c +++ b/services/src/init_import.c @@ -15,7 +15,9 @@ #include "init_import.h" #include +#include #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 +} diff --git a/services/src/init_jobs.c b/services/src/init_jobs.c index 97bea7983a561981fdab9f65a19ebe50c81eb0a7..fa8a9fd194e48ace410da22b9a5b1ab87930b6c0 100644 --- a/services/src/init_jobs.c +++ b/services/src/init_jobs.c @@ -17,8 +17,10 @@ #include #include +#include #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; diff --git a/services/src/init_read_cfg.c b/services/src/init_read_cfg.c index 97566985a8149110eb3d33e7cf1e489f0a820d7c..b6f8e1c8116c4d5151a8b512b8547477433d843e 100644 --- a/services/src/init_read_cfg.c +++ b/services/src/init_read_cfg.c @@ -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(); diff --git a/services/src/init_reboot.c b/services/src/init_reboot.c new file mode 100644 index 0000000000000000000000000000000000000000..5b950533a5e1df7128295e434646a16ead1a7732 --- /dev/null +++ b/services/src/init_reboot.c @@ -0,0 +1,188 @@ +/* + * 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 +#include +#include +#include +#include +#include +#include +#include +#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; + +} + diff --git a/services/src/init_service.c b/services/src/init_service.c index 52d516b1c6b1c6e9f5721d513d7d8b7ec560f1dc..fc85be1628ede0cbc130dfc58744e10f5d4a9ba3 100644 --- a/services/src/init_service.c +++ b/services/src/init_service.c @@ -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); diff --git a/services/src/init_service_manager.c b/services/src/init_service_manager.c old mode 100755 new mode 100644 index 1113d5d1317f73926d231fc4a31a5c43ec5c219c..2ce7e54fd0c56f9366d34a6b9c43e5ab17a07eb4 --- a/services/src/init_service_manager.c +++ b/services/src/init_service_manager.c @@ -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); } } } diff --git a/services/src/init_service_socket.c b/services/src/init_service_socket.c old mode 100755 new mode 100644 index df565ca26a1402e2db4815f306bb203b0728b20c..c661f69216405b50be21e6579551030f7c257b5e --- a/services/src/init_service_socket.c +++ b/services/src/init_service_socket.c @@ -23,6 +23,7 @@ #include #include #include +#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; diff --git a/services/src/init_signal_handler.c b/services/src/init_signal_handler.c index c79feca9a49b8b93486bb44bc5942e33c6cb1f4d..bd5ca1c31005c80c53b217cf97e13e35cba2809c 100644 --- a/services/src/init_signal_handler.c +++ b/services/src/init_signal_handler.c @@ -23,8 +23,13 @@ #include #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 diff --git a/services/src/init_utils.c b/services/src/init_utils.c old mode 100755 new mode 100644 index e100a68d1029ff1d4209d29b48ea63cb46352cca..d1e7e55095ac8c2b3b7c3b3928ddd29f09b1c94d --- a/services/src/init_utils.c +++ b/services/src/init_utils.c @@ -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" }; diff --git a/services/src/list.c b/services/src/list.c old mode 100755 new mode 100644 diff --git a/services/src/main.c b/services/src/main.c old mode 100755 new mode 100644 index 906f5d13478f3f51fa8ea4e4cc04470329d8568c..0b3fa214627d6011c43ca83487535ebeafef3cb4 --- a/services/src/main.c +++ b/services/src/main.c @@ -25,6 +25,7 @@ #include #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. diff --git a/services/src/uevent.c b/services/src/uevent.c old mode 100755 new mode 100644 index 08cf8afe18befc60dd41a35a7ae6f2fff5874fc2..b55bc6c74fcd288c1959b175a74dbde71f6e6413 --- a/services/src/uevent.c +++ b/services/src/uevent.c @@ -28,6 +28,7 @@ #include #include #include +#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; } diff --git a/services/test/unittest/common/BUILD.gn b/services/test/unittest/common/BUILD.gn index 0d8da09fe21c5cbb2ab123facc2fdec84da116c2..f654300f263b6e1229972c81284a51a81060e8e3 100644 --- a/services/test/unittest/common/BUILD.gn +++ b/services/test/unittest/common/BUILD.gn @@ -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", ] diff --git a/services/trigger/BUILD.gn b/services/trigger/BUILD.gn deleted file mode 100755 index 8a6ac55146a9312795fd61bbe8f5b983d122d1b7..0000000000000000000000000000000000000000 --- a/services/trigger/BUILD.gn +++ /dev/null @@ -1,40 +0,0 @@ -# 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