diff options
| author | wangmenglan <[email protected]> | 2023-12-04 15:41:02 +0800 |
|---|---|---|
| committer | wangmenglan <[email protected]> | 2023-12-08 16:51:17 +0800 |
| commit | 052fc5bb8d6765ac20c2f8ce5dda97750d929dcd (patch) | |
| tree | 61746aa5a7a2073a955288ea8472e4fb5dddcb13 | |
| parent | 0c5df1fe2e8451cb85ee25bf01fb111d15a4ed0f (diff) | |
support obp dynamic configuration loadingv4.6.63-20231208
| -rw-r--r-- | cmake/PostInstall.in | 8 | ||||
| -rw-r--r-- | service/include/olp_dev.h | 32 | ||||
| -rw-r--r-- | service/include/sc_common.h | 2 | ||||
| -rw-r--r-- | service/src/core.c | 31 | ||||
| -rw-r--r-- | service/src/monit.c | 2 | ||||
| -rw-r--r-- | service/src/node_vwire.c | 15 | ||||
| -rw-r--r-- | service/src/olp.c | 20 | ||||
| -rw-r--r-- | service/src/olp_6500.c | 1428 | ||||
| -rw-r--r-- | service/test/TestOLP.cc | 938 | ||||
| -rw-r--r-- | tools/CMakeLists.txt | 1 | ||||
| -rw-r--r-- | tools/monit_obp/CMakeLists.txt | 2 | ||||
| -rw-r--r-- | tools/monit_obp/monit_obp.py | 252 | ||||
| -rw-r--r-- | tools/systemd/CMakeLists.txt | 4 | ||||
| -rw-r--r-- | tools/systemd/mrapm_obp.service.in | 14 |
14 files changed, 2067 insertions, 682 deletions
diff --git a/cmake/PostInstall.in b/cmake/PostInstall.in index 3315661..ca25800 100644 --- a/cmake/PostInstall.in +++ b/cmake/PostInstall.in @@ -48,6 +48,10 @@ command="update-alternatives --altdir @CMAKE_INSTALL_PREFIX@/altdir \ monit_device \ @MR_INSTALL_BINDIR@/monit_device \ --slave \ + @CMAKE_INSTALL_PREFIX@/bin/monit_obp \ + monit_obp \ + @MR_INSTALL_BINDIR@/monit_obp \ + --slave \ @CMAKE_INSTALL_PREFIX@/bin/dpdk-hugepages.py \ dpdk-hugepages.py \ @MR_INSTALL_BINDIR@/dpdk-hugepages.py \ @@ -84,6 +88,10 @@ command="update-alternatives --altdir @CMAKE_INSTALL_PREFIX@/altdir \ mrapm_stream.service \ @MR_INSTALL_SYSTEM@/mrapm_stream.service \ --slave \ + /usr/lib/systemd/system/mrapm_obp.service \ + mrapm_obp.service \ + @MR_INSTALL_SYSTEM@/mrapm_obp.service \ + --slave \ /usr/lib/systemd/system/mrtunnat.service \ mrtunnat.service \ @MR_INSTALL_SYSTEM@/mrtunnat.service \ diff --git a/service/include/olp_dev.h b/service/include/olp_dev.h index 67949a5..406ff26 100644 --- a/service/include/olp_dev.h +++ b/service/include/olp_dev.h @@ -6,8 +6,6 @@ #define NR_OLP_DEVICE_MAX 8 #define NR_OLP_CHANNEL_PER_DEVICE_MAX 16 -typedef int (*olp_status_query_cb)(void); - enum olp_connect_type { OLP_CONNECT_TYPE_UNKNOW, @@ -23,17 +21,17 @@ enum olp_device_type OLP_DEVICE_TYPE_OLP_6500, }; -enum olp_channel_used +enum olp_used_state { - OLP_CHANNEL_STATE_UNUSED, - OLP_CHANNEL_STATE_USED, + OLP_STATE_UNUSED, + OLP_STATE_USED, }; enum olp_channel_state { - OLP_CHANNEL_STATE_FORCE_ACTIVE, + OLP_CHANNEL_STATE_FORCE_INLINE, OLP_CHANNEL_STATE_FORCE_BYPASS, - OLP_CHANNEL_STATE_REGULAR, + OLP_CHANNEL_STATE_TAP, }; enum olp_channel_heartbeat @@ -55,7 +53,8 @@ struct olp_channel_timer struct channel_runtime { - uint8_t traffic_mode; + uint8_t errcode; + uint8_t workline; float r1_optical_power; float r2_optical_power; float r3_optical_power; @@ -67,7 +66,7 @@ struct channel_runtime struct olp_channel { uint32_t olp_channel_id; - enum olp_channel_used used; + enum olp_used_state used; enum olp_channel_state state; uint32_t en_heartbeat; @@ -90,6 +89,7 @@ struct olp_network_s struct olp_dev_desc { char devsym[MR_SYMBOL_MAX]; + enum olp_used_state used; enum olp_device_type type; enum olp_connect_type conn_type; union { @@ -98,22 +98,16 @@ struct olp_dev_desc uint32_t refcnt; struct olp_channel * channels; - - olp_status_query_cb status_query; }; -struct olp_manager_main +struct olp_device { struct olp_dev_desc * olp_dev_descs[NR_OLP_DEVICE_MAX]; uint32_t nr_olp_dev_descs; }; -struct olp_dev_register +// TODO: when support more olp-devices, use *olp-dev[]. +struct olp_manager_main { - char devsym[MR_SYMBOL_MAX]; - enum olp_device_type type; - - olp_status_query_cb status_query; + struct olp_device * olp6500_main; }; - -struct olp6500_packet; diff --git a/service/include/sc_common.h b/service/include/sc_common.h index ed9bcb8..984aad5 100644 --- a/service/include/sc_common.h +++ b/service/include/sc_common.h @@ -64,6 +64,8 @@ struct sc_main char local_hwfile[MR_STRING_MAX]; /* 本地配置文件位置 */ char local_cfgfile[MR_STRING_MAX]; + /* 本地动态配置文件位置 */ + char local_dyfile[MR_STRING_MAX]; /* 本地日志文件位置 */ char local_logfile[MR_STRING_MAX]; /* 状态监测文件 */ diff --git a/service/src/core.c b/service/src/core.c index 7b158cf..b5ca1b4 100644 --- a/service/src/core.c +++ b/service/src/core.c @@ -53,6 +53,10 @@ const char service_git_version[] = ""; #define MR_SERVICE_DEFAULT_CFG "/etc/mrglobal.conf" #endif +#ifndef MR_SERVICE_DEFAULT_DYNAMIC_CFG +#define MR_SERVICE_DEFAULT_DYNAMIC_CFG "/etc/mrglobal.dynamic.conf" +#endif + #ifndef MR_SERVICE_DEFAULT_APPSYM #define MR_SERVICE_DEFAULT_APPSYM "service" #endif @@ -180,6 +184,7 @@ int32_t sw_forward_service_entry(void * args); int32_t sw_vlan_base_forward_service_entry(void * args); int32_t smartoffload_service_entry(void * args); int32_t node_manager_pkt_graph_service_entry(void * args); +int olp_config_reload(struct sc_main * sc_main); int sc_check_spinlock_loop(struct sc_main * sc_main) { @@ -904,6 +909,7 @@ __rte_unused static void signal_handler(int signum) __rte_unused static void config_reload_handler(int signum) { + olp_config_reload(g_sc_main); return; } @@ -947,6 +953,8 @@ int main(int argc, char * argv[]) snprintf(sc->local_monitfile, sizeof(sc->local_monitfile), "%s", MR_SERVICE_DEFAULT_MONIT_FILE); /* Hardware File */ snprintf(sc->local_hwfile, sizeof(sc->local_hwfile), "%s", MR_SERVICE_DEFAULT_HWFILE); + /* Configure Dynamic File */ + snprintf(sc->local_dyfile, sizeof(sc->local_dyfile), "%s", MR_SERVICE_DEFAULT_DYNAMIC_CFG); /* 通过Systemd启动,关闭标准输出,采用syslog方式记录日志 */ if (__check_is_notify()) @@ -956,7 +964,7 @@ int main(int argc, char * argv[]) int ret = 0; int opt = 0; - while ((opt = getopt(argc, argv, "hvc:w:d:")) != -1) + while ((opt = getopt(argc, argv, "hvc:w:d:s:")) != -1) { switch (opt) { @@ -975,6 +983,10 @@ int main(int argc, char * argv[]) break; case 'd': snprintf(sc->local_hwfile, sizeof(sc->local_hwfile), "%s", optarg); + break; + case 's': + snprintf(sc->local_dyfile, sizeof(sc->local_dyfile), "%s", optarg); + break; default: break; } @@ -1011,7 +1023,7 @@ int main(int argc, char * argv[]) /* Exegesis the singnal for fast stop */ // signal(SIGINT, signal_handler); // signal(SIGTERM, signal_handler); - // signal(SIGHUP, config_reload_handler); + signal(SIGHUP, config_reload_handler); if (devmgr_early_init(sc) != RT_SUCCESS) { @@ -1145,6 +1157,14 @@ int main(int argc, char * argv[]) goto quit; } + /* Must Before 'vwire' init */ + if (olp_manager_init(sc) != RT_SUCCESS) + { + MR_ERROR("olp manager initialization failed. "); + ret = EXIT_FAILURE; + goto quit; + } + /* Must Before 'Classifier' init */ if (vwire_init(sc) != RT_SUCCESS) { @@ -1181,13 +1201,6 @@ int main(int argc, char * argv[]) goto quit; } - if (olp_manager_init(sc) != RT_SUCCESS) - { - MR_ERROR("olp manager initialization failed. "); - ret = EXIT_FAILURE; - goto quit; - } - sc_config_dump(sc); vdev_dump(sc); diff --git a/service/src/monit.c b/service/src/monit.c index 3e7d5a3..b94b3b3 100644 --- a/service/src/monit.c +++ b/service/src/monit.c @@ -378,7 +378,7 @@ static cJSON * monit_root(struct sc_main * sc) cJSON_AddItemToObject(j_root, "health-session-state", health_check_session_monit_loop(sc)); cJSON_AddItemToObject(j_root, "forwarder-table", forwarder_table_monit_loop(sc)); cJSON_AddItemToObject(j_root, "peer-table", peer_monit_loop(sc)); - cJSON_AddItemToObject(j_root, "olp", olp_manager_monit_loop(sc)); + cJSON_AddItemToObject(j_root, "OBP", olp_manager_monit_loop(sc)); return j_root; } diff --git a/service/src/node_vwire.c b/service/src/node_vwire.c index f8fc1b7..54580c9 100644 --- a/service/src/node_vwire.c +++ b/service/src/node_vwire.c @@ -72,6 +72,8 @@ struct vwire_node_main static struct vwire_node_main * p_vwire_node_main = NULL; static unsigned int g_vwire_max_entry = 256; +int olp_set_used(char * dev_sym, uint32_t channel_id); + /* Vwire get max rule num */ unsigned int vwire_get_max_rule_num() { @@ -467,6 +469,19 @@ int vwire_init(struct sc_main * sc) } vwire_forward_rule_add__DEV_TYPE(p_vwire_node_main, sc, str_int_dev, str_ext_dev); + + char str_obp_dev[MR_SYMBOL_MAX] = {0}; + ret = MESA_load_profile_string_nodef(sc->local_cfgfile, sec_symbol, "obp_device", str_obp_dev, + sizeof(str_obp_dev) - 1); + if (ret > 0) + { + uint32_t channel_id = 0; + ret = MESA_load_profile_uint_nodef(sc->local_cfgfile, sec_symbol, "obp_segment", &channel_id); + if (ret >= 0) + { + olp_set_used(str_obp_dev, channel_id); + } + } } /* Check group num */ diff --git a/service/src/olp.c b/service/src/olp.c index 08c8457..e2b8438 100644 --- a/service/src/olp.c +++ b/service/src/olp.c @@ -31,9 +31,12 @@ #include <olp_dev.h> struct olp_manager_main * g_olp_mgr_main; +extern int g_olp6500_config_ready; -int olp6500_init(struct sc_main * sc_main); +int olp6500_init(struct olp_manager_main * olp_mgr_main, char * cfgfile); cJSON * olp6500_monit_loop(struct sc_main * sc_main); +int olp6500_set_used_state(struct olp_device * olp_dev, char * dev_sym, uint32_t channel_id); +int olp6500_config_reload(); cJSON * olp_manager_monit_loop(struct sc_main * sc_main) { @@ -42,6 +45,19 @@ cJSON * olp_manager_monit_loop(struct sc_main * sc_main) return json_root; } +int olp_config_reload(struct sc_main * sc_main) +{ + olp6500_config_reload(); + return RT_SUCCESS; +} + +int olp_set_used(char * dev_sym, uint32_t channel_id) +{ + olp6500_set_used_state(g_olp_mgr_main->olp6500_main, dev_sym, channel_id); + __atomic_exchange_n(&g_olp6500_config_ready, 1, __ATOMIC_SEQ_CST); + return RT_SUCCESS; +} + int olp_manager_init(struct sc_main * sc_main) { int ret = 0; @@ -51,7 +67,7 @@ int olp_manager_init(struct sc_main * sc_main) g_olp_mgr_main = olp_mgr_main; sc_main->olp_mgr_main = olp_mgr_main; - ret = olp6500_init(sc_main); + ret = olp6500_init(olp_mgr_main, sc_main->local_dyfile); if (ret != RT_SUCCESS) { MR_ERROR("OLP_6500 initialization failed. "); diff --git a/service/src/olp_6500.c b/service/src/olp_6500.c index 4f9ddb0..47d0198 100644 --- a/service/src/olp_6500.c +++ b/service/src/olp_6500.c @@ -40,35 +40,17 @@ #define OLP6500_WORK_LINE_OBJECT (0x1070) #define OLP6500_SWITCHBACK_OBJECT (0x1020) #define OLP6500_CHANNEL_INFO_OBJECT (0x0200) +#define OLP6500_CHANNEL_CONF_OBJECT (0x0501) #define LINE_STATUS_INLINE (0x30) #define LINE_STATUS_BYPASS (0xc0) -#define OLP6500_TIMER_ONE_CYCLE_MS 5000 +#define OLP6500_TIMER_ONE_CYCLE_US 5000 +#define OLP6500_RELOAD_CONFIG_CYCLE_US 1000 #define OLP6500_LOAD_CONFIG_NOT_READY 0 #define OLP6500_LOAD_CONFIG_READY 1 -#define MR_OLP6500_TOPIC_FULL_UPDATE "OLP6500FullUpdate" -#define OLP6500_CJSON_KEY_ARRAY "OPBArray" -#define OLP6500_CJSON_KEY_DEV_NAME "name" -#define OLP6500_CJSON_KEY_TYPE "type" -#define OLP6500_CJSON_KEY_CONNECT "connect" -#define OLP6500_CJSON_KEY_ADDR "addr" -#define OLP6500_CJSON_KEY_PORT "port" -#define OLP6500_CJSON_KEY_SEGMENT "segment" -#define OLP6500_CJSON_KEY_SEGMENT_ID "segment_id" -#define OLP6500_CJSON_KEY_WORKLINE "workline" -#define OLP6500_CJSON_KEY_HEARTBEAT "heartbeat" -#define OLP6500_CJSON_KEY_HEARTBEAT_SEND_INTERVAL_IN_MS "heartbeat_send_interval_in_ms" -#define OLP6500_CJSON_KEY_HEARTBEAT_TIMEOUT_INTERVAL_IN_MS "heartbeat_timeout_interval_in_ms" -#define OLP6500_CJSON_KEY_HEARTBEAT_LOST_THRESHOLD "heartbeat_lost_threshold" -#define OLP6500_CJSON_KEY_NONREVERTIVE_MODE "nonrevertive_mode" - -/* Dynamic classifier rule result */ -#define OLP6500_RPC_RESULT "Result" -#define OLP6500_RPC_ERR_REASON "ErrReason" - enum { OLP_TIMER_DISABLE, @@ -91,10 +73,23 @@ enum OLP_HEARTBEAT_PACKET = 4, OLP_GET_CHANNEL_INFO = 5, + OLP_GET_CHANNEL_CONF = 6, OLP_OBJECT_MAX }; +enum +{ + OLP_SUCCESS = 0, + OLP_ERR_CODE_CONN_FAIL = 1, + OLP_ERR_CODE_GET_CHANNEL_INFO_FAIL = 2, + OLP_ERR_CODE_HB_MODE_INCONSISTENT = 3, + OLP_ERR_CODE_HB_INTERVAL_INCONSISTENT = 4, + OLP_ERR_CODE_HB_COUNT_INCONSISTENT = 5, + OLP_ERR_CODE_WORK_LINE_INCONSISTENT = 6, + OLP_ERR_CODE_SW_BACK_INCONSISTENT = 7, +}; + /* * Heartbeat Switch Data Format * 0 1 2 3 @@ -175,6 +170,42 @@ struct channel_info_data int16_t r2_optical_power; }__attribute__((packed)); +struct channel_conf_data +{ + uint8_t card_function; + uint8_t reserved_1; + uint8_t work_line; + uint16_t reserved_2; + uint8_t work_mode; + uint8_t tx_wavelength; + uint8_t rx_wavelength; + uint16_t switch_delay; + uint16_t switch_back_delay; + int16_t tx_alarm_threshold; + int16_t t1_alarm_threshold; + int16_t t2_alarm_threshold; + int16_t rx_alarm_threshold; + int16_t r1_alarm_threshold; + int16_t r2_alarm_threshold; + int16_t switch_r1_threshold; + int16_t switch_r2_threshold; + int16_t high_temperature_alarm_threshold; + int16_t low_temperature_alarm_threshold; + uint8_t switch_back_mode; + uint16_t mode_back_delay; + uint8_t key_board; + uint8_t bypass_mode; + uint8_t bypass_back_mode; + uint8_t power_down_mode; + uint8_t power_down_delay; + uint8_t heart_mode; + uint8_t heart_detect; + uint8_t heart_idle_delay; + uint8_t heart_interval; + uint8_t heart_count; + uint8_t CRC; +}__attribute__((packed)); + /* * OLP6500 Format * 0 1 2 3 @@ -206,11 +237,15 @@ struct olp6500_packet struct work_line_data work_line; struct switch_back_data sw_back; struct channel_info_data channel_info; + struct channel_conf_data channel_conf; char data[0]; }; }__attribute__((packed)); -int olp6500_config_ready; +char *g_cfgfile; +int g_olp6500_config_ready; +int g_olp6500_config_reload; +struct olp_device * g_olp6500_dev; uint16_t olp6500_object_map[OLP_OBJECT_MAX] = { [OLP_SET_HEARTBEAT_SWITCH] = OLP6500_HEARTBEAT_SWITCH_OBJECT, [OLP_SET_WORK_MODE] = OLP6500_WORK_MODE_OBJECT, @@ -218,460 +253,196 @@ uint16_t olp6500_object_map[OLP_OBJECT_MAX] = { [OLP_SET_SWITCHBACK_MODE] = OLP6500_SWITCHBACK_OBJECT, [OLP_HEARTBEAT_PACKET] = OLP6500_HEARTBEAT_PACKET_OBJECT, [OLP_GET_CHANNEL_INFO] = OLP6500_CHANNEL_INFO_OBJECT, + [OLP_GET_CHANNEL_CONF] = OLP6500_CHANNEL_CONF_OBJECT, }; -int olp6500_construct_packet(struct olp_channel * channel, int object, char *buff); -int olp6500_send_command_sync(struct olp_dev_desc *dev_desc, uint16_t object, char *send_buff, int send_len, char *recv_buff, int recv_len); - // void * heartbeat_recv_thread(void * args) // { // return NULL; // } -#if 0 -/* - * [olp0:0] - * state = 0 - * heartbeat = 1 - * heartbeat_send_interval_in_ms = 300 - * heartbeat_timeout_interval_in_ms = 300 - * heartbeat_lost_threshold = 3 - * nonrevertive_mode = 1 - */ -static int olp6500_channel_config_load(struct olp_dev_desc * olp_dev_desc, char *cfgfile, char *devsym) +char * str_olp_device_type(enum olp_device_type device_type) { - int ret = 0; - struct olp_channel * channel; - olp_dev_desc->channels = ZMALLOC(sizeof(struct olp_channel) * NR_OLP6500_CHANNEL_PER_DEVICE_MAX); - MR_VERIFY_MALLOC(olp_dev_desc->channels); - - for (uint32_t i = 0; i < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; i++) + switch(device_type) { - char chann_section[MR_SYMBOL_MAX] = {0}; - snprintf(chann_section, sizeof(chann_section) - 1, "%s:%u", devsym, i); - - uint32_t olp_channel_state = 0; - ret = MESA_load_profile_uint_nodef(cfgfile, chann_section, "state", &olp_channel_state); - if (ret < 0) - { - MR_DEBUG("state is not existed in section %s, ignore this section", chann_section); - continue; - } - - uint32_t olp_channel_heartbeat = 0; - ret = MESA_load_profile_uint_nodef(cfgfile, chann_section, "heartbeat", &olp_channel_heartbeat); - if (ret < 0) - { - MR_DEBUG("heartbeat is not existed in section %s, ignore this section", chann_section); - continue; - } - - channel = &olp_dev_desc->channels[i]; - channel->olp_channel_id = i; - channel->used = OLP_CHANNEL_STATE_USED; - channel->state = olp_channel_state; - channel->dev_desc = olp_dev_desc; - channel->en_heartbeat = olp_channel_heartbeat; - - MESA_load_profile_uint_nodef(cfgfile, chann_section, "heartbeat_timeout_interval_in_ms", &channel->heartbeat_timeout_interval_in_ms); - MESA_load_profile_uint_nodef(cfgfile, chann_section, "heartbeat_send_interval_in_ms", &channel->heartbeat_send_interval_in_ms); - MESA_load_profile_uint_nodef(cfgfile, chann_section, "heartbeat_lost_threshold", &channel->heartbeat_lost_threshold); - MESA_load_profile_uint_nodef(cfgfile, chann_section, "nonrevertive_mode", &channel->nonrevertive_mode); + case OLP_DEVICE_TYPE_NIAGARA_3296: + return "NIAGARA-3296"; + case OLP_DEVICE_TYPE_OLP_6500: + return "OLP-6500"; + default: + return ""; } - return RT_SUCCESS; } -/* config example: - * [olp_device:0] - * name = olp0 - * type = 2 - * connect = 3 - * in_addr = 1.1.1.1 - * port = 6800 - */ -int olp6500_config_load(struct olp_manager_main * olp_mgr_main, char *cfgfile) +char * str_olp_connect_type(enum olp_connect_type conn_type) { - int ret = 0; - - for (uint32_t i = 0; i < NR_OLP_DEVICE_MAX; i++) + switch(conn_type) { - char dev_symbol[MR_SYMBOL_MAX] = {0}; - snprintf(dev_symbol, sizeof(dev_symbol) - 1, "olp_device:%u", i); - - uint32_t olp_dev_type = 0; - MESA_load_profile_uint_def(cfgfile, dev_symbol, "type", &olp_dev_type, OLP_DEVICE_TYPE_UNKNOWN); - - if (olp_dev_type != OLP_DEVICE_TYPE_OLP_6500) - { - MR_DEBUG("type is not OLP_6500 in section %s, ignore this section", dev_symbol); - continue; - } - - if (olp_mgr_main->nr_olp_dev_descs == NR_OLP_DEVICE_MAX) - { - MR_WARNING("failed to add OLP_6500 config, Configured quantity has reached its maximum limit."); - continue; - } - - struct olp_dev_desc * olp_dev_desc = ZMALLOC(sizeof(struct olp_dev_desc)); - MR_VERIFY_MALLOC(olp_dev_desc); - - MESA_load_profile_string_nodef(cfgfile, dev_symbol, "name", olp_dev_desc->devsym, - sizeof(olp_dev_desc->devsym) - 1); - olp_dev_desc->type = OLP_DEVICE_TYPE_OLP_6500; - - uint32_t olp_conn_type = 0; - MESA_load_profile_uint_def(cfgfile, dev_symbol, "connect", &olp_conn_type, OLP_CONNECT_TYPE_UNKNOW); - olp_dev_desc->conn_type = olp_conn_type; - - if (olp_dev_desc->conn_type == OLP_CONNECT_TYPE_NETWORK) - { - char str_in_addr[INET_ADDRSTRLEN] = {0}; - MESA_load_profile_string_nodef(cfgfile, dev_symbol, "in_addr", str_in_addr, sizeof(str_in_addr)); - ret = inet_pton(AF_INET, str_in_addr, &olp_dev_desc->network.addr.sin_addr); - if (ret <= 0) - { - MR_CFGERR_INVALID_FORMAT(cfgfile, dev_symbol, "in_addr"); - return RT_ERR; - } - - uint32_t port = 0; - ret = MESA_load_profile_uint_nodef(cfgfile, dev_symbol, "port", &port); - if (ret < 0) - { - MR_CFGERR_INVALID_FORMAT(cfgfile, dev_symbol, "port"); - return RT_ERR; - } - - olp_dev_desc->network.addr.sin_family = AF_INET; - olp_dev_desc->network.addr.sin_port = htons(port); - } - olp6500_channel_config_load(olp_dev_desc, cfgfile, olp_dev_desc->devsym); - - olp_mgr_main->olp_dev_descs[olp_mgr_main->nr_olp_dev_descs++] = olp_dev_desc; + case OLP_CONNECT_TYPE_COM: + return "COM"; + case OLP_CONNECT_TYPE_USB: + return "USB"; + case OLP_CONNECT_TYPE_NETWORK: + return "NETWORK"; + default: + return ""; } - - return RT_SUCCESS; } -int olp6500_enable_dev(struct olp_manager_main * olp_mgr_main, char *cfgfile) +char * str_olp_workline(enum olp_channel_state state) { - int ret = 0; - uint32_t g_vwire_max_entry = 256; - - for (uint32_t i = 0; i < g_vwire_max_entry; i++) + switch(state) { - char sec_symbol[MR_SYMBOL_MAX] = {0}; - snprintf(sec_symbol, sizeof(sec_symbol) - 1, "vwire:%u", i); - - char str_opb_dev[MR_SYMBOL_MAX] = {0}; - ret = MESA_load_profile_string_nodef(cfgfile, sec_symbol, "opb-device", str_opb_dev, - sizeof(str_opb_dev) - 1); - if (ret > 0) - { - int channel_id = -1; - ret = MESA_load_profile_int_nodef(cfgfile, sec_symbol, "opb-segment", &channel_id); - if (ret >= 0) - { - struct olp_dev_desc *dev_desc = NULL; - dev_desc = olp6500_find_device_by_symbol(olp_mgr_main, str_opb_dev); - if (dev_desc == NULL) - { - continue; - } - olp6500_apply_control_command_to_peer(dev_desc, channel_id); - } - } + case OLP_CHANNEL_STATE_FORCE_INLINE: + return "INLINE"; + case OLP_CHANNEL_STATE_FORCE_BYPASS: + return "BYPASS"; + case OLP_CHANNEL_STATE_TAP: + return "TAP"; + default: + return ""; } - return RT_SUCCESS; } -#endif -void olp6500_dump(struct olp_manager_main *olp_mgr_main) +char * str_olp_enable_or_disable(uint32_t value) +{ + if (value) + return "ENABLE"; + else + return "DISABLE"; +} + +void olp6500_device_dump_one(struct olp_dev_desc * dev_desc, uint32_t channel_id) { - struct olp_dev_desc * olp_dev_desc = NULL; struct olp_channel * channel = NULL; char str_ip_addr[INET_ADDRSTRLEN] = {0}; uint16_t port; - MR_INFO("olp devices:%u", olp_mgr_main->nr_olp_dev_descs); - for (uint32_t i = 0; i < olp_mgr_main->nr_olp_dev_descs; i++) + MR_INFO("OLP-6500 device name:%s: is used", dev_desc->devsym); + MR_INFO("\tdevice_type:\t\t\t\t\t%s", str_olp_device_type(dev_desc->type)); + MR_INFO("\tconnect_type:\t\t\t\t\t%s", str_olp_connect_type(dev_desc->conn_type)); + if (dev_desc->conn_type == OLP_CONNECT_TYPE_NETWORK) { - olp_dev_desc = olp_mgr_main->olp_dev_descs[i]; - inet_ntop(AF_INET, &(olp_dev_desc->network.addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); - port = ntohs(olp_dev_desc->network.addr.sin_port); - MR_INFO("olp 6500 name:%s, type:%d, conn_type:%d, ipaddr:%s, port:%u", - olp_dev_desc->devsym, - olp_dev_desc->type, - olp_dev_desc->conn_type, - str_ip_addr, - port); - for (uint32_t j = 0; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) - { - channel = &olp_dev_desc->channels[j]; - if (channel->used == OLP_CHANNEL_STATE_UNUSED) - { - continue; - } - MR_INFO("channel: channel_id:%u, used:%d, state:%d, en_heartbeat:%u, heartbeat_send_interval_in_ms:%u, heartbeat_timeout_interval_in_ms:%u, heartbeat_lost_threshold:%u, nonrevertive_mode:%u", - channel->olp_channel_id, - channel->used, - channel->state, - channel->en_heartbeat, - channel->heartbeat_send_interval_in_ms, - channel->heartbeat_timeout_interval_in_ms, - channel->heartbeat_lost_threshold, - channel->nonrevertive_mode); - } + inet_ntop(AF_INET, &(dev_desc->network.addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); + port = ntohs(dev_desc->network.addr.sin_port); + MR_INFO("\tipaddr:\t\t\t\t\t\t%s", str_ip_addr); + MR_INFO("\tport:\t\t\t\t\t\t%u", port); } -} - -int olp6500_get_optical_power( char *buff, struct olp_channel * channel) -{ - struct olp6500_packet *pkt = (struct olp6500_packet *)buff; - if (pkt->object != htons(OLP6500_CHANNEL_INFO_OBJECT) || pkt->len != 17) - { - return RT_ERR; - } - - int16_t r1_optical_power = ntohs(pkt->channel_info.r1_optical_power); - int16_t r2_optical_power = ntohs(pkt->channel_info.r2_optical_power); - int16_t r3_optical_power = ntohs(pkt->channel_info.r3_optical_power); - int16_t r4_optical_power = ntohs(pkt->channel_info.r4_optical_power); - channel->runtime.r1_optical_power = ((float)r1_optical_power)/100; - channel->runtime.r2_optical_power = ((float)r2_optical_power)/100; - channel->runtime.r3_optical_power = ((float)r3_optical_power)/100; - channel->runtime.r4_optical_power = ((float)r4_optical_power)/100; - channel->runtime.traffic_mode = pkt->channel_info.work_line; - return RT_SUCCESS; + channel = &dev_desc->channels[channel_id]; + MR_INFO("\tchannel_id:\t\t\t\t\t%u", channel->olp_channel_id); + MR_INFO("\t\tused:\t\t\t\t\t%d", channel->used); + MR_INFO("\t\tworkline:\t\t\t\t%s", str_olp_workline(channel->state)); + MR_INFO("\t\theartbeat_mode:\t\t\t\t%s", str_olp_enable_or_disable(channel->en_heartbeat)); + MR_INFO("\t\theartbeat_send_interval_in_ms:\t\t%u", channel->heartbeat_send_interval_in_ms); + MR_INFO("\t\theartbeat_timeout_interval_in_ms:\t%u", channel->heartbeat_timeout_interval_in_ms); + MR_INFO("\t\theartbeat_lost_threshold:\t\t%u", channel->heartbeat_lost_threshold); + MR_INFO("\t\tnonrevertive_mode:\t\t\t%s", str_olp_enable_or_disable(channel->nonrevertive_mode)); } -cJSON * olp6500_monit_loop(struct sc_main * sc_main) +void olp6500_device_dump(struct olp_device * olp_dev) { - int ret = 0; - int pkt_len = 0; - char str_time[80] = {0}; - char buff[BUFF_MAX] = {0}; - char str_olp_name[MR_STRING_MAX] = {0}; - char str_optical_power[16] = {0}; - struct olp_dev_desc * dev_desc = NULL; + struct olp_dev_desc * olp_dev_desc = NULL; struct olp_channel * channel = NULL; - struct olp_manager_main *olp_mgr_main = sc_main->olp_mgr_main; - - cJSON * json_root = cJSON_CreateObject(); - - if (__atomic_load_n(&olp6500_config_ready, __ATOMIC_RELAXED) == OLP6500_LOAD_CONFIG_NOT_READY) - { - goto end; - } + char str_ip_addr[INET_ADDRSTRLEN] = {0}; + uint16_t port; - for (int index = 0; index < olp_mgr_main->nr_olp_dev_descs; index++) + for (uint32_t i = 0; i < olp_dev->nr_olp_dev_descs; i++) { - dev_desc = olp_mgr_main->olp_dev_descs[index]; - if (dev_desc->type != OLP_DEVICE_TYPE_OLP_6500) - continue; - - __atomic_fetch_add(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); + olp_dev_desc = olp_dev->olp_dev_descs[i]; - for (uint32_t j = 0; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) + MR_INFO("OLP-6500 device name:%s", olp_dev_desc->devsym); + MR_INFO("\tdevice_type:\t\t\t\t\t%s", str_olp_device_type(olp_dev_desc->type)); + MR_INFO("\tconnect_type:\t\t\t\t\t%s", str_olp_connect_type(olp_dev_desc->conn_type)); + if (olp_dev_desc->conn_type == OLP_CONNECT_TYPE_NETWORK) { - channel = &dev_desc->channels[j]; - if (channel->used == OLP_CHANNEL_STATE_UNUSED) + inet_ntop(AF_INET, &(olp_dev_desc->network.addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); + port = ntohs(olp_dev_desc->network.addr.sin_port); + MR_INFO("\tipaddr:\t\t\t\t\t\t%s", str_ip_addr); + MR_INFO("\tport:\t\t\t\t\t\t%u", port); + } + for (uint32_t j = 1; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) + { + channel = &olp_dev_desc->channels[j]; + if (channel->olp_channel_id == 0) { continue; } - - pkt_len = olp6500_construct_packet(channel, OLP_GET_CHANNEL_INFO, buff); - if (pkt_len > 0) - { - ret = olp6500_send_command_sync(dev_desc, OLP_GET_CHANNEL_INFO, buff, pkt_len, buff, BUFF_MAX); - if (ret != RT_SUCCESS) - { - continue; - } - - cJSON * item_obj = cJSON_CreateObject(); - - olp6500_get_optical_power(buff, channel); - - cJSON_AddNumberToObject(item_obj, "olp_channel_id", channel->olp_channel_id); - switch (channel->runtime.traffic_mode) - { - case 0x03: - cJSON_AddStringToObject(item_obj, "traffic_mode", "inline"); - break; - case 0x0c: - cJSON_AddStringToObject(item_obj, "traffic_mode", "bypass"); - break; - default: - cJSON_AddStringToObject(item_obj, "traffic_mode", "error"); - } - - snprintf(str_optical_power, sizeof(str_optical_power), "%.2f", channel->runtime.r1_optical_power); - cJSON_AddStringToObject(item_obj, "r1", str_optical_power); - snprintf(str_optical_power, sizeof(str_optical_power), "%.2f", channel->runtime.r2_optical_power); - cJSON_AddStringToObject(item_obj, "r2", str_optical_power); - snprintf(str_optical_power, sizeof(str_optical_power), "%.2f", channel->runtime.r3_optical_power); - cJSON_AddStringToObject(item_obj, "r3", str_optical_power); - snprintf(str_optical_power, sizeof(str_optical_power), "%.2f", channel->runtime.r4_optical_power); - cJSON_AddStringToObject(item_obj, "r4", str_optical_power); - snprintf(str_time, sizeof(str_time), "%ld", channel->runtime.last_active_time.tv_sec); - cJSON_AddStringToObject(item_obj, "last_active_time", str_time); - - snprintf(str_olp_name, sizeof(str_olp_name) - 1, "olp_name:%s", dev_desc->devsym); - cJSON_AddItemToObject(json_root, str_olp_name, item_obj); - } + MR_INFO("\tchannel_id:\t\t\t\t\t%u", channel->olp_channel_id); + MR_INFO("\t\tused:\t\t\t\t\t%d", channel->used); + MR_INFO("\t\tworkline:\t\t\t\t%s", str_olp_workline(channel->state)); + MR_INFO("\t\theartbeat_mode:\t\t\t\t%s", str_olp_enable_or_disable(channel->en_heartbeat)); + MR_INFO("\t\theartbeat_send_interval_in_ms:\t\t%u", channel->heartbeat_send_interval_in_ms); + MR_INFO("\t\theartbeat_timeout_interval_in_ms:\t%u", channel->heartbeat_timeout_interval_in_ms); + MR_INFO("\t\theartbeat_lost_threshold:\t\t%u", channel->heartbeat_lost_threshold); + MR_INFO("\t\tnonrevertive_mode:\t\t\t%s", str_olp_enable_or_disable(channel->nonrevertive_mode)); } } - - for (int index = 0; index < olp_mgr_main->nr_olp_dev_descs; index++) - { - dev_desc = olp_mgr_main->olp_dev_descs[index]; - if (dev_desc->type != OLP_DEVICE_TYPE_OLP_6500) - continue; - __atomic_fetch_sub(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); - } -end: - return json_root; } -void olp6500_send_heartbeat_handler(int socket, struct olp_channel *channel) +struct olp_dev_desc * olp6500_find_device_by_symbol(struct olp_device * olp_dev, char * olp_dev_sym) { - int ret = 0; - int pkt_len = 0; - char buff[BUFF_MAX] = {0}; - struct olp_dev_desc *dev_desc = channel->dev_desc; - struct sockaddr_in *addr = &dev_desc->network.addr; - - pkt_len = olp6500_construct_packet(channel, OLP_HEARTBEAT_PACKET, buff); - if (pkt_len <= 0) - { - return; - } - - switch (dev_desc->conn_type) - { - case OLP_CONNECT_TYPE_NETWORK: - do { - ret = sendto(socket, buff, pkt_len, 0, (struct sockaddr*)addr, sizeof(*addr)); - } while(ret == -1 && errno == EINTR); - - break; - default: - break; - } - return; -} - -void * olp6500_cycle_send_heartbeat(void * args) -{ - pthread_detach(pthread_self()); - - struct olp_channel *channel = (struct olp_channel *)args; - struct olp_dev_desc *dev_desc = channel->dev_desc; - struct timespec current_time; - struct timespec send_pkt_last_time; - struct timespec interval_time; - struct timeval timeout; - timeout.tv_sec = 5; - timeout.tv_usec = 0; - - memset(&send_pkt_last_time, 0, sizeof(send_pkt_last_time)); - - int sock = socket(AF_INET, SOCK_DGRAM, 0); - if (sock < 0) - { - return NULL; - } - - setsockopt(sock, SOL_SOCKET, SO_SNDTIMEO, &timeout, sizeof(timeout)); - setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, &timeout, sizeof(timeout)); + struct olp_dev_desc * dev_desc = NULL; - __atomic_fetch_add(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); - while(__atomic_load_n(&channel->timer.enable, __ATOMIC_RELAXED) == OLP_TIMER_ENABLE) + for (uint32_t i = 0; i < olp_dev->nr_olp_dev_descs; i++) { - clock_gettime(CLOCK_MONOTONIC, ¤t_time); - timespec_diff(&send_pkt_last_time, ¤t_time, &interval_time); - if ((interval_time.tv_sec * 1000 + interval_time.tv_nsec/1000/1000) >= channel->heartbeat_send_interval_in_ms) + dev_desc = olp_dev->olp_dev_descs[i]; + if (dev_desc->type == OLP_DEVICE_TYPE_OLP_6500 && + strncmp(olp_dev_sym, dev_desc->devsym, MR_SYMBOL_MAX) == 0) { - send_pkt_last_time = current_time; - struct timespec last_active_time; - clock_gettime(CLOCK_REALTIME, &last_active_time); - olp6500_send_heartbeat_handler(sock, channel); - channel->runtime.last_active_time = last_active_time; + return dev_desc; } - usleep(OLP6500_TIMER_ONE_CYCLE_MS); } - __atomic_fetch_sub(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); - close(sock); return NULL; } -int olp6500_create_thread_for_heartbeat(struct olp_channel *channel) -{ - int ret = 0; - pthread_t tid; - - if (channel->en_heartbeat == OLP_CHANNEL_HEARTBEAT_DISABLE) - { - return RT_SUCCESS; - } - - __atomic_exchange_n(&channel->timer.enable, OLP_TIMER_ENABLE, __ATOMIC_SEQ_CST); - ret = pthread_create(&tid, NULL, olp6500_cycle_send_heartbeat, (void *)channel); - if (ret < 0) - { - MR_ERROR("OLP_6500 create send heartbeat packet thread failed : %s", strerror(errno)); - return RT_ERR; - } - return RT_SUCCESS; -} - char *olp6500_str_object(uint16_t object) { switch(object) { case OLP_SET_HEARTBEAT_SWITCH: - return "OLP_HEARTBEAT_SWITCH"; + return "HEARTBEAT_SWITCH"; case OLP_SET_WORK_MODE: - return "OLP_WORK_MODE"; + return "WORK_MODE"; case OLP_SET_WORK_LINE: - return "OLP_WORK_LINE"; + return "WORK_LINE"; case OLP_SET_SWITCHBACK_MODE: - return "OLP_SWITCHBACK_MODE"; + return "SWITCHBACK_MODE"; case OLP_HEARTBEAT_PACKET: - return "OLP_HEARTBEAT_PACKET"; + return "HEARTBEAT_PACKET"; case OLP_GET_CHANNEL_INFO: - return "OLP_GET_CHANNEL_INFO"; + return "GET_CHANNEL_INFO"; + case OLP_GET_CHANNEL_CONF: + return "GET_CHANNEL_CONF"; default: break; } return NULL; } -int olp6500_check_recv_data(char *buff, uint16_t object) +int olp6500_check_recv_data(char * buff, uint16_t object) { - struct olp6500_packet *pkt = (struct olp6500_packet*)buff; + struct olp6500_packet * pkt = (struct olp6500_packet*)buff; + if (ntohs(pkt->object) != olp6500_object_map[object]) { - MR_ERROR("Object [%s] failed! receive data: 0xFF 0xEE", olp6500_str_object(object)); + MR_ERROR("deployment object [%s] failed! receive data: 0xFF 0xEE", olp6500_str_object(object)); return RT_ERR; } if (pkt->len == 2 && pkt->data[0] == 0xFF && pkt->data[1] == 0xEE) { - MR_ERROR("Object [%s] failed! receive data: 0xFF 0xEE", olp6500_str_object(object)); + MR_ERROR("deployment object [%s] failed! receive data: 0xFF 0xEE", olp6500_str_object(object)); return RT_ERR; } return RT_SUCCESS; } -int olp6500_send_command_over_network_sync(struct olp_dev_desc *dev_desc, char *send_buff, int send_len, char *recv_buff, int recv_len) +int olp6500_send_command_over_network_sync(struct olp_dev_desc * dev_desc, char * send_buff, int send_len, char * recv_buff, int recv_len) { int ret = 0; int length = 0; - char str_ip_addr[INET_ADDRSTRLEN] = {0}; + // char str_ip_addr[INET_ADDRSTRLEN] = {0}; struct sockaddr_in addr = dev_desc->network.addr; struct timeval timeout; @@ -693,8 +464,8 @@ int olp6500_send_command_over_network_sync(struct olp_dev_desc *dev_desc, char * if (ret == -1) { - inet_ntop(AF_INET, &(addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); - MR_ERROR("send request to [%s] fail: %s", str_ip_addr, strerror(errno)); + // inet_ntop(AF_INET, &(addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); + // MR_ERROR("send request to [%s] fail: %s", str_ip_addr, strerror(errno)); goto errout; } @@ -704,8 +475,8 @@ int olp6500_send_command_over_network_sync(struct olp_dev_desc *dev_desc, char * if (length <= 0) { - inet_ntop(AF_INET, &(addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); - MR_ERROR("recv from [%s] fail : %s", str_ip_addr, strerror(errno)); + // inet_ntop(AF_INET, &(addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); + // MR_ERROR("recv from [%s] fail : %s", str_ip_addr, strerror(errno)); goto errout; } close(sock); @@ -715,7 +486,7 @@ errout: return RT_ERR; } -int olp6500_send_command_sync(struct olp_dev_desc *dev_desc, uint16_t object, char *send_buff, int send_len, char *recv_buff, int recv_len) +int olp6500_send_command_sync(struct olp_dev_desc * dev_desc, uint16_t object, char * send_buff, int send_len, char * recv_buff, int recv_len) { int length = 0; @@ -727,7 +498,7 @@ int olp6500_send_command_sync(struct olp_dev_desc *dev_desc, uint16_t object, ch { return RT_ERR; } - + break; case OLP_CONNECT_TYPE_COM: case OLP_CONNECT_TYPE_USB: break; @@ -738,10 +509,10 @@ int olp6500_send_command_sync(struct olp_dev_desc *dev_desc, uint16_t object, ch return olp6500_check_recv_data(recv_buff, object); } -int olp6500_construct_packet(struct olp_channel * channel, int object, char *buff) +int olp6500_construct_packet(struct olp_channel * channel, int object, char * buff) { int length = 0; - struct olp6500_packet *pkt = (struct olp6500_packet *)buff; + struct olp6500_packet * pkt = (struct olp6500_packet *)buff; switch(object) { @@ -794,7 +565,7 @@ int olp6500_construct_packet(struct olp_channel * channel, int object, char *buf pkt->port = 0; pkt->len = 1; - if (channel->state == OLP_CHANNEL_STATE_FORCE_ACTIVE) + if (channel->state == OLP_CHANNEL_STATE_FORCE_INLINE) { pkt->work_line.line_status = LINE_STATUS_INLINE; } @@ -833,6 +604,13 @@ int olp6500_construct_packet(struct olp_channel * channel, int object, char *buf pkt->port = 0; pkt->len = 0; length = 6; + case OLP_GET_CHANNEL_CONF: + pkt->action = OLP_CONFIG_GET; + pkt->slot = channel->olp_channel_id; + pkt->object = htons(olp6500_object_map[object]); + pkt->port = 0; + pkt->len = 0; + length = 6; default: break; } @@ -840,354 +618,808 @@ out: return length; } -struct olp_dev_desc *olp6500_find_device_by_symbol(struct olp_manager_main * olp_mgr_main, char *olp_dev_sym) +void olp6500_send_heartbeat_handler(int socket, struct olp_channel * channel) { - struct olp_dev_desc *dev_desc = NULL; + int ret = 0; + int pkt_len = 0; + char buff[BUFF_MAX] = {0}; + struct olp_dev_desc * dev_desc = channel->dev_desc; + struct sockaddr_in * addr = &dev_desc->network.addr; - for (uint32_t i = 0; i < olp_mgr_main->nr_olp_dev_descs; i++) + pkt_len = olp6500_construct_packet(channel, OLP_HEARTBEAT_PACKET, buff); + if (pkt_len <= 0) { - dev_desc = olp_mgr_main->olp_dev_descs[i]; - if (dev_desc->type == OLP_DEVICE_TYPE_OLP_6500 && - strncmp(olp_dev_sym, dev_desc->devsym, MR_SYMBOL_MAX) == 0) + return; + } + + switch (dev_desc->conn_type) + { + case OLP_CONNECT_TYPE_NETWORK: + do { + ret = sendto(socket, buff, pkt_len, 0, (struct sockaddr*)addr, sizeof(*addr)); + } while(ret == -1 && errno == EINTR); + + break; + default: + break; + } + return; +} + +void * olp6500_cycle_send_heartbeat(void * args) +{ + pthread_detach(pthread_self()); + + struct olp_channel * channel = (struct olp_channel *)args; + struct olp_dev_desc * dev_desc = channel->dev_desc; + struct timespec current_time; + struct timespec send_pkt_last_time; + struct timespec interval_time; + struct timeval timeout; + timeout.tv_sec = 5; + timeout.tv_usec = 0; + + memset(&send_pkt_last_time, 0, sizeof(send_pkt_last_time)); + + int sock = socket(AF_INET, SOCK_DGRAM, 0); + if (sock < 0) + { + return NULL; + } + + setsockopt(sock, SOL_SOCKET, SO_SNDTIMEO, &timeout, sizeof(timeout)); + setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, &timeout, sizeof(timeout)); + + __atomic_fetch_add(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); + while(__atomic_load_n(&channel->timer.enable, __ATOMIC_RELAXED) == OLP_TIMER_ENABLE) + { + clock_gettime(CLOCK_MONOTONIC, ¤t_time); + timespec_diff(&send_pkt_last_time, ¤t_time, &interval_time); + if ((interval_time.tv_sec * 1000 + interval_time.tv_nsec/1000/1000) >= channel->heartbeat_send_interval_in_ms) { - return dev_desc; + send_pkt_last_time = current_time; + struct timespec last_active_time; + clock_gettime(CLOCK_REALTIME, &last_active_time); + olp6500_send_heartbeat_handler(sock, channel); + channel->runtime.last_active_time = last_active_time; } + usleep(OLP6500_TIMER_ONE_CYCLE_US); } + __atomic_fetch_sub(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); + close(sock); return NULL; } -int olp6500_apply_control_command_to_peer(struct olp_dev_desc *dev_desc, uint32_t channel_id) +int olp6500_create_thread_send_heartbeat(struct olp_channel * channel) { int ret = 0; - int pkt_len = 0; - char buff[BUFF_MAX] = {0}; - struct olp_channel *channel = NULL; + pthread_t tid; - channel = &dev_desc->channels[channel_id]; - if (channel->used == OLP_CHANNEL_STATE_UNUSED) + if (channel->en_heartbeat == OLP_CHANNEL_HEARTBEAT_DISABLE) { + return RT_SUCCESS; + } + + __atomic_exchange_n(&channel->timer.enable, OLP_TIMER_ENABLE, __ATOMIC_SEQ_CST); + ret = pthread_create(&tid, NULL, olp6500_cycle_send_heartbeat, (void *)channel); + if (ret < 0) + { + MR_ERROR("OLP_6500 create send heartbeat packet thread failed : %s", strerror(errno)); return RT_ERR; } + return RT_SUCCESS; +} +int olp6500_apply_control_command_to_peer(struct olp_dev_desc * dev_desc, uint32_t channel_id) +{ + int ret = 0; + int pkt_len = 0; + char buff[BUFF_MAX] = {0}; + char str_ip_addr[INET_ADDRSTRLEN] = {0}; + struct olp_channel * channel = NULL; + + channel = &dev_desc->channels[channel_id]; + pkt_len = olp6500_construct_packet(channel, OLP_SET_HEARTBEAT_SWITCH, buff); - if (pkt_len > 0) + ret = olp6500_send_command_sync(dev_desc, OLP_SET_HEARTBEAT_SWITCH, buff, pkt_len, buff, BUFF_MAX); + if (ret != RT_SUCCESS) { - ret = olp6500_send_command_sync(dev_desc, OLP_SET_HEARTBEAT_SWITCH, buff, pkt_len, buff, BUFF_MAX); - if (ret != RT_SUCCESS) - { - return RT_ERR; - } + goto errout; } + pkt_len = olp6500_construct_packet(channel, OLP_SET_WORK_MODE, buff); - if (pkt_len > 0) + ret = olp6500_send_command_sync(dev_desc, OLP_SET_WORK_MODE, buff, pkt_len, buff, BUFF_MAX); + if (ret != RT_SUCCESS) { - ret = olp6500_send_command_sync(dev_desc, OLP_SET_WORK_MODE, buff, pkt_len, buff, BUFF_MAX); - if (ret != RT_SUCCESS) - { - return RT_ERR; - } + goto errout; } + pkt_len = olp6500_construct_packet(channel, OLP_SET_WORK_LINE, buff); if (pkt_len > 0) { ret = olp6500_send_command_sync(dev_desc, OLP_SET_WORK_LINE, buff, pkt_len, buff, BUFF_MAX); if (ret != RT_SUCCESS) { - return RT_ERR; + goto errout; } } + pkt_len = olp6500_construct_packet(channel, OLP_SET_SWITCHBACK_MODE, buff); - if (pkt_len > 0) + ret = olp6500_send_command_sync(dev_desc, OLP_SET_SWITCHBACK_MODE, buff, pkt_len, buff, BUFF_MAX); + if (ret != RT_SUCCESS) { - ret = olp6500_send_command_sync(dev_desc, OLP_SET_SWITCHBACK_MODE, buff, pkt_len, buff, BUFF_MAX); - if (ret != RT_SUCCESS) - { - return RT_ERR; - } + goto errout; } - olp6500_create_thread_for_heartbeat(channel); + olp6500_create_thread_send_heartbeat(channel); + channel->runtime.errcode = OLP_SUCCESS; return RT_SUCCESS; +errout: + if (channel->runtime.errcode != OLP_ERR_CODE_CONN_FAIL) + { + inet_ntop(AF_INET, &(dev_desc->network.addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); + MR_ERROR("The deployment of the OBP[%s:%u] configuration has encountered a failure. Reason: Connect %s:%u failed or configuration settings failed.", + dev_desc->devsym, + channel->olp_channel_id, + str_ip_addr, + ntohs(dev_desc->network.addr.sin_port)); + } + channel->runtime.errcode = OLP_ERR_CODE_CONN_FAIL; + return RT_ERR; } -/* +void * _olp6500_retry_apply_control_command(void * args) { - "OPBArray": [ + struct olp_dev_desc * dev_desc = NULL; + struct olp_channel * channel = NULL; + + while(1) + { + sleep(10); + + if (__atomic_load_n(&g_olp6500_config_ready, __ATOMIC_RELAXED) == OLP6500_LOAD_CONFIG_NOT_READY) { - "name": "opb1", - "type": 2, - "connect": 3, - "addr": "192.168.40.76", - "port": "6800", - "segment": [ + continue; + } + + for (uint32_t i = 0; i < g_olp6500_dev->nr_olp_dev_descs; i++) + { + dev_desc = g_olp6500_dev->olp_dev_descs[i]; + __atomic_fetch_add(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); + + if (dev_desc->type != OLP_DEVICE_TYPE_OLP_6500 || dev_desc->used != OLP_STATE_USED) + { + continue; + } + for (uint32_t j = 1; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) + { + channel = &dev_desc->channels[j]; + if (channel->used != OLP_STATE_USED) { - "segment_id": 7, - "workline": 1, - "heartbeat": 1, - "heartbeat_send_interval_in_ms": 60, - "heartbeat_timeout_interval_in_ms": 60, - "heartbeat_lost_threshold": 5, - "nonrevertive_mode": 1 + continue; } - ] + + if (channel->runtime.errcode == OLP_ERR_CODE_CONN_FAIL) + { + olp6500_apply_control_command_to_peer(dev_desc, channel->olp_channel_id); + } + } + } + + for (uint32_t i = 0; i < g_olp6500_dev->nr_olp_dev_descs; i++) + { + dev_desc = g_olp6500_dev->olp_dev_descs[i]; + __atomic_fetch_sub(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); } - ] + } + + return NULL; } - */ -int olp6500_cjson_parser(cJSON * req, struct olp_manager_main *olp_mgr_main, char *err_reason, uint32_t sz_err_reason) + +int olp6500_retry_apply_control_command() { - struct olp_channel * channel = NULL; - cJSON * olp_array = cJSON_GetObjectItem(req, OLP6500_CJSON_KEY_ARRAY); - if (olp_array == NULL) + int ret = 0; + pthread_t tid; + + ret = pthread_create(&tid, NULL, _olp6500_retry_apply_control_command, NULL); + if (ret < 0) { - snprintf(err_reason, sz_err_reason, "OLP6500Array parser cjson error, array is null ."); - MR_ERROR("%s", err_reason); + MR_ERROR("OLP_6500 create retry apply control command thread failed : %s", strerror(errno)); return RT_ERR; } + return RT_SUCCESS; +} + +/* + * [olp0:1] + * state = 0 + * heartbeat = 1 + * heartbeat_send_interval_in_ms = 300 + * heartbeat_timeout_interval_in_ms = 300 + * heartbeat_lost_threshold = 3 + * nonrevertive_mode = 1 + */ +static int olp6500_channel_config_load(struct olp_dev_desc * olp_dev_desc, char * cfgfile, char * devsym) +{ + int ret = 0; + struct olp_channel * channel; + olp_dev_desc->channels = ZMALLOC(sizeof(struct olp_channel) * NR_OLP6500_CHANNEL_PER_DEVICE_MAX); + MR_VERIFY_MALLOC(olp_dev_desc->channels); - int olp_array_num = cJSON_GetArraySize(olp_array); - if (olp_array_num > NR_OLP_DEVICE_MAX) + for (uint32_t i = 1; i < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; i++) { - snprintf(err_reason, sz_err_reason, "OLP6500Array num over max [%d] .", NR_OLP_DEVICE_MAX); - MR_ERROR("%s", err_reason); - return RT_ERR; + char channel_section[MR_SYMBOL_MAX] = {0}; + snprintf(channel_section, sizeof(channel_section) - 1, "%s:%u", devsym, i); + + uint32_t olp_channel_state = 0; + ret = MESA_load_profile_uint_nodef(cfgfile, channel_section, "state", &olp_channel_state); + if (ret < 0) + { + MR_DEBUG("state is not existed in section %s, ignore this section", channel_section); + continue; + } + + uint32_t olp_channel_heartbeat = 0; + ret = MESA_load_profile_uint_nodef(cfgfile, channel_section, "heartbeat", &olp_channel_heartbeat); + if (ret < 0) + { + MR_DEBUG("heartbeat is not existed in section %s, ignore this section", channel_section); + continue; + } + + channel = &olp_dev_desc->channels[i]; + channel->olp_channel_id = i; + channel->state = olp_channel_state; + channel->dev_desc = olp_dev_desc; + channel->en_heartbeat = olp_channel_heartbeat; + + MESA_load_profile_uint_nodef(cfgfile, channel_section, "heartbeat_timeout_interval_in_ms", &channel->heartbeat_timeout_interval_in_ms); + MESA_load_profile_uint_nodef(cfgfile, channel_section, "heartbeat_send_interval_in_ms", &channel->heartbeat_send_interval_in_ms); + MESA_load_profile_uint_nodef(cfgfile, channel_section, "heartbeat_lost_threshold", &channel->heartbeat_lost_threshold); + MESA_load_profile_uint_nodef(cfgfile, channel_section, "nonrevertive_mode", &channel->nonrevertive_mode); } + return RT_SUCCESS; +} + +/* + * [olp_device:0] + * name = olp0 + * type = 2 + * connect = 3 + * in_addr = 1.1.1.1 + * port = 6800 + */ +int olp6500_config_load(struct olp_device * olp_dev, char * cfgfile) +{ + int ret = 0; - for (int i = 0; i < olp_array_num; i++) + for (uint32_t i = 0; i < NR_OLP_DEVICE_MAX; i++) { - cJSON * olp_array_item = cJSON_GetArrayItem(olp_array, i); - - cJSON * cj_dev_name = cJSON_GetObjectItem(olp_array_item, OLP6500_CJSON_KEY_DEV_NAME); - cJSON * cj_type = cJSON_GetObjectItem(olp_array_item, OLP6500_CJSON_KEY_TYPE); - cJSON * cj_connect = cJSON_GetObjectItem(olp_array_item, OLP6500_CJSON_KEY_CONNECT); - cJSON * cj_addr = cJSON_GetObjectItem(olp_array_item, OLP6500_CJSON_KEY_ADDR); - cJSON * cj_port = cJSON_GetObjectItem(olp_array_item, OLP6500_CJSON_KEY_PORT); - cJSON * segment_array = cJSON_GetObjectItem(olp_array_item, OLP6500_CJSON_KEY_SEGMENT); - - if (cj_type->valueint != OLP_DEVICE_TYPE_OLP_6500) + char dev_symbol[MR_SYMBOL_MAX] = {0}; + snprintf(dev_symbol, sizeof(dev_symbol) - 1, "olp_device:%u", i); + + uint32_t olp_dev_type = 0; + MESA_load_profile_uint_def(cfgfile, dev_symbol, "type", &olp_dev_type, OLP_DEVICE_TYPE_UNKNOWN); + + if (olp_dev_type != OLP_DEVICE_TYPE_OLP_6500) + { + continue; + } + + if (olp_dev->nr_olp_dev_descs == NR_OLP_DEVICE_MAX) { + MR_WARNING("failed to add OLP_6500 config, Configured quantity has reached its maximum limit[%d].", NR_OLP_DEVICE_MAX); continue; } struct olp_dev_desc * olp_dev_desc = ZMALLOC(sizeof(struct olp_dev_desc)); MR_VERIFY_MALLOC(olp_dev_desc); - snprintf(olp_dev_desc->devsym, MR_SYMBOL_MAX, "%s", cj_dev_name->valuestring); + MESA_load_profile_string_nodef(cfgfile, dev_symbol, "name", olp_dev_desc->devsym, + sizeof(olp_dev_desc->devsym) - 1); olp_dev_desc->type = OLP_DEVICE_TYPE_OLP_6500; - olp_dev_desc->conn_type = cj_connect->valueint; - if (cj_addr) + + uint32_t olp_conn_type = 0; + MESA_load_profile_uint_def(cfgfile, dev_symbol, "connect", &olp_conn_type, OLP_CONNECT_TYPE_UNKNOW); + olp_dev_desc->conn_type = olp_conn_type; + + if (olp_dev_desc->conn_type == OLP_CONNECT_TYPE_NETWORK) { + char str_in_addr[INET_ADDRSTRLEN] = {0}; + MESA_load_profile_string_nodef(cfgfile, dev_symbol, "in_addr", str_in_addr, sizeof(str_in_addr)); + ret = inet_pton(AF_INET, str_in_addr, &olp_dev_desc->network.addr.sin_addr); + if (ret <= 0) + { + MR_CFGERR_INVALID_FORMAT(cfgfile, dev_symbol, "in_addr"); + return RT_ERR; + } + + uint32_t port = 0; + ret = MESA_load_profile_uint_nodef(cfgfile, dev_symbol, "port", &port); + if (ret < 0) + { + MR_CFGERR_INVALID_FORMAT(cfgfile, dev_symbol, "port"); + return RT_ERR; + } + olp_dev_desc->network.addr.sin_family = AF_INET; - inet_pton(AF_INET, cj_addr->valuestring, &olp_dev_desc->network.addr.sin_addr); + olp_dev_desc->network.addr.sin_port = htons(port); + } + olp6500_channel_config_load(olp_dev_desc, cfgfile, olp_dev_desc->devsym); + + olp_dev->olp_dev_descs[olp_dev->nr_olp_dev_descs++] = olp_dev_desc; + } + + return RT_SUCCESS; +} + +int olp6500_set_used_state(struct olp_device * olp_dev, char * dev_sym, uint32_t channel_id) +{ + struct olp_dev_desc * dev_desc = NULL; + dev_desc = olp6500_find_device_by_symbol(olp_dev, dev_sym); + if (dev_desc == NULL) + { + return RT_ERR; + } + dev_desc->channels[channel_id].used = OLP_STATE_USED; + dev_desc->used = OLP_STATE_USED; + + olp6500_apply_control_command_to_peer(dev_desc, channel_id); + olp6500_device_dump_one(dev_desc, channel_id); + return RT_SUCCESS; +} + +int olp6500_copy_device_state(struct olp_device * src, struct olp_device * dst) +{ + struct olp_channel * channel = NULL; + struct olp_dev_desc * src_dev_desc = NULL; + struct olp_dev_desc * dst_dev_desc = NULL; + + for (uint32_t i = 0; i < src->nr_olp_dev_descs; i++) + { + src_dev_desc = src->olp_dev_descs[i]; + if (src_dev_desc->type != OLP_DEVICE_TYPE_OLP_6500 || src_dev_desc->used != OLP_STATE_USED) + { + continue; } - if (cj_port) + + dst_dev_desc = olp6500_find_device_by_symbol(dst, src_dev_desc->devsym); + if (dst_dev_desc == NULL) { - int port = 0; - sscanf(cj_port->valuestring, "%d", &port); - olp_dev_desc->network.addr.sin_port = htons(port); + continue; } - olp_dev_desc->channels = ZMALLOC(sizeof(struct olp_channel) * NR_OLP6500_CHANNEL_PER_DEVICE_MAX); - MR_VERIFY_MALLOC(olp_dev_desc->channels); - int segment_array_num = cJSON_GetArraySize(segment_array); - for (int j = 0; j < segment_array_num; j++) + for (uint32_t j = 1; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) { - cJSON * segment_array_item = cJSON_GetArrayItem(segment_array, j); - cJSON * cj_segment_id = cJSON_GetObjectItem(segment_array_item, OLP6500_CJSON_KEY_SEGMENT_ID); - cJSON * cj_segment_workline = cJSON_GetObjectItem(segment_array_item, OLP6500_CJSON_KEY_WORKLINE); - cJSON * cj_segment_heartbeat = cJSON_GetObjectItem(segment_array_item, OLP6500_CJSON_KEY_HEARTBEAT); - cJSON * cj_segment_hb_send_interval = cJSON_GetObjectItem(segment_array_item, OLP6500_CJSON_KEY_HEARTBEAT_SEND_INTERVAL_IN_MS); - cJSON * cj_segment_hb_timeout_interval = cJSON_GetObjectItem(segment_array_item, OLP6500_CJSON_KEY_HEARTBEAT_TIMEOUT_INTERVAL_IN_MS); - cJSON * cj_segment_lost_threshold = cJSON_GetObjectItem(segment_array_item, OLP6500_CJSON_KEY_HEARTBEAT_LOST_THRESHOLD); - cJSON * cj_segment_nonrevertive_mode = cJSON_GetObjectItem(segment_array_item, OLP6500_CJSON_KEY_NONREVERTIVE_MODE); - - channel = &olp_dev_desc->channels[cj_segment_id->valueint]; - channel->olp_channel_id = cj_segment_id->valueint; - channel->used = OLP_CHANNEL_STATE_USED; - channel->dev_desc = olp_dev_desc; - channel->state = cj_segment_workline->valueint; - channel->en_heartbeat = cj_segment_heartbeat->valueint; - if (cj_segment_hb_send_interval) - { - channel->heartbeat_send_interval_in_ms = cj_segment_hb_send_interval->valueint; - } - if (cj_segment_hb_timeout_interval) + channel = &src_dev_desc->channels[j]; + if (channel->used != OLP_STATE_USED) { - channel->heartbeat_timeout_interval_in_ms = cj_segment_hb_timeout_interval->valueint; - } - if (cj_segment_lost_threshold) - { - channel->heartbeat_lost_threshold = cj_segment_lost_threshold->valueint; + continue; } - channel->nonrevertive_mode = cj_segment_nonrevertive_mode->valueint; + + dst_dev_desc->channels[channel->olp_channel_id].runtime.last_active_time = channel->runtime.last_active_time; + dst_dev_desc->channels[channel->olp_channel_id].used = OLP_STATE_USED; + dst_dev_desc->used = OLP_STATE_USED; + + olp6500_apply_control_command_to_peer(dst_dev_desc, channel->olp_channel_id); + olp6500_device_dump_one(dst_dev_desc, channel->olp_channel_id); } - olp_mgr_main->olp_dev_descs[olp_mgr_main->nr_olp_dev_descs++] = olp_dev_desc; } return RT_SUCCESS; } -int olp6500_apply_new_config(struct olp_manager_main *olp_mgr_old, struct olp_manager_main *olp_mgr_new) +int olp6500_get_optical_power( char * buff, struct olp_channel * channel) { - int ret = 0; - struct olp_channel *channel_old = NULL; - struct olp_channel *channel_new = NULL; - struct olp_dev_desc *olp_dev_old = NULL; - struct olp_dev_desc *olp_dev_new = NULL; + struct olp6500_packet * pkt = (struct olp6500_packet *)buff; + if (pkt->object != htons(OLP6500_CHANNEL_INFO_OBJECT) || pkt->len != 17) + { + return RT_ERR; + } + + int16_t r1_optical_power = ntohs(pkt->channel_info.r1_optical_power); + int16_t r2_optical_power = ntohs(pkt->channel_info.r2_optical_power); + int16_t r3_optical_power = ntohs(pkt->channel_info.r3_optical_power); + int16_t r4_optical_power = ntohs(pkt->channel_info.r4_optical_power); + channel->runtime.r1_optical_power = ((float)r1_optical_power)/100; + channel->runtime.r2_optical_power = ((float)r2_optical_power)/100; + channel->runtime.r3_optical_power = ((float)r3_optical_power)/100; + channel->runtime.r4_optical_power = ((float)r4_optical_power)/100; - for (uint32_t i = 0; i < olp_mgr_new->nr_olp_dev_descs; i++) + channel->runtime.workline = pkt->channel_info.work_line; + return RT_SUCCESS; +} + +int olp6500_check_channel_config(struct olp_channel * channel, char * buff, char *str_err_reason, int sz_err_reason) +{ + struct olp6500_packet * pkt = (struct olp6500_packet *)buff; + struct olp_dev_desc * dev_desc = channel->dev_desc; + + if (pkt->object != htons(OLP6500_CHANNEL_CONF_OBJECT)) { - olp_dev_new = olp_mgr_new->olp_dev_descs[i]; - if (olp_dev_new->type != OLP_DEVICE_TYPE_OLP_6500) + snprintf(str_err_reason, sz_err_reason, "get channel %d config fail.", channel->olp_channel_id); + return RT_ERR; + } + + if (pkt->channel_conf.heart_detect != channel->en_heartbeat) + { + snprintf(str_err_reason, sz_err_reason, "The current device[%s:%u] configuration[heartbeat_mode:%s] is inconsistent with the administrator's settings[heartbeat_mode:%s].", + dev_desc->devsym, + channel->olp_channel_id, + pkt->channel_conf.heart_detect?"enable":"disable", + channel->en_heartbeat?"enable":"disable"); + if (channel->runtime.errcode != OLP_ERR_CODE_HB_MODE_INCONSISTENT) { - continue; + MR_ERROR("The current device[%s:%u] configuration[heartbeat_mode:%s] is inconsistent with the administrator's settings[heartbeat_mode:%s].", + dev_desc->devsym, + channel->olp_channel_id, + pkt->channel_conf.heart_detect?"enable":"disable", + channel->en_heartbeat?"enable":"disable"); } + channel->runtime.errcode = OLP_ERR_CODE_HB_MODE_INCONSISTENT; + return RT_ERR; + } - for (uint32_t j = 0; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) + if (channel->en_heartbeat) + { + if (pkt->channel_conf.heart_interval != (channel->heartbeat_timeout_interval_in_ms/20)) { - channel_new = &olp_dev_new->channels[j]; - if (channel_new->used == OLP_CHANNEL_STATE_UNUSED) + snprintf(str_err_reason, sz_err_reason, "The current device[%s:%u] configuration[heartbeat_timeout_interval_in_ms:%u] is inconsistent with the administrator's settings[heartbeat_timeout_interval_in_ms:%d].", + dev_desc->devsym, + channel->olp_channel_id, + pkt->channel_conf.heart_interval*20, + channel->heartbeat_timeout_interval_in_ms); + if (channel->runtime.errcode != OLP_ERR_CODE_HB_INTERVAL_INCONSISTENT) { - continue; + MR_ERROR("The current device[%s:%u] configuration[heartbeat_timeout_interval_in_ms:%u] is inconsistent with the administrator's settings[heartbeat_timeout_interval_in_ms:%d].", + dev_desc->devsym, + channel->olp_channel_id, + pkt->channel_conf.heart_interval*20, + channel->heartbeat_timeout_interval_in_ms); } - ret = olp6500_apply_control_command_to_peer(olp_dev_new, channel_new->olp_channel_id); - if (ret != RT_SUCCESS) + channel->runtime.errcode = OLP_ERR_CODE_HB_INTERVAL_INCONSISTENT; + return RT_ERR; + } + + if (pkt->channel_conf.heart_count != channel->heartbeat_lost_threshold) + { + snprintf(str_err_reason, sz_err_reason, "The current device[%s:%u] configuration[heartbeat_lost_threshold:%u] is inconsistent with the administrator's settings[heartbeat_lost_threshold:%u].", + dev_desc->devsym, + channel->olp_channel_id, + pkt->channel_conf.heart_count, + channel->heartbeat_lost_threshold); + if (channel->runtime.errcode != OLP_ERR_CODE_HB_COUNT_INCONSISTENT) + { + MR_ERROR("The current device[%s:%u] configuration[heartbeat_lost_threshold:%u] is inconsistent with the administrator's settings[heartbeat_lost_threshold:%u].", + dev_desc->devsym, + channel->olp_channel_id, + pkt->channel_conf.heart_count, + channel->heartbeat_lost_threshold); + } + channel->runtime.errcode = OLP_ERR_CODE_HB_COUNT_INCONSISTENT; + return RT_ERR; + } + } + else + { + uint8_t channel_work_line = channel->state == OLP_CHANNEL_STATE_FORCE_INLINE ? 0x03 : 0x0c; + if (pkt->channel_conf.work_line != channel_work_line) + { + snprintf(str_err_reason, sz_err_reason, "The current device[%s:%u] configuration[workline:%s] is inconsistent with the administrator's settings[workline:%s].", + dev_desc->devsym, + channel->olp_channel_id, + pkt->channel_conf.work_line==0x03?"inline":"bypass", + channel_work_line==0x03?"inline":"bypass"); + if (channel->runtime.errcode != OLP_ERR_CODE_WORK_LINE_INCONSISTENT) { - goto errout; + MR_ERROR("The current device[%s:%u] configuration[workline:%s] is inconsistent with the administrator's settings[workline:%s].", + dev_desc->devsym, + channel->olp_channel_id, + pkt->channel_conf.work_line==0x03?"inline":"bypass", + channel_work_line==0x03?"inline":"bypass"); } + channel->runtime.errcode = OLP_ERR_CODE_WORK_LINE_INCONSISTENT; + return RT_ERR; + } + } + + if ((!pkt->channel_conf.switch_back_mode) != channel->nonrevertive_mode) + { + snprintf(str_err_reason, sz_err_reason, "The current device[%s:%u] configuration[nonrevertive_mode:%s] is inconsistent with the administrator's settings[nonrevertive_mode:%s].", + dev_desc->devsym, + channel->olp_channel_id, + (!pkt->channel_conf.switch_back_mode)?"yes":"no", + channel->nonrevertive_mode?"yes":"no"); + if (channel->runtime.errcode != OLP_ERR_CODE_SW_BACK_INCONSISTENT) + { + MR_ERROR("The current device[%s:%u] configuration[nonrevertive_mode:%s] is inconsistent with the administrator's settings[nonrevertive_mode:%s].", + dev_desc->devsym, + channel->olp_channel_id, + (!pkt->channel_conf.switch_back_mode)?"yes":"no", + channel->nonrevertive_mode?"yes":"no"); } + channel->runtime.errcode = OLP_ERR_CODE_SW_BACK_INCONSISTENT; + return RT_ERR; + } + channel->runtime.errcode = OLP_SUCCESS; + return RT_SUCCESS; +} + +cJSON * olp6500_monit_loop(struct sc_main * sc_main) +{ + int ret = 0; + int pkt_len = 0; + char str_time[80] = {0}; + char buff[BUFF_MAX] = {0}; + char str_ip_addr[INET_ADDRSTRLEN] = {0}; + char str_err_reason[MR_STRING_MAX] = {0}; + char str_optical_power[16] = {0}; + struct olp_dev_desc * dev_desc = NULL; + struct olp_channel * channel = NULL; + struct olp_device * olp_dev = sc_main->olp_mgr_main->olp6500_main; + cJSON * j_obp_device = NULL; + cJSON * j_channel = NULL; + struct cJSON * j_obp_device_array = cJSON_CreateArray(); + struct cJSON * j_channel_array = NULL; + + if (__atomic_load_n(&g_olp6500_config_ready, __ATOMIC_RELAXED) == OLP6500_LOAD_CONFIG_NOT_READY) + { + goto end; } - for (uint32_t i = 0; i < olp_mgr_old->nr_olp_dev_descs; i++) + for (int index = 0; index < olp_dev->nr_olp_dev_descs; index++) { - olp_dev_old = olp_mgr_old->olp_dev_descs[i]; - if (olp_dev_old->type != OLP_DEVICE_TYPE_OLP_6500) + dev_desc = olp_dev->olp_dev_descs[index]; + __atomic_fetch_add(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); + + if (dev_desc->type != OLP_DEVICE_TYPE_OLP_6500 || dev_desc->used != OLP_STATE_USED) { continue; } - for (uint32_t j = 0; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) + j_obp_device = cJSON_CreateObject(); + cJSON_AddStringToObject(j_obp_device, "symbol", dev_desc->devsym); + + j_channel_array = cJSON_CreateArray(); + for (uint32_t j = 1; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) { - channel_old = &olp_dev_old->channels[j]; - if (channel_old->used == OLP_CHANNEL_STATE_UNUSED) + channel = &dev_desc->channels[j]; + if (channel->used == OLP_STATE_UNUSED) { continue; } - __atomic_exchange_n(&channel_old->timer.enable, OLP_TIMER_DISABLE, __ATOMIC_SEQ_CST); + + j_channel = cJSON_CreateObject(); + + if (channel->runtime.errcode == OLP_ERR_CODE_CONN_FAIL) + { + cJSON_AddNumberToObject(j_channel, "channel_id", channel->olp_channel_id); + inet_ntop(AF_INET, &(dev_desc->network.addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); + snprintf(str_err_reason, sizeof(str_err_reason), "The deployment of the OBP configuration has encountered a failure. Reason: Connect %s:%u failed or configuration settings failed. ", str_ip_addr, ntohs(dev_desc->network.addr.sin_port)); + cJSON_AddStringToObject(j_channel, "error_reason", str_err_reason); + cJSON_AddItemToArray(j_channel_array, j_channel); + continue; + } + + pkt_len = olp6500_construct_packet(channel, OLP_GET_CHANNEL_INFO, buff); + ret = olp6500_send_command_sync(dev_desc, OLP_GET_CHANNEL_INFO, buff, pkt_len, buff, BUFF_MAX); + if (ret != RT_SUCCESS) + { + cJSON_AddNumberToObject(j_channel, "channel_id", channel->olp_channel_id); + cJSON_AddStringToObject(j_channel, "workline", "--"); + cJSON_AddStringToObject(j_channel, "R1", "--"); + cJSON_AddStringToObject(j_channel, "R2", "--"); + cJSON_AddStringToObject(j_channel, "R3", "--"); + cJSON_AddStringToObject(j_channel, "R4", "--"); + snprintf(str_time, sizeof(str_time), "%ld", channel->runtime.last_active_time.tv_sec); + cJSON_AddStringToObject(j_channel, "last_active_time", str_time); + inet_ntop(AF_INET, &(dev_desc->network.addr.sin_addr), str_ip_addr, INET_ADDRSTRLEN); + snprintf(str_err_reason, sizeof(str_err_reason), "Get channel info error: connect %s:%u failed.", str_ip_addr, ntohs(dev_desc->network.addr.sin_port)); + cJSON_AddStringToObject(j_channel, "error_reason", str_err_reason); + cJSON_AddItemToArray(j_channel_array, j_channel); + if (channel->runtime.errcode != OLP_ERR_CODE_GET_CHANNEL_INFO_FAIL) + { + MR_ERROR("Get channel info error: connect %s:%u failed.", str_ip_addr, ntohs(dev_desc->network.addr.sin_port)); + } + channel->runtime.errcode = OLP_ERR_CODE_GET_CHANNEL_INFO_FAIL; + continue; + } + + olp6500_get_optical_power(buff, channel); + + cJSON_AddNumberToObject(j_channel, "channel_id", channel->olp_channel_id); + switch (channel->runtime.workline) + { + case 0x03: + cJSON_AddStringToObject(j_channel, "workline", "inline"); + break; + case 0x0c: + cJSON_AddStringToObject(j_channel, "workline", "bypass"); + break; + default: + cJSON_AddStringToObject(j_channel, "workline", "error"); + } + + snprintf(str_optical_power, sizeof(str_optical_power), "%.2f", channel->runtime.r1_optical_power); + cJSON_AddStringToObject(j_channel, "r1", str_optical_power); + snprintf(str_optical_power, sizeof(str_optical_power), "%.2f", channel->runtime.r2_optical_power); + cJSON_AddStringToObject(j_channel, "r2", str_optical_power); + snprintf(str_optical_power, sizeof(str_optical_power), "%.2f", channel->runtime.r3_optical_power); + cJSON_AddStringToObject(j_channel, "r3", str_optical_power); + snprintf(str_optical_power, sizeof(str_optical_power), "%.2f", channel->runtime.r4_optical_power); + cJSON_AddStringToObject(j_channel, "r4", str_optical_power); + snprintf(str_time, sizeof(str_time), "%ld", channel->runtime.last_active_time.tv_sec); + cJSON_AddStringToObject(j_channel, "last_active_time", str_time); + + pkt_len = olp6500_construct_packet(channel, OLP_GET_CHANNEL_CONF, buff); + ret = olp6500_send_command_sync(dev_desc, OLP_GET_CHANNEL_CONF, buff, pkt_len, buff, BUFF_MAX); + if (ret == RT_SUCCESS) + { + ret = olp6500_check_channel_config(channel, buff, str_err_reason, sizeof(str_err_reason)); + if (ret != RT_SUCCESS) + { + cJSON_AddStringToObject(j_channel, "error_reason", str_err_reason); + } + } + cJSON_AddItemToArray(j_channel_array, j_channel); } + + cJSON_AddItemToObject(j_obp_device, "channel", j_channel_array); + cJSON_AddItemToArray(j_obp_device_array, j_obp_device); } - return RT_SUCCESS; -errout: - for (uint32_t i = 0; i < olp_mgr_new->nr_olp_dev_descs; i++) + for (int index = 0; index < olp_dev->nr_olp_dev_descs; index++) + { + dev_desc = olp_dev->olp_dev_descs[index]; + __atomic_fetch_sub(&dev_desc->refcnt, 1, __ATOMIC_RELAXED); + } +end: + return j_obp_device_array; +} + +int olp6500_destroy_timer(struct olp_device * olp_dev) +{ + struct olp_channel * channel = NULL; + struct olp_dev_desc * dev_desc = NULL; + + for (uint32_t i = 0; i < olp_dev->nr_olp_dev_descs; i++) { - olp_dev_new = olp_mgr_new->olp_dev_descs[i]; - if (olp_dev_new->type != OLP_DEVICE_TYPE_OLP_6500) + dev_desc = olp_dev->olp_dev_descs[i]; + if (dev_desc->type != OLP_DEVICE_TYPE_OLP_6500 || dev_desc->used != OLP_STATE_USED) { continue; } - for (uint32_t j = 0; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) + for (uint32_t j = 1; j < NR_OLP6500_CHANNEL_PER_DEVICE_MAX; j++) { - channel_new = &olp_dev_new->channels[j]; - if (channel_new->used == OLP_CHANNEL_STATE_UNUSED) + channel = &dev_desc->channels[j]; + if (channel->used == OLP_STATE_UNUSED) { continue; } - __atomic_exchange_n(&channel_new->timer.enable, OLP_TIMER_DISABLE, __ATOMIC_SEQ_CST); + __atomic_exchange_n(&channel->timer.enable, OLP_TIMER_DISABLE, __ATOMIC_SEQ_CST); } } - return ret; + + return RT_SUCCESS; } -int olp6500_manager_deinit(struct olp_manager_main *olp_mgr_main) +int olp6500_device_deinit(struct olp_device * olp_dev) { struct olp_dev_desc * dev_desc = NULL; - for (uint32_t i = 0; i < olp_mgr_main->nr_olp_dev_descs; i++) + for (uint32_t i = 0; i < olp_dev->nr_olp_dev_descs; i++) { - dev_desc = olp_mgr_main->olp_dev_descs[i]; + dev_desc = olp_dev->olp_dev_descs[i]; while(__atomic_load_n(&dev_desc->refcnt, __ATOMIC_RELAXED) > 0) { - usleep(OLP6500_TIMER_ONE_CYCLE_MS); + usleep(OLP6500_TIMER_ONE_CYCLE_US); } } - for (uint32_t i = 0; i < olp_mgr_main->nr_olp_dev_descs; i++) + for (uint32_t i = 0; i < olp_dev->nr_olp_dev_descs; i++) { - dev_desc = olp_mgr_main->olp_dev_descs[i]; + dev_desc = olp_dev->olp_dev_descs[i]; FREE(dev_desc->channels); FREE(dev_desc); } - FREE(olp_mgr_main); + FREE(olp_dev); return RT_SUCCESS; } -int olp6500_full_update_handler(cJSON * req, cJSON ** rsp, void * arg) +int olp6500_config_reload() +{ + __atomic_exchange_n(&g_olp6500_config_reload, 1, __ATOMIC_SEQ_CST); + return RT_SUCCESS; +} + +void * _olp6500_config_reload(void * args) { int ret = 0; - char str_error_reason[MR_STRING_MAX] = {0}; - struct sc_main * sc = (struct sc_main *)arg; - struct olp_manager_main * olp_mgr_old = NULL; - cJSON * response = cJSON_CreateObject(); + struct olp_manager_main * olp_mgr_main = (struct olp_manager_main *)args; + struct olp_device * olp_dev_old = NULL; + struct olp_device * olp_dev_new = NULL; - struct olp_manager_main * olp_mgr_new = ZMALLOC(sizeof(struct olp_manager_main)); - MR_VERIFY_MALLOC(olp_mgr_new); + while(1) + { + usleep(OLP6500_RELOAD_CONFIG_CYCLE_US); - __atomic_exchange_n(&olp6500_config_ready, OLP6500_LOAD_CONFIG_NOT_READY, __ATOMIC_SEQ_CST); + if (__atomic_load_n(&g_olp6500_config_ready, __ATOMIC_RELAXED) == OLP6500_LOAD_CONFIG_NOT_READY) + { + continue; + } - ret = olp6500_cjson_parser(req, olp_mgr_new, str_error_reason, MR_STRING_MAX); - if (ret != RT_SUCCESS) - { - goto end; - } + if (__atomic_load_n(&g_olp6500_config_reload, __ATOMIC_RELAXED) == 0) + { + continue; + } + __atomic_exchange_n(&g_olp6500_config_reload, 0, __ATOMIC_SEQ_CST); - ret = olp6500_apply_new_config(sc->olp_mgr_main, olp_mgr_new); - if (ret != RT_SUCCESS) - { - snprintf(str_error_reason, MR_STRING_MAX, "Set OPB device failed! communication with the OPB Device failed"); - goto end; - } + ret = 0; + olp_dev_old = olp_mgr_main->olp6500_main; + olp_dev_new = ZMALLOC(sizeof(struct olp_device)); + MR_VERIFY_MALLOC(olp_dev_new); - olp_mgr_old = sc->olp_mgr_main; - sc->olp_mgr_main = olp_mgr_new; + __atomic_exchange_n(&g_olp6500_config_ready, OLP6500_LOAD_CONFIG_NOT_READY, __ATOMIC_SEQ_CST); -end: - __atomic_exchange_n(&olp6500_config_ready, OLP6500_LOAD_CONFIG_READY, __ATOMIC_SEQ_CST); - cJSON_AddNumberToObject(response, OLP6500_RPC_RESULT, ret); - if (ret != 0) - { - cJSON_AddStringToObject(response, OLP6500_RPC_ERR_REASON, str_error_reason); - } - *rsp = response; + ret = olp6500_config_load(olp_dev_new, g_cfgfile); + if (ret != RT_SUCCESS) + { + goto errout; + } - if (ret != RT_SUCCESS) - { - olp6500_manager_deinit(olp_mgr_new); + olp6500_copy_device_state(olp_dev_old, olp_dev_new); + + olp6500_destroy_timer(olp_dev_old); + + olp_mgr_main->olp6500_main = olp_dev_new; + g_olp6500_dev = olp_mgr_main->olp6500_main; + + __atomic_exchange_n(&g_olp6500_config_ready, OLP6500_LOAD_CONFIG_READY, __ATOMIC_SEQ_CST); + olp6500_device_deinit(olp_dev_old); + continue; + errout: + g_olp6500_dev = olp_mgr_main->olp6500_main; + __atomic_exchange_n(&g_olp6500_config_ready, OLP6500_LOAD_CONFIG_READY, __ATOMIC_SEQ_CST); + olp6500_device_deinit(olp_dev_new); + continue; } - else + + return NULL; +} + +int olp6500_create_thread_config_reload(struct olp_manager_main * olp_mgr_main) +{ + int ret = 0; + pthread_t tid; + + ret = pthread_create(&tid, NULL, _olp6500_config_reload, olp_mgr_main); + if (ret < 0) { - olp6500_manager_deinit(olp_mgr_old); + MR_ERROR("OLP_6500 create config reload thread failed : %s", strerror(errno)); + return RT_ERR; } - olp6500_dump(sc->olp_mgr_main); - return RT_SUCCESS; } -int olp6500_init(struct sc_main * sc_main) +int olp6500_init(struct olp_manager_main * olp_mgr_main, char * cfgfile) { - struct olp_manager_main *olp_mgr_main = sc_main->olp_mgr_main; - if (olp_mgr_main->nr_olp_dev_descs >= NR_OLP_DEVICE_MAX) { - MR_ERROR("create OLP_6500 device failed: too many devices. "); - goto errout; - } + int ret = 0; + g_cfgfile = cfgfile; + + struct olp_device * olp_dev = ZMALLOC(sizeof(struct olp_device)); + MR_VERIFY_MALLOC(olp_dev); - if (rpc_server_recv_request_register(sc_main->rpc_srv_handler, MR_OLP6500_TOPIC_FULL_UPDATE, - olp6500_full_update_handler, sc_main) != 0) + ret = olp6500_config_load(olp_dev, cfgfile); + if (ret != RT_SUCCESS) { - MR_ERROR("The '%s' Request Register Failed . ", MR_OLP6500_TOPIC_FULL_UPDATE); - return RT_ERR; + MR_ERROR("load OLP_6500 config failed. "); + goto errout; } + olp_mgr_main->olp6500_main = olp_dev; + g_olp6500_dev = olp_dev; + olp6500_retry_apply_control_command(); + olp6500_create_thread_config_reload(olp_mgr_main); return RT_SUCCESS; errout: return RT_ERR; diff --git a/service/test/TestOLP.cc b/service/test/TestOLP.cc index 65a0021..c00c68c 100644 --- a/service/test/TestOLP.cc +++ b/service/test/TestOLP.cc @@ -1,8 +1,9 @@ #include <gtest/gtest.h> +#include <arpa/inet.h> +#include <common.h> #include <olp_dev.h> - enum { OLP_SET_HEARTBEAT_SWITCH = 0, @@ -12,20 +13,37 @@ enum OLP_HEARTBEAT_PACKET = 4, - OLP_TYPES_MAX + OLP_GET_CHANNEL_INFO = 5, + OLP_GET_CHANNEL_CONF = 6, + + OLP_OBJECT_MAX }; +struct olp6500_packet +{ + uint8_t action; + uint8_t slot; + uint16_t object; + uint8_t port; + uint8_t len; + char data[0]; +}__attribute__((packed)); + unsigned int g_logger_to_stdout = 1; unsigned int g_logger_level = LOG_DEBUG; unsigned int g_keep_running = 1; uint8_t g_ctrlzone_id = 0; #define BUFF_MAX 256 +#define NR_OLP6500_CHANNEL_PER_DEVICE_MAX (17) extern "C" { extern int olp6500_construct_packet(struct olp_channel * channel, int type, char *buff); -extern int olp6500_check_recv_data(char *buff, int type); +extern int olp6500_check_recv_data(char * buff, uint16_t object); +extern int olp6500_apply_control_command_to_peer(struct olp_dev_desc * dev_desc, uint32_t channel_id); +extern int olp6500_destroy_timer(struct olp_device * olp_dev); +extern int olp6500_device_deinit(struct olp_device * olp_dev); } void olp_dev_desc_init(struct olp_dev_desc *dev_desc, struct olp_channel *channel) @@ -33,11 +51,11 @@ void olp_dev_desc_init(struct olp_dev_desc *dev_desc, struct olp_channel *channe snprintf(dev_desc->devsym, sizeof(dev_desc->devsym), "olp0"); dev_desc->type = OLP_DEVICE_TYPE_OLP_6500; - channel->olp_channel_id = 0; - channel->state = OLP_CHANNEL_STATE_FORCE_ACTIVE; + channel->olp_channel_id = 1; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; channel->en_heartbeat = 1; - channel->heartbeat_timeout_interval_in_ms = 5; - channel->heartbeat_send_interval_in_ms = 30; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; channel->heartbeat_lost_threshold = 3; channel->nonrevertive_mode = 1; channel->dev_desc = dev_desc; @@ -60,43 +78,17 @@ TEST(OLP_PACKET, OLP_SET_HEARTBEAT_SWITCH) pkt_len = olp6500_construct_packet(&dev_desc.channels[0], OLP_SET_HEARTBEAT_SWITCH, buff); EXPECT_TRUE(pkt_len == 10); EXPECT_TRUE(buff[0] == 0x01); - EXPECT_TRUE(buff[1] == 0x00); + EXPECT_TRUE(buff[1] == 0x01); EXPECT_TRUE(buff[2] == 0x06); EXPECT_TRUE(buff[3] == 0x00); EXPECT_TRUE(buff[4] == 0x00); EXPECT_TRUE(buff[5] == 0x04); EXPECT_TRUE(buff[6] == 0x01); EXPECT_TRUE(buff[7] == 0x01); - EXPECT_TRUE(buff[8] == 0x05); + EXPECT_TRUE(buff[8] == 0x03); EXPECT_TRUE(buff[9] == 0x03); } -TEST(OLP_PACKET, OLP_HEARTBEAT_PACKET) -{ - int pkt_len = 0; - char buff[256] = {0}; - struct olp_dev_desc dev_desc; - struct olp_channel dev_channel; - - memset(&dev_desc, 0, sizeof(dev_desc)); - memset(&dev_channel, 0, sizeof(dev_channel)); - - olp_dev_desc_init(&dev_desc, &dev_channel); - - pkt_len = olp6500_construct_packet(&dev_desc.channels[0], OLP_HEARTBEAT_PACKET, buff); - EXPECT_TRUE(pkt_len == 10); - EXPECT_TRUE(buff[0] == 0x00); - EXPECT_TRUE(buff[1] == 0x00); - EXPECT_TRUE(buff[2] == 0x06); - EXPECT_TRUE(buff[3] == 0x01); - EXPECT_TRUE(buff[4] == 0x00); - EXPECT_TRUE(buff[5] == 0x04); - EXPECT_TRUE(buff[6] == 0x00); - EXPECT_TRUE(buff[7] == 0x00); - EXPECT_TRUE(buff[8] == 0x00); - EXPECT_TRUE(buff[9] == 0x00); -} - TEST(OLP_PACKET, OLP_SET_WORK_MODE) { int pkt_len = 0; @@ -112,7 +104,7 @@ TEST(OLP_PACKET, OLP_SET_WORK_MODE) pkt_len = olp6500_construct_packet(&dev_desc.channels[0], OLP_SET_WORK_MODE, buff); EXPECT_TRUE(pkt_len == 7); EXPECT_TRUE(buff[0] == 0x01); - EXPECT_TRUE(buff[1] == 0x00); + EXPECT_TRUE(buff[1] == 0x01); EXPECT_TRUE(buff[2] == 0x10); EXPECT_TRUE(buff[3] == 0x10); EXPECT_TRUE(buff[4] == 0x00); @@ -151,7 +143,7 @@ TEST(OLP_PACKET, OLP_SET_SWITCHBACK_MODE) pkt_len = olp6500_construct_packet(&dev_desc.channels[0], OLP_SET_SWITCHBACK_MODE, buff); EXPECT_TRUE(pkt_len == 7); EXPECT_TRUE(buff[0] == 0x01); - EXPECT_TRUE(buff[1] == 0x00); + EXPECT_TRUE(buff[1] == 0x01); EXPECT_TRUE(buff[2] == 0x10); EXPECT_TRUE(buff[3] == 0x20); EXPECT_TRUE(buff[4] == 0x00); @@ -159,6 +151,72 @@ TEST(OLP_PACKET, OLP_SET_SWITCHBACK_MODE) EXPECT_TRUE(buff[6] == 0x02); } +TEST(OLP_PACKET, OLP_HEARTBEAT_PACKET) +{ + int pkt_len = 0; + char buff[256] = {0}; + struct olp_dev_desc dev_desc; + struct olp_channel dev_channel; + + memset(&dev_desc, 0, sizeof(dev_desc)); + memset(&dev_channel, 0, sizeof(dev_channel)); + + olp_dev_desc_init(&dev_desc, &dev_channel); + + pkt_len = olp6500_construct_packet(&dev_desc.channels[0], OLP_HEARTBEAT_PACKET, buff); + EXPECT_TRUE(pkt_len == 6); + EXPECT_TRUE(buff[0] == 0x00); + EXPECT_TRUE(buff[1] == 0x01); + EXPECT_TRUE(buff[2] == 0x06); + EXPECT_TRUE(buff[3] == 0x01); + EXPECT_TRUE(buff[4] == 0x00); + EXPECT_TRUE(buff[5] == 0x00); +} + +TEST(OLP_PACKET, OLP_GET_CHANNEL_INFO) +{ + int pkt_len = 0; + char buff[256] = {0}; + struct olp_dev_desc dev_desc; + struct olp_channel dev_channel; + + memset(&dev_desc, 0, sizeof(dev_desc)); + memset(&dev_channel, 0, sizeof(dev_channel)); + + olp_dev_desc_init(&dev_desc, &dev_channel); + + pkt_len = olp6500_construct_packet(&dev_desc.channels[0], OLP_GET_CHANNEL_INFO, buff); + EXPECT_TRUE(pkt_len == 6); + EXPECT_TRUE(buff[0] == 0x00); + EXPECT_TRUE(buff[1] == 0x01); + EXPECT_TRUE(buff[2] == 0x02); + EXPECT_TRUE(buff[3] == 0x00); + EXPECT_TRUE(buff[4] == 0x00); + EXPECT_TRUE(buff[5] == 0x00); +} + +TEST(OLP_PACKET, OLP_GET_CHANNEL_CONF) +{ + int pkt_len = 0; + char buff[256] = {0}; + struct olp_dev_desc dev_desc; + struct olp_channel dev_channel; + + memset(&dev_desc, 0, sizeof(dev_desc)); + memset(&dev_channel, 0, sizeof(dev_channel)); + + olp_dev_desc_init(&dev_desc, &dev_channel); + + pkt_len = olp6500_construct_packet(&dev_desc.channels[0], OLP_GET_CHANNEL_CONF, buff); + EXPECT_TRUE(pkt_len == 6); + EXPECT_TRUE(buff[0] == 0x00); + EXPECT_TRUE(buff[1] == 0x01); + EXPECT_TRUE(buff[2] == 0x05); + EXPECT_TRUE(buff[3] == 0x01); + EXPECT_TRUE(buff[4] == 0x00); + EXPECT_TRUE(buff[5] == 0x00); +} + TEST(OLP_RECV_PACKET, OLP_SET_HEARTBEAT_SWITCH) { int ret = 0; @@ -175,22 +233,6 @@ TEST(OLP_RECV_PACKET, OLP_SET_HEARTBEAT_SWITCH) EXPECT_TRUE(ret == -1); } -TEST(OLP_RECV_PACKET, OLP_HEARTBEAT_PACKET) -{ - int ret = 0; - unsigned char data_succ[] = { - 0x00, 0x00, 0x06, 0x01, 0x00, 0x04, 0x30, 0x00, 0x00, 0x00 - }; - unsigned char data_fail[] = { - 0x00, 0x00, 0x86, 0x01, 0x00, 0x02, 0xFF, 0xEE - }; - - ret = olp6500_check_recv_data((char *)data_succ, OLP_HEARTBEAT_PACKET); - EXPECT_TRUE(ret == 0); - ret = olp6500_check_recv_data((char *)data_fail, OLP_HEARTBEAT_PACKET); - EXPECT_TRUE(ret == -1); -} - TEST(OLP_RECV_PACKET, OLP_SET_WORK_MODE) { int ret = 0; @@ -239,8 +281,798 @@ TEST(OLP_RECV_PACKET, OLP_SET_SWITCHBACK_MODE) EXPECT_TRUE(ret == -1); } +TEST(OLP_RECV_PACKET, OLP_HEARTBEAT_PACKET) +{ + int ret = 0; + unsigned char data_succ[] = { + 0x00, 0x00, 0x06, 0x01, 0x00, 0x00 + }; + unsigned char data_fail[] = { + 0x00, 0x00, 0x86, 0x01, 0x00, 0x02, 0xFF, 0xEE + }; + + ret = olp6500_check_recv_data((char *)data_succ, OLP_HEARTBEAT_PACKET); + EXPECT_TRUE(ret == 0); + ret = olp6500_check_recv_data((char *)data_fail, OLP_HEARTBEAT_PACKET); + EXPECT_TRUE(ret == -1); +} + +TEST(OLP_RECV_PACKET, OLP_GET_CHANNEL_INFO) +{ + int ret = 0; + unsigned char data_succ[] = { + 0x00, 0x00, 0x02, 0x00, 0x00, 0x00 + }; + unsigned char data_fail[] = { + 0x00, 0x00, 0x82, 0x00, 0x00, 0x02, 0xFF, 0xEE + }; + + ret = olp6500_check_recv_data((char *)data_succ, OLP_GET_CHANNEL_INFO); + EXPECT_TRUE(ret == 0); + ret = olp6500_check_recv_data((char *)data_fail, OLP_GET_CHANNEL_INFO); + EXPECT_TRUE(ret == -1); +} + +TEST(OLP_RECV_PACKET, OLP_GET_CHANNEL_CONF) +{ + int ret = 0; + unsigned char data_succ[] = { + 0x00, 0x00, 0x05, 0x01, 0x00, 0x00 + }; + unsigned char data_fail[] = { + 0x00, 0x00, 0x85, 0x01, 0x00, 0x02, 0xFF, 0xEE + }; + + ret = olp6500_check_recv_data((char *)data_succ, OLP_GET_CHANNEL_CONF); + EXPECT_TRUE(ret == 0); + ret = olp6500_check_recv_data((char *)data_fail, OLP_GET_CHANNEL_CONF); + EXPECT_TRUE(ret == -1); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_1) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 1; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_2) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 2; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_3) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 3; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 0; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_4) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 4; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 0; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_5) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 5; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_BYPASS; + channel->en_heartbeat = 0; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_6) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 6; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_7) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 7; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_8) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 8; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_9) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 9; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_10) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 10; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_11) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 11; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_12) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 12; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_13) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 13; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_14) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 14; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_15) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 15; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +TEST(OLP_CONTROL_COMMAND, CHANNEL_16) +{ + int ret = 0; + struct olp_device olp_dev; + struct olp_dev_desc olp_dev_desc; + struct olp_channel olp_channel[NR_OLP6500_CHANNEL_PER_DEVICE_MAX]; + struct olp_channel *channel = NULL; + + memset(&olp_dev, 0, sizeof(olp_dev)); + memset(&olp_dev_desc, 0, sizeof(olp_dev_desc)); + memset(olp_channel, 0, sizeof(olp_channel)); + channel = &(olp_channel[1]); + + channel->olp_channel_id = 16; + channel->used = OLP_STATE_USED; + channel->state = OLP_CHANNEL_STATE_FORCE_INLINE; + channel->en_heartbeat = 1; + channel->heartbeat_timeout_interval_in_ms = 60; + channel->heartbeat_send_interval_in_ms = 60; + channel->heartbeat_lost_threshold = 3; + channel->nonrevertive_mode = 1; + channel->dev_desc = &olp_dev_desc; + + olp_dev_desc.used = OLP_STATE_USED; + olp_dev_desc.conn_type = OLP_CONNECT_TYPE_NETWORK; + olp_dev_desc.network.addr.sin_family = AF_INET; + inet_pton(AF_INET, "127.0.0.1", &olp_dev_desc.network.addr.sin_addr); + olp_dev_desc.network.addr.sin_port = htons(6800); + snprintf(olp_dev_desc.devsym, sizeof(olp_dev_desc.devsym), "olp0"); + olp_dev_desc.type = OLP_DEVICE_TYPE_OLP_6500; + olp_dev_desc.channels = olp_channel; + olp_dev.olp_dev_descs[olp_dev.nr_olp_dev_descs++] = &olp_dev_desc; + + ret = olp6500_apply_control_command_to_peer(&olp_dev_desc, 1); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 1); + EXPECT_TRUE(channel->runtime.errcode == 0); + + ret = olp6500_destroy_timer(&olp_dev); + EXPECT_TRUE(ret == 0); + EXPECT_TRUE(channel->timer.enable == 0); +} + +void * olp_device_server(void * args) +{ + int ret = 0; + int sock = 0; + char send_buff[64] = {0}; + char recv_buff[64] = {0}; + struct sockaddr_in addr; + struct sockaddr cli_addr; + socklen_t cli_len = sizeof(cli_addr); + struct olp6500_packet *pkt = NULL; + + pthread_detach(pthread_self()); + + sock = socket(AF_INET, SOCK_DGRAM, 0); + if (sock < 0) + return 0; + + memset(&addr, 0, sizeof(addr)); + addr.sin_family = AF_INET; + addr.sin_port = htons(6800); + addr.sin_addr.s_addr = htonl(INADDR_ANY); + bind(sock, (struct sockaddr*)&addr, sizeof(addr)); + while(1) + { + memset(recv_buff, 0, sizeof(recv_buff)); + memset(send_buff, 0, sizeof(send_buff)); + memset(&cli_addr, 0, sizeof(cli_addr)); + ret = recvfrom(sock, recv_buff, sizeof(recv_buff), 0, &cli_addr, &cli_len); + if (ret == -1) + { + printf("recvfrom fail! error:%s\n", strerror(errno)); + continue; + } + + pkt = (struct olp6500_packet*)recv_buff; + ret = sendto(sock, recv_buff, pkt->len+6, 0, &cli_addr, cli_len); + if (ret == -1) + { + printf("sendto fail! error:%s\n", strerror(errno)); + continue; + } + } + return NULL; +} + int main(int argc, char * argv[]) { + int ret = 0; + pthread_t tid; ::testing::InitGoogleTest(&argc, argv); + + ret = pthread_create(&tid, NULL, olp_device_server, NULL); + if (ret < 0) + { + MR_ERROR("olp devices server start error: %s", strerror(errno)); + return -1; + } return RUN_ALL_TESTS(); } diff --git a/tools/CMakeLists.txt b/tools/CMakeLists.txt index 9754a4f..7140a0c 100644 --- a/tools/CMakeLists.txt +++ b/tools/CMakeLists.txt @@ -1,6 +1,7 @@ add_subdirectory(tcpdump) add_subdirectory(monit_device) add_subdirectory(monit_stream) +add_subdirectory(monit_obp) add_subdirectory(pagstat) add_subdirectory(dlogreader) add_subdirectory(devbind) diff --git a/tools/monit_obp/CMakeLists.txt b/tools/monit_obp/CMakeLists.txt new file mode 100644 index 0000000..f420dbb --- /dev/null +++ b/tools/monit_obp/CMakeLists.txt @@ -0,0 +1,2 @@ +configure_file(monit_obp.py monit_obp) +install(PROGRAMS ${CMAKE_CURRENT_BINARY_DIR}/monit_obp DESTINATION ${MR_INSTALL_BINDIR_RELATIVE_PATH} COMPONENT Program) diff --git a/tools/monit_obp/monit_obp.py b/tools/monit_obp/monit_obp.py new file mode 100644 index 0000000..be77da9 --- /dev/null +++ b/tools/monit_obp/monit_obp.py @@ -0,0 +1,252 @@ +#!/usr/bin/env python2 + +import prettytable +import argparse +import json +import time +import sys +import signal +import os +import socket + +from functools import partial +from BaseHTTPServer import HTTPServer, BaseHTTPRequestHandler + +TBPS = (1 * 1000 * 1000 * 1000 * 1000) +GBPS = (1 * 1000 * 1000 * 1000) +MBPS = (1 * 1000 * 1000) +KBPS = (1 * 1000) + +G_JSON_PATH = '/var/run/mrzcpd/mrmonit.daemon' + +TITLE_VECTOR = [ + 'WorkLine', + 'R1', + 'R2', + 'R3', + 'R4', + 'last_active_time' +] + +TITLE_ERROR_VECTOR = [ + 'Reason' +] + +TITLE_ERROR_MAP = { + 'Reason': 'error_reason' +} + +OBP_DEVICE_TYPE_VECTOR = ['SINO-OLP-6500'] + +TITLE_MAP = { + 'WorkLine': 'workline', + 'R1': 'r1', + 'R2': 'r2', + 'R3': 'r3', + 'R4': 'r4', + 'last_active_time': 'last_active_time' +} + +TITLE_MAP_PROMETHEUS = { + 'WorkLine': 'obp_workline', + 'R1': 'obp_r1_optical_power', + 'R2': 'obp_r2_optical_power', + 'R3': 'obp_r3_optical_power', + 'R4': 'obp_r4_optical_power', + 'last_active_time': 'obp_last_active_time' +} + +def locate_vector_by_key(vector, key, symbol): + return [s for s in vector if s[key] == symbol] + +def list_all_obp_dev(json_fp): + return [s['symbol'] for s in json_fp['OBP']['SINO-OLP-6500']] + +def list_all_channel(json_fp, devsym): + obp_devs = locate_vector_by_key(json_fp['OBP']['SINO-OLP-6500'], "symbol", devsym) + return [s['channel_id'] for s in obp_devs[0]['channel']] + +def obp_dev_get_channel(json_fp, str_device, channel_id): + obp_devs = locate_vector_by_key(json_fp['OBP']['SINO-OLP-6500'], "symbol", str_device) + return locate_vector_by_key(obp_devs[0]['channel'], 'channel_id', channel_id) + +def timestamp_to_locale_time(timestamp): + local_time = time.localtime(float(timestamp)) + return time.strftime('%c', local_time) + +def dump_human_table(json_fp, devsym, channel_list): + title_flag = 0 + table_obp_dev = prettytable.PrettyTable([' '] + TITLE_VECTOR, + vertical_char=' ', horizontal_char='-', junction_char=' ') + + table_obp_dev.align[' '] = 'r' + + for item in TITLE_VECTOR: + table_obp_dev.align[item] = 'r' + + for channel_id in channel_list: + build_table_flag = 1 + channel = obp_dev_get_channel(json_fp, devsym, channel_id) + channel_table_list = [] + channel_table_list.append('channel_id:%d' % channel_id) + + for item in TITLE_VECTOR: + try: + if item == 'last_active_time': + if channel[0][TITLE_MAP[item]] == "0": + channel_table_list.append("--") + else: + channel_table_list.append(timestamp_to_locale_time(channel[0][TITLE_MAP[item]])) + else: + channel_table_list.append(channel[0][TITLE_MAP[item]]) + except Exception as e: + build_table_flag = 0 + break + + if build_table_flag == 0: + continue + + table_obp_dev.add_row(channel_table_list) + if title_flag == 0: + print('\nTime: %s, OBP device: %s' % (time.strftime('%c'), devsym)) + title_flag = 1 + if title_flag > 0: + print(table_obp_dev) + +def dump_error_reason(json_fp, devsym, channel_list): + title_flag = 0 + + for channel_id in channel_list: + channel = obp_dev_get_channel(json_fp, devsym, channel_id) + if 'error_reason' not in channel[0]: + continue + + if title_flag == 0: + print('\nTime: %s, OBP device: %s Output error message.' % (time.strftime('%c'), devsym)) + title_flag = 1 + print('channel_id:%d Reason:%s' % (channel_id, str(channel[0]['error_reason']))) + +# APM sendlog format + +def dump_prometheus_output(json_fp, devsym, channel_id): + resp = '' + channel = obp_dev_get_channel(json_fp, devsym, channel_id) + for item in TITLE_VECTOR: + try: + if item == 'WorkLine': + if channel[0][TITLE_MAP[item]] == 'bypass': + resp += '%s{dev=\"%s\", channel=\"%u\"} %u\n' % (TITLE_MAP_PROMETHEUS[item], devsym, channel_id, 0) + elif channel[0][TITLE_MAP[item]] == 'inline': + resp += '%s{dev=\"%s\", channel=\"%u\"} %u\n' % (TITLE_MAP_PROMETHEUS[item], devsym, channel_id, 1) + elif item == 'R1' or item == 'R2' or item == 'R3' or item == 'R4' : + resp += '%s{dev=\"%s\", channel=\"%u\"} %0.2f\n' % (TITLE_MAP_PROMETHEUS[item], devsym, channel_id, float(channel[0][TITLE_MAP[item]])) + else: + resp += '%s{dev=\"%s\", channel=\"%u\"} %u\n' % (TITLE_MAP_PROMETHEUS[item], devsym, channel_id, float(channel[0][TITLE_MAP[item]])) + except Exception as e: + resp += '' + return resp + +def setup_argv_parser(obp_dev_list): + parser = argparse.ArgumentParser( + description='Marsio ZeroCopy Tools -- Monitor OBP devices') + + parser.add_argument('-t', '--time', help='interval, seconds to wait between updates', + type=int, default=1) + parser.add_argument('-l', '--loop', help='print loop, exit when recv a signal', + action='store_true', default=0) + parser.add_argument('-i', '--device', help='the name of OBP device name', + action='append', choices=obp_dev_list) + parser.add_argument('--clear-screen', help='clear screen at start of loop', + action='store_true', default=0) + + # APM sendlog options + parser.add_argument('--prometheus-client', help='Run as prometheus client', + action='store_true', default=0) + + parser.add_argument('--prometheus-client-listen-port', help='Default Port of prometheus client', + type=int, default=8903) + + return parser.parse_args() + +def obp_dev_json_load(): + with open(G_JSON_PATH) as json_fp: + return json.load(json_fp) + +def sigint_handler(handler, frame): + sys.exit(0) + + +class PrometheusClient(BaseHTTPRequestHandler): + def __init__(self, request, client_address, server): + self.json_fp = obp_dev_json_load() + self.obp_dev_list = list_all_obp_dev(self.json_fp) + BaseHTTPRequestHandler.__init__(self, request, client_address, server) + + def do_GET(self): + if self.path == '/metrics': + resp = '' + + for devsym in self.obp_dev_list: + channel_list = list_all_channel(self.json_fp, devsym) + for channel_id in channel_list: + resp += dump_prometheus_output(self.json_fp, devsym, channel_id) + self.send_response(200) + self.send_header('Content-type', 'text/plain; version=0.0.4') + self.end_headers() + self.wfile.write(resp) + else: + self.send_error(404) + self.end_headers() + +def prometheus_client_init(json_fp, obp_dev_list, prometheus_client_port): + HTTPServer(("", prometheus_client_port), PrometheusClient).serve_forever() + + +def main(): + signal.signal(signal.SIGINT, sigint_handler) + + try: + json_fp = obp_dev_json_load() + obp_dev_list = list_all_obp_dev(json_fp) + r_option = setup_argv_parser(obp_dev_list) + + if r_option.prometheus_client: + prometheus_client_init(json_fp, obp_dev_list, + r_option.prometheus_client_listen_port) + + sleep_interval = r_option.time + obp_dev_user_list = obp_dev_list if r_option.device is None else r_option.device + if len(obp_dev_user_list) == 0: + print("monit_obp: error: No OBP device exists.") + sys.exit(1) + + while True: + if r_option.clear_screen: + os.system('clear') + + json_fp = obp_dev_json_load() + + for devsym in obp_dev_user_list: + channel_list = list_all_channel(json_fp, devsym) + dump_human_table(json_fp, devsym, channel_list) + + for devsym in obp_dev_user_list: + channel_list = list_all_channel(json_fp, devsym) + dump_error_reason(json_fp, devsym, channel_list) + + if not r_option.loop: + break + + time.sleep(float(sleep_interval)) + + except KeyboardInterrupt: + pass + except ValueError as err: + print(("%s, perhaps mrzcpd program is not running.") % str(err)) + except IOError as err: + print(("%s, perhaps mrzcpd program is not running.") % str(err)) + + return 0 + +if __name__ == '__main__': + main() diff --git a/tools/systemd/CMakeLists.txt b/tools/systemd/CMakeLists.txt index 9ecee55..641dafb 100644 --- a/tools/systemd/CMakeLists.txt +++ b/tools/systemd/CMakeLists.txt @@ -4,6 +4,7 @@ configure_file(mrzcpd.service.in mrzcpd.service) configure_file(mrtunnat.service.in mrtunnat.service) configure_file(mrapm_device.service.in mrapm_device.service) configure_file(mrapm_stream.service.in mrapm_stream.service) +configure_file(mrapm_obp.service.in mrapm_obp.service) install(FILES ${CMAKE_BINARY_DIR}/tools/systemd/mrzcpd_hwdb_setup.service DESTINATION ${MR_INSTALL_SYSTEM} COMPONENT Program) @@ -23,3 +24,6 @@ install(FILES ${CMAKE_BINARY_DIR}/tools/systemd/mrapm_device.service install(FILES ${CMAKE_BINARY_DIR}/tools/systemd/mrapm_stream.service DESTINATION ${MR_INSTALL_SYSTEM} COMPONENT Program) +install(FILES ${CMAKE_BINARY_DIR}/tools/systemd/mrapm_obp.service + DESTINATION ${MR_INSTALL_SYSTEM} COMPONENT Program) + diff --git a/tools/systemd/mrapm_obp.service.in b/tools/systemd/mrapm_obp.service.in new file mode 100644 index 0000000..34bf70c --- /dev/null +++ b/tools/systemd/mrapm_obp.service.in @@ -0,0 +1,14 @@ +[Unit] +Description=Marsio APM logwritter(monit_obp) +After=mrzcpd.service +Requires=mrzcpd.service + +[Service] +Type=simple +ExecStart=@MR_INSTALL_PREFIX@/bin/monit_obp --prometheus-client +RestartSec=10s +Restart=always +PrivateTmp=True + +[Install] +WantedBy=multi-user.target |
