From 6322c3728b4b57a351701a118d9c1771e98be769 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mario=20H=C3=BCttel?= Date: Sat, 15 May 2021 21:58:00 +0200 Subject: [PATCH] Use singly linked list to store profile commands. --- .../config-parser/temp-profile-parser.c | 40 ++++++++++++++++--- .../config-parser/temp-profile-parser.h | 29 +++++++++++++- .../reflow-controller/temp-profile-executer.h | 2 +- stm-firmware/temp-profile-executer.c | 18 +++++++-- 4 files changed, 77 insertions(+), 12 deletions(-) diff --git a/stm-firmware/config-parser/temp-profile-parser.c b/stm-firmware/config-parser/temp-profile-parser.c index 7e5500f..08c42c8 100644 --- a/stm-firmware/config-parser/temp-profile-parser.c +++ b/stm-firmware/config-parser/temp-profile-parser.c @@ -23,6 +23,7 @@ #include #include #include +#include struct pl_command_list_map { enum pl_command_type command; @@ -155,9 +156,20 @@ static int parse_line(char *line, struct pl_command *cmd) return 0; } +static SlList *copy_and_append_command_to_list(SlList *list, const struct pl_command *cmd) +{ + struct pl_command *alloced_cmd; + + alloced_cmd = (struct pl_command *)malloc(sizeof(struct pl_command)); + memcpy(alloced_cmd, cmd, sizeof(struct pl_command)); + list = sl_list_append(list, alloced_cmd); + + return list; +} + enum pl_ret_val temp_profile_parse_from_file(const char *filename, - struct pl_command *cmd_list, - uint32_t cmd_list_length, + SlList **command_list, + uint32_t max_len, uint32_t *cmds_parsed) { FIL script_file; @@ -165,9 +177,10 @@ enum pl_ret_val temp_profile_parse_from_file(const char *filename, int res; enum pl_ret_val ret = PL_RET_SUCCESS; char workbuff[256]; + struct pl_command temp_command; uint32_t cmd_idx; - if (!filename || !cmd_list || !cmd_list_length || !cmds_parsed) + if (!filename || !command_list || !max_len || !cmds_parsed) return PL_RET_PARAM_ERR; @@ -189,19 +202,22 @@ enum pl_ret_val temp_profile_parse_from_file(const char *filename, } /* Check if list already full */ - if (cmd_idx >= cmd_list_length) { + if (cmd_idx >= max_len) { ret = PL_RET_LIST_FULL; goto exit_close; } /* Parse the line */ - res = parse_line(workbuff, &cmd_list[cmd_idx]); + res = parse_line(workbuff, &temp_command); if (res < 0) { ret = PL_RET_SCRIPT_ERR; goto exit_close; } else if (res == 0) { cmd_idx++; - *cmds_parsed= cmd_idx; + *cmds_parsed = cmd_idx; + + /* Append the temp_command to the list */ + *command_list = copy_and_append_command_to_list(*command_list, &temp_command); } @@ -212,3 +228,15 @@ exit_close: exit: return ret; } + +static void delete_pl_command(void *cmd) +{ + if (cmd) + free(cmd); +} + +void temp_profile_free_command_list(SlList **list) +{ + sl_list_free_full(*list, delete_pl_command); + *list = NULL; +} diff --git a/stm-firmware/include/reflow-controller/config-parser/temp-profile-parser.h b/stm-firmware/include/reflow-controller/config-parser/temp-profile-parser.h index fed19e6..2b4e945 100644 --- a/stm-firmware/include/reflow-controller/config-parser/temp-profile-parser.h +++ b/stm-firmware/include/reflow-controller/config-parser/temp-profile-parser.h @@ -22,6 +22,7 @@ #define __CONFIG_PARSER_TEMP_PROFILE_PARSER_H__ #include +#include enum pl_command_type { PL_PID_CONF = 0, @@ -49,9 +50,33 @@ struct pl_command { float params[PROFILE_LANG_MAX_NUM_ARGS]; }; +/** + * @brief Parse a temperature profile from file and generate the command list + * + * Commands are parsed into the list given by \p command_list. If \p max_len is reached, + * the function returns with @ref PL_RET_LIST_FULL + * + * In any case, the command list not cleared afterwards. The user has to clear the command list manually + * using @ref temp_profile_free_command_list. + * + * @param filename File to parse + * @param[in, out] command_list Command list to output @ref pl_command elements in. + * @param max_len maximum number of commands. + * @param cmds_parsed Number of parsed commands + * @return + */ enum pl_ret_val temp_profile_parse_from_file(const char *filename, - struct pl_command *cmd_list, - uint32_t cmd_list_length, + SlList **command_list, + uint32_t max_len, uint32_t *cmds_parsed); +/** + * @brief Fully free a comamnd list including hte sotred command structures. + * + * \p list's destination is set to NULL to indicate the empty list. + * + * @param[in, out] list Pointer to list. + */ +void temp_profile_free_command_list(SlList **list); + #endif /* __CONFIG_PARSER_TEMP_PROFILE_PARSER_H__ */ diff --git a/stm-firmware/include/reflow-controller/temp-profile-executer.h b/stm-firmware/include/reflow-controller/temp-profile-executer.h index 67ad3e3..0fc025b 100644 --- a/stm-firmware/include/reflow-controller/temp-profile-executer.h +++ b/stm-firmware/include/reflow-controller/temp-profile-executer.h @@ -24,7 +24,7 @@ #include #include -#define MAX_PROFILE_LENGTH 50 +#define MAX_PROFILE_LENGTH 64 enum tpe_status { TPE_OFF, diff --git a/stm-firmware/temp-profile-executer.c b/stm-firmware/temp-profile-executer.c index 940ed8f..042e584 100644 --- a/stm-firmware/temp-profile-executer.c +++ b/stm-firmware/temp-profile-executer.c @@ -34,7 +34,7 @@ static bool IN_SECTION(.ccm.bss) pid_should_run; struct pid_controller IN_SECTION(.ccm.bss) pid; bool IN_SECTION(.ccm.bss) cmd_continue; -static struct pl_command IN_SECTION(.ccm.bss) cmd_list[MAX_PROFILE_LENGTH]; +static SlList *command_list = NULL; static void tpe_abort(void) { @@ -59,11 +59,19 @@ enum pl_ret_val temp_profile_executer_start(const char *filename) state.profile_steps = 0; cmd_continue = false; - res = temp_profile_parse_from_file(filename, cmd_list, MAX_PROFILE_LENGTH, &parsed_count); + /* This should never happen... But who knows */ + if (command_list) { + temp_profile_free_command_list(&command_list); + } + + res = temp_profile_parse_from_file(filename, &command_list, MAX_PROFILE_LENGTH, &parsed_count); if (res == PL_RET_SUCCESS) { state.profile_steps = parsed_count; state.status = TPE_RUNNING; state.start_timestamp = systick_get_global_tick(); + } else { + if (command_list) + temp_profile_free_command_list(&command_list); } return res; @@ -177,7 +185,7 @@ int temp_profile_executer_handle(void) if (!systick_ticks_have_passed(last_tick, 100)) return 0; - current_cmd = &cmd_list[state.step]; + current_cmd = (struct pl_command *)sl_list_nth(command_list, state.step)->data; next_step = state.step; switch (current_cmd->cmd) { @@ -250,6 +258,10 @@ int temp_profile_executer_stop(void) oven_pid_stop(); } + /* Free the command list */ + if (command_list) + temp_profile_free_command_list(&command_list); + loudspeaker_set(0); return 0;