diff --git a/.$架构.drawio.bkp b/.$架构.drawio.bkp new file mode 100644 index 0000000..faa5e5c --- /dev/null +++ b/.$架构.drawio.bkp @@ -0,0 +1,16 @@ + + + + + + + + + + + + + + + + diff --git a/.vscode/launch.json b/.vscode/launch.json new file mode 100644 index 0000000..30290b0 --- /dev/null +++ b/.vscode/launch.json @@ -0,0 +1,25 @@ +{ + "version": "0.2.0", + "configurations": [ + { + "name": "(gdb) Launch", + "type": "cppdbg", + "request": "launch", + "program": "${workspaceFolder}/port_self.exe", //只改这里 + "args": [], + "stopAtEntry": false, + "cwd": "${workspaceFolder}", + "environment": [], + "externalConsole": true, + "MIMode": "gdb", + "setupCommands": [ + { + "description": "Enable pretty-printing for gdb", + "text": "-enable-pretty-printing", + "ignoreFailures": true + } + ], + // "preLaunchTask": "build_111" //可以新增一条 + } + ] +} \ No newline at end of file diff --git a/.vscode/settings.json b/.vscode/settings.json index db529d0..dfd61ea 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -28,5 +28,6 @@ "binaryPath": "d:\\WORK\\erpc\\port_self.exe", "binaryArgs": [] } - ] + ], + "cmake.ignoreCMakeListsMissing": true } \ No newline at end of file diff --git a/.vscode/tasks.json b/.vscode/tasks.json new file mode 100644 index 0000000..e5f231a --- /dev/null +++ b/.vscode/tasks.json @@ -0,0 +1,23 @@ +{ + "tasks": [ + { + "type": "cppbuild", + "label": "build_111", + "command": "make", + "args": [ + ], + "options": { + "cwd": "${fileDirname}" + }, + "problemMatcher": [ + "$gcc" + ], + "group": { + "kind": "build", + "isDefault": true + }, + "detail": "调试器生成的任务。" + } + ], + "version": "2.0.0" +} \ No newline at end of file diff --git a/build/crc16.o b/build/crc16.o new file mode 100644 index 0000000..6e7fb7a Binary files /dev/null and b/build/crc16.o differ diff --git a/build/erpc_core.o b/build/erpc_core.o new file mode 100644 index 0000000..f4f1516 Binary files /dev/null and b/build/erpc_core.o differ diff --git a/build/list.o b/build/list.o new file mode 100644 index 0000000..f195381 Binary files /dev/null and b/build/list.o differ diff --git a/build/port_self.o b/build/port_self.o new file mode 100644 index 0000000..37fbaef Binary files /dev/null and b/build/port_self.o differ diff --git a/config.h b/config.h index b39ffb5..9850bae 100644 --- a/config.h +++ b/config.h @@ -8,4 +8,7 @@ #define u16 unsigned short #define u32 unsigned int +#define UNUSED(x) (void)(x) +#define ERPC_DEBUG(...) printf(__VA_ARGS__) +// #define ERPC_DEBUG(...) #endif /* _CONFIG_H_ */ \ No newline at end of file diff --git a/crc16.c b/crc16.c index 190d082..fd32d26 100644 --- a/crc16.c +++ b/crc16.c @@ -31,13 +31,13 @@ static const uint16_t crc16tab[256] = { 0xdf7c, 0xaf9b, 0xbfba, 0x8fd9, 0x9ff8, 0x6e17, 0x7e36, 0x4e55, 0x5e74, 0x2e93, 0x3eb2, 0x0ed1, 0x1ef0}; -uint16_t crc16(const unsigned char *buf, size_t len) { - int counter; - uint16_t crc = 0; - for (counter = 0; counter < len; counter++) - crc = (crc << 8) ^ crc16tab[((crc >> 8) ^ *buf++) & 0x00FF]; - return crc; -} +// uint16_t crc16(const unsigned char *buf, size_t len) { +// int counter; +// uint16_t crc = 0; +// for (counter = 0; counter < (int)len; counter++) +// crc = (crc << 8) ^ crc16tab[((crc >> 8) ^ *buf++) & 0x00FF]; +// return crc; +// } u16 cmd_cal_crc16(erpc_cmd_def_t *cmd) { u16 crc = 0; diff --git a/crc16.o b/crc16.o deleted file mode 100644 index 6f0997b..0000000 Binary files a/crc16.o and /dev/null differ diff --git a/erpc_core.c b/erpc_core.c index 12e6915..93145f1 100644 --- a/erpc_core.c +++ b/erpc_core.c @@ -9,11 +9,14 @@ erpc_sleep erpc_sleep_tick = NULL; static list_t erpc_hw; -void clean_cache(erpc_hw_cfg_t *hw) { - for (int i = 0; i < MAX_REC_CMD_CACHE_NUM; i++) { +void clean_cache(erpc_hw_cfg_t *hw) +{ + for (int i = 0; i < MAX_REC_CMD_CACHE_NUM; i++) + { hw->rec_cache->state = ERPC_CMD_NO_ERROR; } - for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) { + for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) + { hw->send_cache[i].state = ERPC_CMD_NO_ERROR; } } @@ -21,29 +24,35 @@ void clean_cache(erpc_hw_cfg_t *hw) { * 注册 hardware 设备 * 线程不安全 */ -u32 erpc_hw_add(erpc_hw_cfg_t *hw) { +u32 erpc_hw_add(erpc_hw_cfg_t *hw) +{ list_t *list = &erpc_hw; - if (list->data == NULL) { + if (list->data == NULL) + { list->data = (void *)hw; clean_cache(hw); return ERPC_NO_ERROR; } list_t *list_node = malloc(sizeof(list_t)); - if (list_node == NULL) { + if (list_node == NULL) + { return ERPC_ERR_MALLOC_ERROR; } list_node->data = (void *)hw; u8 hw_ord = hw->ord; // 检查hw是否已经存在 - while (list != NULL) { + while (list != NULL) + { erpc_hw_cfg_t *hw_cfg = (erpc_hw_cfg_t *)list->data; - if (hw_cfg->ord == hw_ord) { + if (hw_cfg->ord == hw_ord) + { return ERPC_ERR_HW_EXIST; } list = list->next; } list_t *result = list_append(&erpc_hw, hw); - if (result == NULL) { + if (result == NULL) + { return ERPC_ERR_MALLOC_ERROR; } clean_cache(hw); @@ -53,14 +62,17 @@ u32 erpc_hw_add(erpc_hw_cfg_t *hw) { * 注册命令列表 * 线程不安全 */ -u32 erpc_add_cmd_list(erpc_hw_cfg_t *hw, erpc_cmd_list_t *cmd_list) { +u32 erpc_add_cmd_list(erpc_hw_cfg_t *hw, erpc_cmd_list_t *cmd_list) +{ list_t *list = &hw->cmd_list; - if (list->data == NULL) { + if (list->data == NULL) + { list->data = (void *)cmd_list; return ERPC_NO_ERROR; } list = list_append(&hw->cmd_list, cmd_list); - if (list == NULL) { + if (list == NULL) + { return ERPC_ERR_MALLOC_ERROR; } return ERPC_NO_ERROR; @@ -69,14 +81,18 @@ u32 erpc_add_cmd_list(erpc_hw_cfg_t *hw, erpc_cmd_list_t *cmd_list) { * 移除 hardware 设备 * 线程不安全 */ -u32 erpc_hw_remove(u8 hw) { +u32 erpc_hw_remove(u8 hw) +{ list_t *list = &erpc_hw; - if (list->data == NULL) { + if (list->data == NULL) + { return ERPC_ERR_NOFOND_HW; } - while (list != NULL) { + while (list != NULL) + { erpc_hw_cfg_t *hw_cfg = (erpc_hw_cfg_t *)list->data; - if (hw_cfg->ord == hw) { + if (hw_cfg->ord == hw) + { list_delete(&erpc_hw, list); free(list); return ERPC_NO_ERROR; @@ -88,27 +104,34 @@ u32 erpc_hw_remove(u8 hw) { /** * 获取 hardware 设备 */ -erpc_hw_cfg_t *erpc_hw_get(u8 hw) { +erpc_hw_cfg_t *erpc_hw_get(u8 hw) +{ list_t *list = &erpc_hw; - if (list->data == NULL) { + if (list->data == NULL) + { return NULL; } - while (list != NULL) { + while (list != NULL) + { erpc_hw_cfg_t *hw_cfg = (erpc_hw_cfg_t *)list->data; - if (hw_cfg->ord == hw) { + if (hw_cfg->ord == hw) + { return hw_cfg; } } return NULL; } u32 erpc_send_base(erpc_hw_cfg_t *hw_cfg, u8 dest_id, u16 port, u8 package_type, - u8 *data, u16 len) { + u8 *data, u16 len) +{ CHECK_IF_ERROR(hw_cfg == NULL, ERPC_ERR_NOFOND_HW); u8 cache_ord = 255; // 查找可用的发送缓存 - for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) { - if (hw_cfg->send_cache[i].state == ERPC_CMD_NO_ERROR) { - printf("find send cache %d\n", i); + for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) + { + if (hw_cfg->send_cache[i].state == ERPC_CMD_NO_ERROR) + { + ERPC_DEBUG("find send cache %d\n", i); cache_ord = i; break; } @@ -122,13 +145,19 @@ u32 erpc_send_base(erpc_hw_cfg_t *hw_cfg, u8 dest_id, u16 port, u8 package_type, cmd->head.dest_id = dest_id; cmd->head.port = port; cmd->head.msg_len = len; - if (data != NULL) { + if (data == NULL) + { cmd->head.msg_len = 0; + len = 0; } cmd->head.type = package_type; cmd->head.src_id = hw_cfg->local_id; - if (len > 0 && data != NULL) { - memcpy(cmd->data, data, len); + if (len > 0 && data != NULL) + { + for (int i = 0; i < len; i++) + { + cmd->data[i] = data[i]; + } } // 计算校验和 cmd_cal_crc16(cmd); @@ -137,29 +166,37 @@ u32 erpc_send_base(erpc_hw_cfg_t *hw_cfg, u8 dest_id, u16 port, u8 package_type, hw_cfg->send_cache[cache_ord].state = ERPC_CMD_WAIT_SEND; // 等待数据发送完成 int wait_time = CMD_TIMEOUT; - while (wait_time > 0) { - if (hw_cfg->send_cache[cache_ord].state == ERPC_CMD_SEND_OK) { + while (wait_time > 0) + { + if (hw_cfg->send_cache[cache_ord].state == ERPC_CMD_SEND_OK) + { break; } - if (hw_cfg->send_cache[cache_ord].state == ERPC_CMD_DEST_BUSY) { + if (hw_cfg->send_cache[cache_ord].state == ERPC_CMD_DEST_BUSY) + { return ERPC_ERR_DEST_BUSY; } - if (erpc_sleep_tick != NULL) { + if (erpc_sleep_tick != NULL) + { erpc_sleep_tick(1); } wait_time--; } u32 ret = ERPC_NO_ERROR; - do { - if (wait_time == 0) { + do + { + if (wait_time == 0) + { ret = ERPC_ERR_SEND_TIMEOUT; break; } - if (hw_cfg->send_cache[cache_ord].state == ERPC_CMD_SEND_ONCE) { + if (hw_cfg->send_cache[cache_ord].state == ERPC_CMD_SEND_ONCE) + { ret = ERPC_ERR_DEST_NO_RESPONSE; break; } - if (hw_cfg->send_cache[cache_ord].state == ERPC_CMD_SEND_REPEAT) { + if (hw_cfg->send_cache[cache_ord].state == ERPC_CMD_SEND_REPEAT) + { ret = ERPC_ERR_DEST_NO_RESPONSE; break; } @@ -167,7 +204,8 @@ u32 erpc_send_base(erpc_hw_cfg_t *hw_cfg, u8 dest_id, u16 port, u8 package_type, hw_cfg->send_cache[cache_ord].state = ERPC_CMD_NO_ERROR; return ret; } -u32 erpc_send(u8 hw, u8 dest_id, u16 port, u8 *data, u16 len) { +u32 erpc_send(u8 hw, u8 dest_id, u16 port, u8 *data, u16 len) +{ erpc_hw_cfg_t *hw_cfg = erpc_hw_get(hw); u32 ret = erpc_send_base(hw_cfg, dest_id, port, PACKAGE_TYPE_CMD_REQ, data, len); @@ -175,30 +213,42 @@ u32 erpc_send(u8 hw, u8 dest_id, u16 port, u8 *data, u16 len) { } u32 erpc_wait_resp_package(u8 hw, u8 dest_id, u16 port, u8 *reply_data, - u16 *reply_len, u32 time_out) { + u16 *reply_len, u32 time_out) +{ erpc_hw_cfg_t *hw_cfg = erpc_hw_get(hw); CHECK_IF_ERROR(hw_cfg == NULL, ERPC_ERR_NOFOND_HW); - while (time_out > 0) { - for (int i = 0; i < MAX_REC_CMD_CACHE_NUM; i++) { + while (time_out > 0) + { + for (int i = 0; i < MAX_REC_CMD_CACHE_NUM; i++) + { erpc_data_cache_t *rec_cahce = &hw_cfg->rec_cache[i]; - if (rec_cahce->state != ERPC_CMD_RESP_OK) { + if (rec_cahce->state != ERPC_CMD_RESP_OK) + { continue; } erpc_cmd_def_t *cmd = (erpc_cmd_def_t *)&rec_cahce->data[0]; - if (cmd->head.port != port) { + if (cmd->head.port != port) + { continue; } - if (cmd->head.src_id != dest_id) { + if (cmd->head.src_id != dest_id) + { continue; } - if (reply_data != NULL) { - memccpy(reply_data, cmd->data, 0, cmd->head.msg_len); - *reply_len = cmd->head.msg_len; + if (reply_data != NULL) + { + // memccpy(reply_data, cmd->data, 0, cmd->head.msg_len); + memcpy(reply_data, cmd->data, cmd->head.msg_len); + if (reply_len != NULL) + { + *reply_len = cmd->head.msg_len; + } } rec_cahce->state = ERPC_CMD_NO_ERROR; return ERPC_NO_ERROR; } - if (erpc_sleep_tick != NULL) { + if (erpc_sleep_tick != NULL) + { erpc_sleep_tick(1); } time_out--; @@ -207,29 +257,34 @@ u32 erpc_wait_resp_package(u8 hw, u8 dest_id, u16 port, u8 *reply_data, return ERPC_NO_ERROR; } u32 erpc_send_wait_reply(u8 hw, u8 dest_id, u16 port, u8 *data, u16 len, - u8 *reply_data, u16 *reply_len, u32 timeout) { + u8 *reply_data, u16 *reply_len, u32 timeout) +{ u32 ret = erpc_send(hw, dest_id, port, data, len); - if (reply_len != NULL) { + if (reply_len != NULL) + { *reply_len = 0; } CHECK_IF_ERROR(ret != ERPC_NO_ERROR, ret); - printf("send ok\n"); ret = erpc_wait_resp_package(hw, dest_id, port, reply_data, reply_len, timeout); CHECK_IF_ERROR(ret != ERPC_NO_ERROR, ret); return ERPC_NO_ERROR; } -u32 erpc_replay(u8 hw, u8 dest_id, u16 port, u8 *data_out, u16 len) { +u32 erpc_replay(u8 hw, u8 dest_id, u16 port, u8 *data_out, u16 len) +{ erpc_hw_cfg_t *hw_cfg = erpc_hw_get(hw); - u32 ret = erpc_send_base(hw_cfg, dest_id, port, PACKAGE_TYPE_CMD_REPEAT, + u32 ret = erpc_send_base(hw_cfg, dest_id, port, PACKAGE_TYPE_CMD_RESP, data_out, len); return ret; } -u32 erpc_send_data(erpc_hw_cfg_t *hw) { - for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) { - if (hw->send_cache[i].state == ERPC_CMD_WAIT_SEND) { +u32 erpc_send_data(erpc_hw_cfg_t *hw) +{ + for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) + { + if (hw->send_cache[i].state == ERPC_CMD_WAIT_SEND) + { erpc_cmd_def_t *cmd = (erpc_cmd_def_t *)&hw->send_cache[i].data[0]; u32 len = sizeof(erpc_cmd_head_t) + 2 + cmd->head.msg_len; hw->send_lock(); @@ -242,12 +297,16 @@ u32 erpc_send_data(erpc_hw_cfg_t *hw) { return ERPC_NO_ERROR; } -u32 erpc_rev_ack_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) { - for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) { +u32 erpc_rev_ack_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) +{ + for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) + { if (hw->send_cache[i].state == ERPC_CMD_SEND_ONCE || - hw->send_cache[i].state == ERPC_CMD_SEND_REPEAT) { + hw->send_cache[i].state == ERPC_CMD_SEND_REPEAT) + { erpc_cmd_def_t *cmd_send = (erpc_cmd_def_t *)&hw->send_cache[i].data[0]; - if (cmd_rev->head.port == cmd_send->head.port) { + if (cmd_rev->head.port == cmd_send->head.port) + { hw->send_cache[i].state = ERPC_CMD_SEND_OK; return ERPC_NO_ERROR; } @@ -255,7 +314,8 @@ u32 erpc_rev_ack_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) { } return ERPC_NO_ERROR; } -u32 erpc_rev_resp_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) { +u32 erpc_rev_resp_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) +{ erpc_cmd_def_t cmd_send; cmd_send.head.dest_id = cmd_rev->head.src_id; cmd_send.head.port = cmd_rev->head.port; @@ -271,25 +331,30 @@ u32 erpc_rev_resp_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) { return ERPC_NO_ERROR; } // 重发数据包 -u32 erpc_rev_repeat_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) { - for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) { +u32 erpc_rev_repeat_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) +{ + for (int i = 0; i < MAX_SEND_CMD_CACHE_NUM; i++) + { if (hw->send_cache[i].state == ERPC_CMD_SEND_ONCE || - hw->send_cache[i].state == ERPC_CMD_SEND_REPEAT) { + hw->send_cache[i].state == ERPC_CMD_SEND_REPEAT) + { erpc_cmd_def_t *cmd_send = (erpc_cmd_def_t *)&hw->send_cache[i].data[0]; - if (cmd_rev->head.port == cmd_send->head.port) { + if (cmd_rev->head.port == cmd_send->head.port) + { u32 len = sizeof(erpc_cmd_head_t) + 2 + cmd_send->head.msg_len; hw->send_lock(); u32 ret = hw->write((u8 *)hw->send_cache[i].data, len); hw->send_unlock(); hw->send_cache[i].state = ERPC_CMD_SEND_REPEAT; - CHECK_IF_ERROR(ret, ERPC_ERR_HW_SEND_FAIL); // + CHECK_IF_ERROR(ret, ERPC_ERR_HW_SEND_FAIL); // return ERPC_NO_ERROR; } } } return ERPC_NO_ERROR; } -u32 erpc_send_ack_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) { +u32 erpc_send_ack_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) +{ erpc_cmd_def_t cmd_send; cmd_send.head.dest_id = cmd_rev->head.src_id; cmd_send.head.port = cmd_rev->head.port; @@ -305,69 +370,87 @@ u32 erpc_send_ack_package(erpc_hw_cfg_t *hw, erpc_cmd_def_t *cmd_rev) { return ERPC_NO_ERROR; } -u32 erpc_rev_package(erpc_hw_cfg_t *hw) { - for (int i = 0; i < MAX_REC_CMD_CACHE_NUM; i++) { - if (hw->rec_cache[i].state == ERPC_CMD_WAIT_SERVER_DEAL) { +u32 erpc_rev_package(erpc_hw_cfg_t *hw) +{ + for (int i = 0; i < MAX_REC_CMD_CACHE_NUM; i++) + { + if (hw->rec_cache[i].state == ERPC_CMD_WAIT_SERVER_DEAL) + { + ERPC_DEBUG("find cmd wait server deal %d\n", i); erpc_cmd_def_t *cmd = (erpc_cmd_def_t *)&hw->rec_cache[i].data[0]; // 检查crc u8 crc_result = cmd_check_crc16(cmd); // 丢弃错误数据包 - if (crc_result) { + if (crc_result) + { hw->rec_cache[i].state = ERPC_CMD_NO_ERROR; continue; } // 丢弃不是本地数据包 - if (cmd->head.dest_id != hw->local_id) { + if (cmd->head.dest_id != hw->local_id) + { hw->rec_cache[i].state = ERPC_CMD_NO_ERROR; continue; } // 处理数据包 - switch (cmd->head.type) { - case PACKAGE_TYPE_CMD_REQ: - printf("{REQ}\n"); - erpc_send_ack_package(hw, cmd); - hw->rec_cache[i].state = ERPC_CMD_WAIT_TASK_DEAL; - break; - case PACKAGE_TYPE_CMD_REQ_ACK: - case PACKAGE_TYPE_CMD_RESP_ACK: - printf("{ACK}\n"); - erpc_rev_ack_package(hw, cmd); - hw->rec_cache[i].state = ERPC_CMD_NO_ERROR; - break; - case PACKAGE_TYPE_CMD_REPEAT: - erpc_rev_repeat_package(hw, cmd); - hw->rec_cache[i].state = ERPC_CMD_NO_ERROR; - break; - case PACKAGE_TYPE_CMD_RESP: - printf("{RESP}\n"); - erpc_rev_resp_package(hw, cmd); - hw->rec_cache[i].state = ERPC_CMD_RESP_OK; - break; - default: + switch (cmd->head.type) + { + case PACKAGE_TYPE_CMD_REQ: + ERPC_DEBUG("{REQ}\n"); + erpc_send_ack_package(hw, cmd); + hw->rec_cache[i].state = ERPC_CMD_WAIT_TASK_DEAL; + break; + case PACKAGE_TYPE_CMD_REQ_ACK: + ERPC_DEBUG("{ACK}\n"); + erpc_rev_ack_package(hw, cmd); + hw->rec_cache[i].state = ERPC_CMD_NO_ERROR; + break; - break; + case PACKAGE_TYPE_CMD_REPEAT: + erpc_rev_repeat_package(hw, cmd); + hw->rec_cache[i].state = ERPC_CMD_NO_ERROR; + break; + case PACKAGE_TYPE_CMD_RESP: + ERPC_DEBUG("{RESP}\n"); + erpc_rev_resp_package(hw, cmd); + hw->rec_cache[i].state = ERPC_CMD_RESP_OK; + break; + case PACKAGE_TYPE_CMD_RESP_ACK: + ERPC_DEBUG("{RESP_ACK}\n"); + erpc_rev_ack_package(hw, cmd); + hw->rec_cache[i].state = ERPC_CMD_NO_ERROR; + break; + default: + + break; } } } return ERPC_NO_ERROR; } -void erpc_rev_package_core() { +void erpc_rev_package_core() +{ list_t *list = &erpc_hw; - if (list->data == NULL) { + if (list->data == NULL) + { return; } - while (list != NULL) { + while (list != NULL) + { erpc_hw_cfg_t *hw = (erpc_hw_cfg_t *)list->data; erpc_rev_package(hw); list = list->next; } } -u32 erpc_set_rev_cahce(u8 hw, u8 *data, u16 len) { +u32 erpc_set_rev_cahce(u8 hw, u8 *data, u16 len) +{ erpc_hw_cfg_t *hw_cfg = erpc_hw_get(hw); CHECK_IF_ERROR(hw_cfg == NULL, ERPC_ERR_NOFOND_HW); - for (int i = 0; i < MAX_REC_CMD_CACHE_NUM; i++) { - if (hw_cfg->rec_cache[i].state == ERPC_CMD_NO_ERROR) { - printf("set rev cache %d\r\n", i); + for (int i = 0; i < MAX_REC_CMD_CACHE_NUM; i++) + { + if (hw_cfg->rec_cache[i].state == ERPC_CMD_NO_ERROR) + { + ERPC_DEBUG("set rev cache %d\r\n", i); memcpy(hw_cfg->rec_cache[i].data, data, len); hw_cfg->rec_cache[i].state = ERPC_CMD_WAIT_SERVER_DEAL; return ERPC_NO_ERROR; @@ -375,59 +458,75 @@ u32 erpc_set_rev_cahce(u8 hw, u8 *data, u16 len) { } return ERPC_ERR_REC_CACHE_FULL; } -void erpc_send_deal_core() { +void erpc_send_deal_core() +{ list_t *list = &erpc_hw; - if (list->data == NULL) { + if (list->data == NULL) + { return; } - while (list != NULL) { + while (list != NULL) + { erpc_hw_cfg_t *hw = (erpc_hw_cfg_t *)list->data; erpc_send_data(hw); } - if (erpc_sleep_tick != NULL) { + if (erpc_sleep_tick != NULL) + { erpc_sleep_tick(1); } } -void erpc_rev_deal_core() { +void erpc_rev_deal_core() +{ list_t *list = &erpc_hw; - if (list->data == NULL) { + if (list->data == NULL) + { return; } - while (list != NULL) { + while (list != NULL) + { erpc_hw_cfg_t *hw = (erpc_hw_cfg_t *)list->data; - { // 遍历接收缓存 - for (int j = 0; j < MAX_REC_CMD_CACHE_NUM; j++) { - { // 发现等待处理的数据包 - if (hw->rec_cache[j].state != ERPC_CMD_WAIT_TASK_DEAL) { + { // 遍历接收缓存 + for (int j = 0; j < MAX_REC_CMD_CACHE_NUM; j++) + { + { // 发现等待处理的数据包 + if (hw->rec_cache[j].state != ERPC_CMD_WAIT_TASK_DEAL) + { continue; } } - { // 多线程下,抢占处理权限 + { // 多线程下,抢占处理权限 hw->deal_lock(); - if (hw->rec_cache[j].state == ERPC_CMD_WAIT_TASK_DEAL) { + if (hw->rec_cache[j].state == ERPC_CMD_WAIT_TASK_DEAL) + { // 获取指令的处理权限 hw->rec_cache[j].state = ERPC_CMD_WAIT_TASK_DEAL_FINISH; - } else { + } + else + { // 已经有线程抢先执行了 hw->deal_unlock(); continue; } hw->deal_unlock(); } - { // 处理指令 + { // 处理指令 // 搜索指令列表 list_t *cmd_list = &hw->cmd_list; // 链表是空的 - if (cmd_list->data == NULL) { + if (cmd_list->data == NULL) + { continue; } // 获取指令指针 erpc_cmd_def_t *cmd_def = (erpc_cmd_def_t *)hw->rec_cache[j].data; - while (cmd_list != NULL) { // 搜索指令列表 + while (cmd_list != NULL) + { // 搜索指令列表 erpc_cmd_list_t *cmd_obj = (erpc_cmd_list_t *)cmd_list->data; - if (cmd_obj->cmd == cmd_def->head.port) { - if (cmd_obj->handle != NULL) { + if (cmd_obj->cmd == cmd_def->head.port) + { + if (cmd_obj->handle != NULL) + { // 指令调用 cmd_obj->handle(hw->ord, cmd_def->head.src_id, cmd_def->head.dest_id, cmd_def->head.port, @@ -445,7 +544,8 @@ void erpc_rev_deal_core() { } list = list->next; } - if (erpc_sleep_tick != NULL) { + if (erpc_sleep_tick != NULL) + { erpc_sleep_tick(1); } } \ No newline at end of file diff --git a/erpc_core.h b/erpc_core.h index 1834a27..07e1fc5 100644 --- a/erpc_core.h +++ b/erpc_core.h @@ -31,13 +31,14 @@ typedef struct erpc_cmd_head_t { u8 msg_len; } erpc_cmd_head_t; +#define MAX_CMD_LEN (256 - sizeof(erpc_cmd_head_t)) // crc16最大支持256字节 + typedef struct erpc_cmd_def_t { erpc_cmd_head_t head; u8 crc_16[2]; - u8 *data; + u8 data[MAX_CMD_LEN]; } erpc_cmd_def_t; -#define MAX_CMD_LEN (256 - sizeof(erpc_cmd_head_t)) // crc16最大支持256字节 #define CMD_MAX_RETRY 5 // 最大重发次数 #define CMD_TIMEOUT 30 // 超时时间 tick #define MAX_REC_CMD_CACHE_NUM \ diff --git a/erpc_core.o b/erpc_core.o deleted file mode 100644 index 9d0e0ba..0000000 Binary files a/erpc_core.o and /dev/null differ diff --git a/erpc设计文档.md b/erpc设计文档.md index d3f5a12..f7d5498 100644 --- a/erpc设计文档.md +++ b/erpc设计文档.md @@ -1 +1,39 @@ +## 协议设计 + +### 指令通讯 +1. 指令发送方法:
+ 采用send-ack模式,即主机发送指令后,等待目标设备的ack确认,确认后才认为指令发送成功。 +2. notify-noreply模式:
+ 接口:
+ ```c + u32 erpc_sand(u8 hw, u8 dest_id, u16 port, u8 *data, u16 len) + ``` + 描述:
+ 主机对目标设备发送一条指令,并不期待回复。其本质就是发送一次指令。 + ![](./picture/1.jpg) +3. notify-reply模式:
+ 接口:
+ ```c + //主机: + u32 erpc_send_wait_reply(u8 hw, u8 dest_id, u16 port, u8 *data, u16 len, u8 *reply_data, u16 *reply_len, u32 timeout); + //目标设备: + u32 erpc_replay(u8 hw, u8 dest_id, u16 port, u8 *data_out, u16 len); + + ``` + 描述:
+ 本质由2条指令组成。
+ 主机发送req指令,从机直接回复。主机开始等待从机指令。
+ 从机处理完成后,向主机发送rep指令,并附带回复数据。
+ 主机收到rep指令后,开始等待rep指令的ack确认。
+ ![](./picture/2.jpg) +4. 指令工作在单线程模式下:
+ 指令发送后,等待ack确认,直到确认后才认为指令发送成功。如果确认超时,则认为指令发送失败。 + 可以在上述的接口中发现 cmd 并不定义为cmd,而是用了port的称呼。port的取值范围为0~65535,可以用来表示不同的指令。
+ +4. 多device通讯方法:
+ 每个port工作是单线程的,这就意味着,如果有多个device需要同时发送指令,则需要多线程或多进程。也就意味着需要定义不同的port号,来区分不同的线程,哪怕他是相同的指令。
+ 例如:节点0x03中挂在了3个电机,需要这3个电机同时运动,此时理论上指令是相同的,但是device不同的。通讯库没有做device id的区分。为此需要将port号划分为cmd + device id的形式。cmd相同的指令,device id不同,这样就可以实现多device通讯。
+ u16(port) = u8(cmd) + u8(device_id);
+ 这样一个cmd号需要链接到多个port上。此时的cmd可叫做cmd组 + ![](./picture/3.jpg) \ No newline at end of file diff --git a/list.c b/list.c index 582a34d..392318c 100644 --- a/list.c +++ b/list.c @@ -1,6 +1,7 @@ #include "list.h" #include "stdio.h" - +#include "stdlib.h" +#include "config.h" list_t *list_create(void *data) { list_t *node = (list_t *)malloc(sizeof(list_t)); @@ -41,7 +42,7 @@ void list_print(list_t *head) list_t *node = head; while (node != NULL) { - printf("%p\n", node->data); + ERPC_DEBUG("%p\n", node->data); node = node->next; } } diff --git a/list.o b/list.o deleted file mode 100644 index e32bab7..0000000 Binary files a/list.o and /dev/null differ diff --git a/makefile b/makefile index 61c0a50..158c108 100644 --- a/makefile +++ b/makefile @@ -3,8 +3,8 @@ # 指定编译器 CC = gcc # 指定编译选项 -CFLAGS = -Wall -Wextra -std=c11 - +CFLAGS = -Wall -Wextra -std=c11 -g +BUILD_DIR = build # 源文件 SRCS = erpc_core.c \ port_self.c \ @@ -22,11 +22,11 @@ all: $(Target) # 链接目标 $(Target): $(OBJS) - $(CC) -o $@ $^ + $(CC) -o $@ $(addprefix $(BUILD_DIR)/, $^) # 编译源文件 %.o: %.c - $(CC) $(CFLAGS) -c $< -o $@ + $(CC) $(CFLAGS) -c $< -o $(BUILD_DIR)/$@ # 清理目标 clean: diff --git a/picture/1.jpg b/picture/1.jpg new file mode 100644 index 0000000..1ec3a88 Binary files /dev/null and b/picture/1.jpg differ diff --git a/picture/2.jpg b/picture/2.jpg new file mode 100644 index 0000000..3984c81 Binary files /dev/null and b/picture/2.jpg differ diff --git a/picture/3.jpg b/picture/3.jpg new file mode 100644 index 0000000..1a8a900 Binary files /dev/null and b/picture/3.jpg differ diff --git a/port_self.c b/port_self.c index 3123aec..802063c 100644 --- a/port_self.c +++ b/port_self.c @@ -6,20 +6,48 @@ #include "erpc_core.h" #include "windows.h" #include -void hellworld() +u32 hellworld(u8 hw, u8 src_id, u8 dest_id, u16 port, u8 *data, u16 len) { - printf("Hello World!\n"); + ERPC_DEBUG("Hello World:\n"); + ERPC_DEBUG("len = %d, msg :%s\n", len, data); + // 防止编译警告 + UNUSED(hw); + UNUSED(src_id); + UNUSED(dest_id); + UNUSED(port); + UNUSED(data); + UNUSED(len); + return 0; } -void hello_cat() +u32 hello_cat(u8 hw, u8 src_id, u8 dest_id, u16 port, u8 *data, u16 len) { - printf("Hello Cat!\n"); + ERPC_DEBUG("Hello Cat!\n"); + // 防止编译警告 + UNUSED(hw); + UNUSED(src_id); + UNUSED(dest_id); + UNUSED(port); + UNUSED(data); + UNUSED(len); + return 0; } -void hello_dog(u8 hw, u8 src_id, u8 dest_id, u16 port, u8 *data, u16 len) +u32 hello_dog(u8 hw, u8 src_id, u8 dest_id, u16 port, u8 *data, u16 len) { - printf("Hello Dog!\n"); + ERPC_DEBUG("Hello Dog!\n"); + // 防止编译警告 u8 data_out[10] = "12345"; - erpc_replay(hw, dest_id, port, data_out, sizeof(data_out)); + u32 ret = erpc_replay(hw, dest_id, port, data_out, sizeof(data_out)); + ERPC_DEBUG("erpc_replay ret:%d\n", ret); + // 防止编译警告 + UNUSED(ret); + UNUSED(hw); + UNUSED(src_id); + UNUSED(dest_id); + UNUSED(port); + UNUSED(data); + UNUSED(len); + return 0; } erpc_cmd_list_t erpc_cmd_list[] = { {.cmd = 0x01, hellworld}, @@ -49,7 +77,7 @@ static void send_unlock_h() ReleaseMutex(send_lock); } u8 data[300]; -static u8 data_write(u8 *data, u32 len) +static u8 data_write(u8 *data, u16 len) { erpc_set_rev_cahce(0, data, len); return 0; @@ -66,7 +94,7 @@ erpc_hw_cfg_t self_hw_cfg = { }; void erpc_cmd_config() { - for (int i = 0; i < sizeof(erpc_cmd_list) / sizeof(erpc_cmd_list[0]); i++) + for (int i = 0; i < (int)sizeof(erpc_cmd_list) / (int)sizeof(erpc_cmd_list[0]); i++) { erpc_add_cmd_list(&self_hw_cfg, &erpc_cmd_list[i]); } @@ -78,6 +106,7 @@ void sys_sleep(u32 ms) DWORD WINAPI send_task(LPVOID lpParam) { + UNUSED(lpParam); while (1) { erpc_send_deal_core(); @@ -85,10 +114,11 @@ DWORD WINAPI send_task(LPVOID lpParam) } DWORD WINAPI rev_task(LPVOID lpParam) { + UNUSED(lpParam); while (1) { - // printf("rev_task\n"); + // ERPC_DEBUG("rev_task\n"); erpc_rev_package_core(); erpc_rev_deal_core(); } @@ -96,42 +126,47 @@ DWORD WINAPI rev_task(LPVOID lpParam) DWORD WINAPI test_task(LPVOID lpParam) { - printf("test_task\n"); + UNUSED(lpParam); + ERPC_DEBUG("test_task\n"); while (1) { - // printf("[test_task]send\n"); - u32 ret = erpc_send(self_hw_cfg.ord, self_hw_cfg.local_id, 0x01, NULL, 0); - printf("[test_task]send ret:%d\n", ret); + // ERPC_DEBUG("[test_task]send\n"); + char msg[] = "miao miao miao\n"; + u32 ret = erpc_send(self_hw_cfg.ord, self_hw_cfg.local_id, 0x01, (u8 *)msg, sizeof(msg)); + ERPC_DEBUG("[test_task]send ret:%d\n", ret); ret = erpc_send(self_hw_cfg.ord, self_hw_cfg.local_id, 0x02, NULL, 0); - printf("[test_task]send ret:%d\n", ret); + ERPC_DEBUG("[test_task]send ret:%d\n", ret); ret = erpc_send_wait_reply(self_hw_cfg.ord, self_hw_cfg.local_id, 0x03, NULL, 0, data, NULL, 1000); - printf("[test_task]send ret:%d\n", ret); + ERPC_DEBUG("[test_task]send ret:%d\n", ret); + UNUSED(ret); sys_sleep(1000); } } int main(int argc, char *argv[]) { + UNUSED(argc); + UNUSED(argv); u32 ret = 0; - printf("erpc_port_self start\n"); + ERPC_DEBUG("erpc_port_self start\n"); ret = erpc_hw_add(&self_hw_cfg); - printf("erpc_hw_add ret:%d\n", ret); + ERPC_DEBUG("erpc_hw_add ret:%d\n", ret); CHECK_IF_ERROR(ret, 0); erpc_cmd_config(); - printf("erpc_cmd_config ret:%d\n", ret); + ERPC_DEBUG("erpc_cmd_config ret:%d\n", ret); erpc_sleep_tick = sys_sleep; HANDLE threadHandle[3]; deal_lock = CreateMutex(NULL, FALSE, NULL); if (deal_lock == NULL) { - printf("创建互斥锁失败,错误代码:%d\n", GetLastError()); + ERPC_DEBUG("创建互斥锁失败\n"); return 1; } send_lock = CreateMutex(NULL, FALSE, NULL); if (send_lock == NULL) { - printf("创建互斥锁失败,错误代码:%d\n", GetLastError()); + ERPC_DEBUG("创建互斥锁失败\n"); return 1; } threadHandle[0] = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)send_task, NULL, 0, NULL); diff --git a/port_self.exe b/port_self.exe index 5877aa2..bbbc9e8 100644 Binary files a/port_self.exe and b/port_self.exe differ diff --git a/port_self.o b/port_self.o deleted file mode 100644 index 7a28d65..0000000 Binary files a/port_self.o and /dev/null differ diff --git a/架构.drawio b/架构.drawio new file mode 100644 index 0000000..c2f7795 --- /dev/null +++ b/架构.drawio @@ -0,0 +1,45 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +