NRK - 2022-01-01

Hi,

I believe having a check for detecting non-portable constant expression would be a useful addition to cppcheck. For example:

static const char a1 = 'a';
static const char a2 = a1;

Will compile under both GCC and Clang without any warnings (even with -std=c89 -Wpedantic) but will straight up fail to compile under smaller compilers such as TCC.

This is because the C standard specifies that the initializer element of an object of static storage duration must be a constant expression, however it also specifies that implementations are allowed to pick their own form of constant expression.

It would be nice if cppcheck can detect usage of constant expression which are not explicitly defined in the C standard under it's portability checks. Here's a couple more examples:

const int i1 = 5 + sizeof(i1); /* fine */
int i2 = i1; /* error */

const char s[] = "ok";
const char *const s2 = "ok";
const char *const p = s; /* fine */
const char *p2 = s2; /* error */
const char *p3 = p; /* error */
const char *const *p4 = &p; /* fine */

struct MyStruct { const char *s; int b; };

const struct MyStruct my_struct1 = { s, 5 };  /* fine */
const struct MyStruct my_struct2 = { s, i1 }; /* error */
struct MyStruct my_struct_array[] = {
    { "ok", 5 }, /* fine */
    my_struct1,  /* error: clang(v13) errors on this, gcc(v11.2) compiles however */
    my_struct2,  /* error: same as above */
    { s, 5 }     /* fine */
};

int main(void) { return 0; }