poe

Уређивач .po фајлова
Дневник | Датотеке | Референце | ПРОЧИТАЈМЕ | ЛИЦЕНЦА

чување 75fb0fdea8b590e9bfdccc2113aceefbb8f96c71
родитељ 5db5e5b19ede56ab60ecc4c7b937b421b4feb2a8
Аутор: Страхиња Радић <contact@strahinja.org>
Датум:   Mon, 29 Nov 2021 21:39:19 +0100

Fix very long comment line cutoff (use dynamic allocation); minor fixes from asan/valgrind

Signed-off-by: Страхиња Радић <contact@strahinja.org>

Diffstat:
MTODO | 2+-
Mpo.c | 83++++++++++++++++++++++++++++++++++++++++++++++++++++++++-----------------------
Mpo.h | 1-
Mpoe.c | 1+
измењених датотека: 4, додавања: 61(+), брисања: 26(-)

diff --git a/TODO b/TODO @@ -8,7 +8,7 @@ [x] Change the word-operations (C-W, C-R, C-T) to be more intuitive with regards to including spaces - [ ] Fix very long comment line cutoff + [x] Fix very long comment line cutoff < > Wrap long lines? Not if it would complicate the code too much. diff --git a/po.c b/po.c @@ -309,6 +309,7 @@ u32_add_comment(struct PoEntry* entry, const uint32_t* comment) { uint32_t** comments = NULL; uint32_t* new_line = NULL; + size_t len = 0; if (!entry) return NULL; @@ -323,11 +324,12 @@ u32_add_comment(struct PoEntry* entry, const uint32_t* comment) return NULL; entry->comments = comments; - new_line = calloc(MAXCOMMENTLINE, sizeof(uint32_t)); + len = u32_strlen(comment)+1; + new_line = calloc(len, sizeof(uint32_t)); if (!new_line) return NULL; entry->comments[entry->comment_lines - 1] = new_line; - u32_strncpy(new_line, comment, MAXCOMMENTLINE); + u32_strncpy(new_line, comment, len); return entry; } @@ -336,6 +338,7 @@ u32_add_trans_comment(struct PoEntry* entry, const uint32_t* trans_comment) { uint32_t** trans_comments = NULL; uint32_t* new_line = NULL; + size_t len = 0; if (!entry) return NULL; @@ -351,11 +354,12 @@ u32_add_trans_comment(struct PoEntry* entry, const uint32_t* trans_comment) return NULL; entry->trans_comments = trans_comments; - new_line = calloc(MAXCOMMENTLINE, sizeof(uint32_t)); + len = u32_strlen(trans_comment)+1; + new_line = calloc(len, sizeof(uint32_t)); if (!new_line) return NULL; entry->trans_comments[entry->trans_comment_lines - 1] = new_line; - u32_strncpy(new_line, trans_comment, MAXCOMMENTLINE); + u32_strncpy(new_line, trans_comment, len); return entry; } @@ -364,6 +368,7 @@ add_ref_comment(struct PoEntry* entry, const char* comment) { char** ref_comments = NULL; char* new_line = NULL; + size_t len = 0; if (!entry) return NULL; @@ -379,11 +384,12 @@ add_ref_comment(struct PoEntry* entry, const char* comment) return NULL; entry->ref_comments = ref_comments; - new_line = calloc(MAXCOMMENTLINE + 1, 1); + len = strlen(comment)+1; + new_line = calloc(len, 1); if (!new_line) return NULL; entry->ref_comments[entry->ref_comment_lines - 1] = new_line; - strncpy(new_line, comment, MAXCOMMENTLINE); + strncpy(new_line, comment, len); return entry; } @@ -483,12 +489,12 @@ save_file(const struct PoEntry* entries, const size_t real_msgid_count, size_t len = strlen(filename); FILE* output = NULL; char* backup_filename = calloc(len + 2, 1); - char tmp_filename[MAXPATH]; - strcpy(tmp_filename, filename); - strcpy(tmp_filename, dirname(tmp_filename)); - strncat(tmp_filename, "/poe.tmp", MAXPATH - 1); + char tmp_filename[2][MAXPATH]; + strcpy(tmp_filename[0], filename); + strcpy(tmp_filename[1], dirname(tmp_filename[0])); + strncat(tmp_filename[1], "/poe.tmp", MAXPATH - 1); - if (!(output = fopen(tmp_filename, "wt"))) + if (!(output = fopen(tmp_filename[1], "wt"))) return SAVE_ERR_CANT_OPEN_FILE; strncpy(backup_filename, filename, len + 1); backup_filename[len] = '~'; @@ -499,28 +505,42 @@ save_loop_entries_start: goto save_loop_entries_done; if (current->comment_lines > 0) { - char u8_comment[MAXCOMMENTLINE * UTF8REPMAX]; + char* u8_comment = NULL; for (size_t c = 0; c < current->comment_lines; c++) { + size_t len = u32_strlen(*(current->comments + c))+1; + if (!u8_comment) + u8_comment = calloc(len * UTF8REPMAX, 1); + else + u8_comment = realloc(u8_comment, len * UTF8REPMAX); + if (!u8_comment) + return SAVE_ERR_CANT_ALLOC; unicode_string_to_u8(u8_comment, - *(current->comments + c), - MAXCOMMENTLINE * UTF8REPMAX); + *(current->comments + c), len * UTF8REPMAX); fprintf(output, "#%s%s\n", current->obsolete ? "~" : "", u8_comment); } + free(u8_comment); } if (current->trans_comment_lines > 0) { - char u8_trans_comment[MAXCOMMENTLINE * UTF8REPMAX]; + char* u8_trans_comment = NULL; for (size_t tc = 0; tc < current->trans_comment_lines; tc++) { + size_t len = u32_strlen(*(current->trans_comments + tc))+1; + if (!u8_trans_comment) + u8_trans_comment = calloc(len * UTF8REPMAX, 1); + else + u8_trans_comment = realloc(u8_trans_comment, len * UTF8REPMAX); + if (!u8_trans_comment) + return SAVE_ERR_CANT_ALLOC; unicode_string_to_u8(u8_trans_comment, - *(current->trans_comments + tc), - MAXCOMMENTLINE * UTF8REPMAX); + *(current->trans_comments + tc), len * UTF8REPMAX); fprintf(output, "#.%s%s\n", u8_trans_comment[0] == 0 ? "" : " ", u8_trans_comment); } + free(u8_trans_comment); } if (current->ref_comment_lines > 0) { @@ -816,7 +836,7 @@ save_loop_entries_done: if (rename(filename, backup_filename) == -1) return SAVE_ERR_CANT_MOVE_FILE; - if (rename(tmp_filename, filename) == -1) + if (rename(tmp_filename[1], filename) == -1) return SAVE_ERR_CANT_MOVE_FILE; free(backup_filename); @@ -1068,15 +1088,25 @@ parse_po_line(const char* line, struct DrawState* dstate, dstate); else if (*pstate & PS_COMMENT_TRAN) { - uint32_t u32_token[MAXCOMMENTLINE]; - u8_string_to_unicode(u32_token, token, MAXCOMMENTLINE); + uint32_t* u32_token = NULL; + size_t len = strlen(token)+1; + u32_token = calloc(len, sizeof(uint32_t)); + if (!u32_token) + return PARSE_ERR_ALLOC; + u8_string_to_unicode(u32_token, token, len); u32_add_comment(*current_entry, u32_token); + free(u32_token); } else if (*pstate & PS_COMMENT_EXTR) { - uint32_t u32_token[MAXCOMMENTLINE]; - u8_string_to_unicode(u32_token, token, MAXCOMMENTLINE); + uint32_t* u32_token = NULL; + size_t len = strlen(token)+1; + u32_token = calloc(len, sizeof(uint32_t)); + if (!u32_token) + return PARSE_ERR_ALLOC; + u8_string_to_unicode(u32_token, token, len); u32_add_trans_comment(*current_entry, u32_token); + free(u32_token); } else if (*pstate & PS_COMMENT_FLAG) { @@ -1126,10 +1156,15 @@ parse_po_line(const char* line, struct DrawState* dstate, add_ref_comment(*current_entry, token); else if (*pstate & PS_COMMENT_OBSO) { - uint32_t u32_token[MAXCOMMENTLINE]; - u8_string_to_unicode(u32_token, token, MAXCOMMENTLINE); + uint32_t* u32_token = NULL; + size_t len = strlen(token)+1; + u32_token = calloc(len, sizeof(uint32_t)); + if (!u32_token) + return PARSE_ERR_ALLOC; + u8_string_to_unicode(u32_token, token, len); u32_add_comment(*current_entry, u32_token); (*current_entry)->obsolete = 1; + free(u32_token); } *token = 0; } diff --git a/po.h b/po.h @@ -4,7 +4,6 @@ #include <stdlib.h> #define MSGSTR_MAX 4096 -#define MAXCOMMENTLINE 512 #define ALLOC_DELTA 10 #define PO_DETECTION_LINES 24 diff --git a/poe.c b/poe.c @@ -2237,6 +2237,7 @@ main(int argc, char** argv) tb_init(); error[0] = 0; + state.maxx = 0; while (state.running) {