Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Aren't a[][] and (*a)[] equivalent as function parameters?

Function prototype

void foo(int n, int a[][]);

gives error about incomplete type while

void foo(int n, int (*a)[]);  

compiles. As per the decay rule int a[][] is equivalent to int (*a)[] in this case and therefore int (*a)[] should also give an error about an incomplete type but GCC seems to accept it. Is there anything I am missing? This might be a GCC bug but I didn't find anything related to it.

like image 263
haccks Avatar asked Jun 20 '17 14:06

haccks


1 Answers

No, they are not equivalent as function parameters. They are not equivalent in exactly the same way as parameter declarations in foo and bar

struct S;
void foo(struct S* s); // OK
void bar(struct S a[]); // ERROR: incomplete type is not allowed

are not equivalent.

C does not allow incomplete types as array elements (see C 1999 6.7.5.2/1: "[...] The element type shall not be an incomplete or function type. [...]") and this restriction applies to array parameter declarations the same way as it applies to any other array declarations. Even though parameters of array type will be later implicitly adjusted to pointer type, C simply provides no special treatment for array declarations in function parameter lists. In other words, array parameter declarations are checked for validity before the aforementioned adjustment.

Your int a[][] is the same thing: an attempt to declare an array with elements of type int [], which is an incomplete type. Meanwhile, int (*a)[] is perfectly legal - there's nothing unusual about pointers to incomplete types.

As a side note, C++ "fixed" this issue, allowing arrays of incomplete type in parameter declarations. However, the original C++ still prohibits int a[][] parameters, int (&a)[] parameters and even int (*a)[] parameters. This was supposedly fixed/allowed later in C++17 (http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#393)

like image 100
AnT Avatar answered Sep 22 '22 23:09

AnT