5

I'm trying to understand the use of the "static" keyword as an array index in a function declaration in C.

After reading this article, I tried to declare such a function, and purposefully passing it an array that is too short:

#include <stdio.h>
#include <stdlib.h>
void print_string10(char string10[static 10]) {
// Should trigger a warning if the argument is NULL or an array of less than 10 elements
 printf("%s\n",string10);
}
int main(void) {
 char short_string[] = "test";
 print_string10(short_string); // should trigger a warning as the string is 5 long
 return EXIT_SUCCESS;
}

Compiling with clang as in the article triggers the warning, but gcc -Wall -Werror does not, it compiles and run fine.

I couldn't find an explanation, is that a normal behaviour for GCC to omit this warning?

melpomene
86.2k8 gold badges95 silver badges154 bronze badges
asked Dec 28, 2018 at 14:11
3
  • 1
    Which versoin of GCC do you have? Do you pass any other options or flags when building? Commented Dec 28, 2018 at 14:16
  • 4
    It seems that none of the messages are required. The compiler can just ignore the keyword there. Commented Dec 28, 2018 at 14:18
  • I'm using gcc 6.3.0, with only -Wall -Werror. Commented Dec 28, 2018 at 15:20

2 Answers 2

5

It looks like this is a bug in GCC. It seems there were some disagreements regarding whether or not this should be reported at compile time. Nonetheless, it was accepted as a bug but there doesn't seem to be a priority on fixing it.

This is detailed in bug report 50584. Comment 9 in particular states:

(In reply to Malcolm Inglis from comment #4)

Could someone change the status of this bug?

Notwithstanding whether the feature is pretty or ugly, GCC does accept this code and warnings for undefined behavior, when possible, are desired. Thus, confirmed.

This does not mean anyone is going to work on fixing this. Please, if you are using this feature and would like to see this warning in GCC, please consider contributing it: https://gcc.gnu.org/wiki/GettingStarted#Basics:_Contributing_to_GCC_in_10_easy_steps

If you start working on this, it would be good to say so here.

answered Dec 28, 2018 at 14:19
Sign up to request clarification or add additional context in comments.

1 Comment

We should note it is a bug in that GCC does not conform to the behavior desired by its maintainers/contributors/supplicants, not that it is a bug in that GCC does not conform to the C standard.
5

Why it does not need to trigger a warning is because of the section of the standard where it occurs - 6.7.6.3p7:

Semantics

[...]

  1. A declaration of a parameter as ''array of type'' shall be adjusted to ''qualified pointer to type'', where the type qualifiers (if any) are those specified within the [ and ] of the array type derivation. If the keyword static also appears within the [ and ] of the array type derivation, then for each call to the function, the value of the corresponding actual argument shall provide access to the first element of an array with at least as many elements as specified by the size expression.

It appears in the semantics section. A conforming implementation is only required to diagnose those that appear in the constraints. Even when it does not diagnose the violation here, it can use the knowledge of the static keyword to infer that the argument is not null, and that loop unrolling and other optimizations could expect an array that would have at least that many elements.


Do also note, that the example 5 there says that

 void f(double (* restrict a)[5]);
 void f(double a[restrict][5]);
 void f(double a[restrict 3][5]);
 void f(double a[restrict static 3][5]);

are all compatible, i.e. you can mix and match them in function pointer assignments without casts even though one has the static dimension!

It seems that clang (perhaps rightly so) loses its ability to diagnose anything if the call is realized through a function pointer:

void (*f)(double a[restrict static 3]);
int main(void) {
 double a[1] = {0};
 f(a);
}

(no diagnostics in Clang 7.0 - remove the * and you will get them).

answered Dec 28, 2018 at 14:35

4 Comments

Thanks for the detailed answer. In the link to the gcc bug tracker provided by dbush, someone states : "I don't recommend this kind of usage of the static keyword. There was even the possibility of removing/deprecating this feature.[...]" Does anyone agree with this ? What should be used instead ?
@SuperBoby the DR205 complains about the use of the static keyword, not that the feature would be bad. It exists in 99, 11 and 17 revisions, it is not going away any time soon, so it should be supported by GCC right now to the fullest extent instead of only providing alternative mechanisms.
@SuperBoby furthermore the problem with the use of static is that it works only in function parameters, whereas some other mechanism might work everywhere where a pointer is needed
In what other case would you need to restrict an array size like this ?

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.