clangupc / clang-upc

Clang UPC Front-End
https://clangupc.github.io/
Other
17 stars 5 forks source link

Upc2c issue 52 #30

Closed PHHargrove closed 10 years ago

PHHargrove commented 10 years ago

Please consider this replacement implementation of StmtPrinter::VisitImplicitValueInitExpr() which resolves issue #52 in the upc2c tracker.

-Paul

PHHargrove commented 10 years ago

Please HOLD OFF on this pull request. I am getting crashes in upc2c on the bug858a.c testcase that are not present w/o my changes.

PHHargrove commented 10 years ago

The following is sufficient to trigger the crash:

int main(void) {
    typedef char type_f2 [6];
    type_f2 f2[3] = { [1] = {[2] = 3,4} };
}
PHHargrove commented 10 years ago

The crash has been fixed by my latest commit. The issue was typedef'ed array types. Please resume consideration of this pull request.

swatanabe commented 10 years ago
[steven@localhost ~]$ cat test.upc
struct X { } arr[2] = { [1] = {} };
[steven@localhost ~]$ intrepid/build/bin/upc2c test.upc 
Segmentation fault (core dumped)

Note that the berkeley translator rejects this code, saying

Error during remote HTTP translation:
upcc: error during UPC-to-C translation (sgiupc stage): 
/tmp/web-trans-S3YD0q.upc:1: Incomplete or unknown type: X
PHHargrove commented 10 years ago

Steve,

Was that crash w/ or w/o my changes applied?

Reminder that '{}' as an initializer-list is NOT valid ISO C99 (even if the empty struct is, which I am uncertain of):

$ gcc -std=c99 -pedantic -c test.c
test.c:1:8: warning: struct has no members [-pedantic]
test.c:1:31: warning: ISO C forbids empty initializer braces [-pedantic]

Of course, regardless of the legality of the code, no input should crash the compiler. I will determine if my version of the code produces this SEGV and fix if so.

swatanabe commented 10 years ago

This is with your changes. The problem is in accessing the first member which doesn't exist for an empty struct.

PHHargrove commented 10 years ago

This is with your changes. The problem is in accessing the first member which doesn't exist for an empty struct.

Right, thanks. Not sure if I can fix today but I will take responsibility for this.

FWIW: I am not sure there exists a portable initiailizer-list for an empty struct. So, there may be no choice but to emit the non-portable "{}" for this case (and only this one).

-Paul

swatanabe commented 10 years ago

On 02/21/2014 03:30 PM, Paul H. Hargrove wrote:

FWIW: I am not sure there exists a portable initiailizer-list for an empty struct. So, there may be no choice but to emit the non-portable "{}" for this case (and only this one).

Agree, with the addition of zero-size arrays, which clang also accepts.

PHHargrove commented 10 years ago

C99 doesn't allow an empty structure.

Quoting from ISO C99 6.7.2.1 (Structure and union specifiers), Semantics paragraph 7:

... The struct-declaration-list is a sequence of declarations for the members of the structure or union. If the struct-declaration-list contains no named members, the behavior is undefined. ...

Gcc documents empty structs as an extension: http://gcc.gnu.org/onlinedocs/gcc/Empty-Structures.html

So, I'll output the non-portable "{}" for this case, instead of crashing.

If there is a consensus to make empty-structs an error that should probably be done prior to upc2c.

PHHargrove commented 10 years ago

I have the empty struct under control (emit '{}' instead of crashing). Will push to by branch after removing my debug output.

The empty array case seems to hit a different bug:

$ cat t2.c
typedef int Z_t[0];
Z_t arr[2] = { [1] = {} };
$ ./bin/clang -c t2.c && echo OK - No error || echo Non-zero exit
OK - No error
$ ./bin/clangupc -x upc -c t2.c && echo OK - No error || echo Non-zero exit
OK - No error
$ ./bin/upc2c t2.c && echo OK - No error || echo Non-zero exit
error: initializer for aggregate with no elements requires explicit braces
1 error generated.
Non-zero exit
swatanabe commented 10 years ago

On 02/21/2014 04:20 PM, Paul H. Hargrove wrote:

The empty array case seems to hit a different bug:

error: initializer for aggregate with no elements requires explicit braces
1 error generated.

I didn't get that. What I used was

struct X { int arr[0]; } test[2] = { [1] = {} };

which becomes:

struct X { int arr[0]; } test[2] = { /implicit/{{0}}, { } };

which gives me:

[steven@localhost ~]$ gcc test.c -c test.c:3:1: warning: excess elements in array initializer [enabled by default] } test[2] = { /implicit/{{0}}, { } }; ^

In Christ, Steven Watanabe

PHHargrove commented 10 years ago

I wrote:

The empty array case seems to hit a different bug

And that issue is present on the master branch too - not my fault. Will investigate later and open a new issue if it seems appropriate to do so. In the meantime I don't even know what the AST will look like for that code

Steve provided a different example: a struct containing an empty array (vs. my array of empty arrays). I will attack that case now...