From 09d48d5757d0c39f36b67f0db23616a5a9399ccc Mon Sep 17 00:00:00 2001 From: gitlost Date: Fri, 15 May 2026 11:20:30 +0100 Subject: [PATCH] aztec: avoid possible overflow in comparison output/CLI/testcommon: suppress some gcc-16 (C23) warnings "-Wdiscarded-qualifiers" (QChar) GUI: suppress some gcc-16 (C23) warnings "-Wdeprecated-enum-enum-conversion" channel: use explicit `const struct` for precalcs instead of typedef (makes code more transparent) README.linux: Fedora 43 -> 44 --- README.linux | 4 ++-- backend/aztec.c | 6 +++--- backend/channel.c | 13 +++++++------ backend/channel_precalcs.h | 6 +++--- backend/output.c | 10 ++++------ backend/output.h | 2 +- backend/tests/testcommon.c | 5 +++-- frontend/main.c | 8 ++++---- frontend_qt/mainwindow.cpp | 21 ++++++++++++--------- 9 files changed, 39 insertions(+), 36 deletions(-) diff --git a/README.linux b/README.linux index 3cde2245..75050b9f 100644 --- a/README.linux +++ b/README.linux @@ -1,6 +1,6 @@ -% README.linux 2026-01-01 +% README.linux 2026-05-15 % Tested on Ubuntu 20.04.4 LTS, Ubuntu 22.04 LTS, Ubuntu 24.04 LTS and -% Fedora Linux 43 (Workstation Edition) +% Fedora Linux 44 (Workstation Edition) % vim: set ts=4 sw=4 et : 1. Prerequisites for building zint diff --git a/backend/aztec.c b/backend/aztec.c index 292bee28..70266746 100644 --- a/backend/aztec.c +++ b/backend/aztec.c @@ -84,7 +84,7 @@ static char az_get_next_mode(const char modes[], const int length, int i) { #define AZ_DOUBLE_PUNCT_NO_LEN_CHECK(s, i) \ (((s)[i] == '\r' && (s)[(i) + 1] == '\n') \ - || ((s)[(i) + 1] == ' ' && ((s)[i] == '.' || (s)[i] == ',' || (s)[i] == ':'))) + || ((s)[(i) + 1] == ' ' && ((s)[i] == '.' || (s)[i] == ',' || (s)[i] == ':'))) #define AZ_DOUBLE_PUNCT(s, l, i) ((i) + 1 < (l) && AZ_DOUBLE_PUNCT_NO_LEN_CHECK(s, i)) @@ -497,7 +497,7 @@ static int az_tokens_add_chk(struct az_state *state, const int extra) { } state->tokens.size = size; state->tokens.used = 0; - } else if (state->tokens.used + extra >= state->tokens.size) { + } else if (state->tokens.used >= state->tokens.size - extra) { /* Compare this way to avoid possible overflow */ struct az_token *tokens; const unsigned short size = state->tokens.size * 2; if (size <= state->tokens.size /* Overflow */ @@ -1029,7 +1029,7 @@ static int az_binary_string(const unsigned char source[], const int length, int } for (i = 0; i < stateEnd.tokens.used; i++) { - const struct az_token *token = stateEnd.tokens.tokens + i; + const struct az_token *const token = stateEnd.tokens.tokens + i; const int count = token->count; if (count < 0) { bp = z_bin_append_posn(token->value, -count, binary_string, bp); diff --git a/backend/channel.c b/backend/channel.c index 62560ccf..b795418f 100644 --- a/backend/channel.c +++ b/backend/channel.c @@ -35,9 +35,9 @@ #include #include "common.h" -typedef const struct s_channel_precalc { +struct channel_precalc { int value; unsigned char B[8]; unsigned char S[8]; unsigned char bmax[7]; unsigned char smax[7]; -} channel_precalc; +}; #if 0 #define CHANNEL_GENERATE_PRECALCS @@ -49,8 +49,8 @@ typedef const struct s_channel_precalc { static void channel_generate_precalc(int channels, int value, int mod, int last, int B[8], int S[8], int bmax[7], int smax[7]) { int i; - if (value == mod) printf("static channel_precalc channel_precalcs%d[] = {\n", channels); - printf(" { %7ld, {", value); for (i = 0; i < 8; i++) printf(" %d,", B[i]); fputs(" },", stdout); + if (value == mod) printf("static const struct channel_precalc channel_precalcs%d[] = {\n", channels); + printf(" { %7d, {", value); for (i = 0; i < 8; i++) printf(" %d,", B[i]); fputs(" },", stdout); fputs(" {", stdout); for (i = 0; i < 8; i++) printf(" %d,", S[i]); fputs(" },", stdout); fputs(" {", stdout); for (i = 0; i < 7; i++) printf(" %d,", bmax[i]); fputs(" },", stdout); fputs(" {", stdout); for (i = 0; i < 7; i++) printf(" %d,", smax[i]); fputs(" }, },\n", stdout); @@ -60,7 +60,8 @@ static void channel_generate_precalc(int channels, int value, int mod, int last, #include "channel_precalcs.h" #endif -static int channel_copy_precalc(channel_precalc *const precalc, int B[8], int S[8], int bmax[7], int smax[7]) { +static int channel_copy_precalc(const struct channel_precalc *const precalc, int B[8], int S[8], int bmax[7], + int smax[7]) { int i; for (i = 0; i < 7; i++) { @@ -89,7 +90,7 @@ static void CHNCHR(int channels, int target_value, int B[8], int S[8]) { /* Use of initial pre-calculations taken from Barcode Writer in Pure PostScript (BWIPP) Copyright (c) 2004-2026 Terry Burton */ /* SPDX-License-Identifier: MIT */ - static channel_precalc initial_precalcs[6] = { + static const struct channel_precalc initial_precalcs[6] = { { 0, { 1, 1, 1, 1, 1, 2, 1, 2, }, { 1, 1, 1, 1, 1, 1, 1, 3, }, { 1, 1, 1, 1, 1, 3, 2, }, { 1, 1, 1, 1, 1, 3, 3, }, }, { 0, { 1, 1, 1, 1, 2, 1, 1, 3, }, { 1, 1, 1, 1, 1, 1, 1, 4, }, { 1, 1, 1, 1, 4, 3, 3, }, diff --git a/backend/channel_precalcs.h b/backend/channel_precalcs.h index f1e6ebf7..1e3f2684 100644 --- a/backend/channel_precalcs.h +++ b/backend/channel_precalcs.h @@ -1,6 +1,6 @@ /* libzint - the open source barcode library - Copyright (C) 2020-2022 Robin Stuart + Copyright (C) 2020-2026 Robin Stuart Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions @@ -35,13 +35,13 @@ /* Channel code precalculated values to avoid excessive looping */ /* To generate uncomment CHANNEL_GENERATE_PRECALCS define and run "backend/tests/test_channel -f generate -g" */ /* Paste result below here */ -static channel_precalc channel_precalcs7[] = { +static const struct channel_precalc channel_precalcs7[] = { { 115338, { 1, 3, 1, 1, 1, 1, 5, 1, }, { 1, 1, 1, 2, 1, 2, 3, 3, }, { 1, 7, 5, 5, 5, 5, 5, }, { 1, 7, 7, 7, 6, 6, 5, }, }, { 230676, { 1, 1, 2, 2, 4, 1, 1, 2, }, { 1, 2, 1, 3, 2, 1, 3, 1, }, { 1, 7, 7, 6, 5, 2, 2, }, { 1, 7, 6, 6, 4, 3, 3, }, }, { 346014, { 1, 2, 3, 1, 1, 1, 3, 2, }, { 1, 2, 2, 1, 1, 3, 1, 3, }, { 1, 7, 6, 4, 4, 4, 4, }, { 1, 7, 6, 5, 5, 5, 3, }, }, { 461352, { 1, 2, 1, 1, 1, 2, 2, 4, }, { 1, 3, 1, 1, 3, 2, 2, 1, }, { 1, 7, 6, 6, 6, 6, 5, }, { 1, 7, 5, 5, 5, 3, 2, }, }, }; -static channel_precalc channel_precalcs8[] = { +static const struct channel_precalc channel_precalcs8[] = { { 119121, { 2, 1, 3, 2, 1, 3, 2, 1, }, { 1, 1, 1, 4, 3, 2, 1, 2, }, { 8, 7, 7, 5, 4, 4, 2, }, { 8, 8, 8, 8, 5, 3, 2, }, }, { 238242, { 2, 1, 1, 2, 2, 2, 1, 4, }, { 1, 1, 3, 1, 1, 2, 4, 2, }, { 8, 7, 7, 7, 6, 5, 4, }, { 8, 8, 8, 6, 6, 6, 5, }, }, { 357363, { 2, 2, 1, 4, 1, 1, 1, 3, }, { 1, 1, 1, 1, 3, 2, 5, 1, }, { 8, 7, 6, 6, 3, 3, 3, }, { 8, 8, 8, 8, 8, 6, 5, }, }, diff --git a/backend/output.c b/backend/output.c index 351b1acd..d5bdb666 100644 --- a/backend/output.c +++ b/backend/output.c @@ -957,7 +957,7 @@ static int out_maybe_mkdir(const char *path) { } /* Create output file, creating sub-directories if necessary. Returns `fopen()` FILE pointer */ -INTERNAL FILE *zint_out_fopen(const char filename[256], const char *mode) { +INTERNAL FILE *zint_out_fopen(char filename[256], const char *mode) { FILE *outfile; #ifdef _WIN32 @@ -968,12 +968,10 @@ INTERNAL FILE *zint_out_fopen(const char filename[256], const char *mode) { char dirname[256]; char *d; #ifdef _WIN32 - char *dirend = strrchr(filename, '\\'); - if (!dirend) { - dirend = strrchr(filename, '/'); - } + char *const dirend_backslash = strrchr(filename, '\\'); + char *const dirend = dirend_backslash ? dirend_backslash : strrchr(filename, '/'); #else - char *dirend = strrchr(filename, '/'); + char *const dirend = strrchr(filename, '/'); #endif if (!dirend) { return outfile; diff --git a/backend/output.h b/backend/output.h index 1f95e12b..012b4257 100644 --- a/backend/output.h +++ b/backend/output.h @@ -71,7 +71,7 @@ INTERNAL float zint_out_large_bar_height(struct zint_symbol *symbol, const int s int *symbol_height_si); /* Create output file, creating sub-directories if necessary. Returns `fopen()` FILE pointer */ -INTERNAL FILE *zint_out_fopen(const char filename[256], const char *mode); +INTERNAL FILE *zint_out_fopen(char filename[256], const char *mode); #ifdef _WIN32 /* Do `fopen()` on Windows, assuming `filename` is UTF-8 encoded. Props Marcel, ticket #288 */ diff --git a/backend/tests/testcommon.c b/backend/tests/testcommon.c index 8cfeb102..477343b4 100644 --- a/backend/tests/testcommon.c +++ b/backend/tests/testcommon.c @@ -2163,7 +2163,8 @@ int testUtilHaveLibreOffice(void) { int testUtilVerifyLibreOffice(const char *filename, int debug) { char cmd[512 + 128]; char svg[512]; - char *slash, *dot; + const char *slash; + char *dot; char buf[16384]; char *b = buf, *be = buf + sizeof(buf) - 1; FILE *fp; @@ -4347,7 +4348,7 @@ static int textUtilZXingCPPDX(const char *expected, const int expected_len, cons /* Helper to append add-on if any to EAN-13, returning expected length */ static int textUtilZXingCPPEAN13AddOn(const char *expected, const int expected_len, char *out) { - char *sep; + const char *sep; if ((sep = strchr(expected, '+')) != NULL || (sep = strchr(expected, ' ')) != NULL) { const int addon_len = expected_len - (int) (sep + 1 - expected); if (addon_len <= 2) { diff --git a/frontend/main.c b/frontend/main.c index 73cb7d54..0baf776c 100644 --- a/frontend/main.c +++ b/frontend/main.c @@ -736,8 +736,8 @@ static int supported_filetype(const char *const filetype, const int no_png, int } /* Get file extension, excluding those of more than 4 letters */ -static char *get_extension(const char *const file) { - char *const dot = strrchr(file, '.'); +static const char *get_extension(const char *const file) { + const char *const dot = strrchr(file, '.'); if (dot && strlen(file) - (dot - file) <= 5) { /* Only recognize up to 4 letter extensions */ return dot + 1; } @@ -755,7 +755,7 @@ static void set_extension(char file[256], const char *const filetype) { cpy_str(lc_filetype, ARRAY_SIZE(lc_filetype), filetype); to_lower(lc_filetype); - extension = get_extension(file); + extension = (char *) get_extension(file); if (extension) { cpy_str(lc_extension, ARRAY_SIZE(lc_extension), extension); to_lower(lc_extension); @@ -1517,7 +1517,7 @@ int main(int argc, char **argv) { int val; int i; int ret; - char *outfile_extension; + const char *outfile_extension; int data_arg_num = 0; int seg_count = 0; float x_dim_mm = 0.0f, dpmm = 0.0f; diff --git a/frontend_qt/mainwindow.cpp b/frontend_qt/mainwindow.cpp index 10eba0d9..d315a752 100644 --- a/frontend_qt/mainwindow.cpp +++ b/frontend_qt/mainwindow.cpp @@ -60,19 +60,22 @@ static const int tempMessageTimeout = 2000; +// Suppress gcc-16 (C23) warning -Wdeprecated-enum-enum-conversion +#define QKC(M, K) (int(M) | int(K)) + // Use on Windows also (i.e. not using QKeySequence::Quit) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, quitKeySeq, (Qt::CTRL | Qt::Key_Q)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, quitKeySeq, QKC(Qt::CTRL, Qt::Key_Q)) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, openCLISeq, (Qt::SHIFT | Qt::CTRL | Qt::Key_C)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, openCLISeq, QKC(Qt::SHIFT | Qt::CTRL, Qt::Key_C)) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyBMPSeq, (Qt::SHIFT | Qt::CTRL | Qt::Key_B)) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyEMFSeq, (Qt::SHIFT | Qt::CTRL | Qt::Key_E)) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyGIFSeq, (Qt::SHIFT | Qt::CTRL | Qt::Key_G)) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyPNGSeq, (Qt::SHIFT | Qt::CTRL | Qt::Key_P)) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copySVGSeq, (Qt::SHIFT | Qt::CTRL | Qt::Key_S)) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyTIFSeq, (Qt::SHIFT | Qt::CTRL | Qt::Key_T)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyBMPSeq, QKC(Qt::SHIFT | Qt::CTRL, Qt::Key_B)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyEMFSeq, QKC(Qt::SHIFT | Qt::CTRL, Qt::Key_E)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyGIFSeq, QKC(Qt::SHIFT | Qt::CTRL, Qt::Key_G)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyPNGSeq, QKC(Qt::SHIFT | Qt::CTRL, Qt::Key_P)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copySVGSeq, QKC(Qt::SHIFT | Qt::CTRL, Qt::Key_S)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, copyTIFSeq, QKC(Qt::SHIFT | Qt::CTRL, Qt::Key_T)) -Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, factoryResetSeq, (Qt::SHIFT | Qt::CTRL | Qt::Key_R)) +Q_GLOBAL_STATIC_WITH_ARGS(QKeySequence, factoryResetSeq, QKC(Qt::SHIFT | Qt::CTRL, Qt::Key_R)) // RGB hexadecimal 6 or 8 in length or CMYK comma-separated decimal percentages "C,M,Y,K" static const QString colorREstr(QSL("^([0-9A-Fa-f]{6}([0-9A-Fa-f]{2})?)|(((100|[0-9]{0,2}),){3}(100|[0-9]{0,2}))$"));