pycparser
pycparser copied to clipboard
Generator generates incorrect code for 1-line type aliases
The following code gets mis-generated & causes a compiler warning:
struct a {};
union {
struct a b;
} u, *uu = &u;
becomes
struct a;
union
{
struct a b;
} u;
union
{
struct a b;
} *uu = & u;
Snippet: import sys from pycparserext.ext_c_parser import GnuCParser as CParser from pycparserext.ext_c_generator import GnuCGenerator as CGenerator
source_parser = CParser()
ast = source_parser.parse(sys.stdin.read())
generator = CGenerator()
print generator.visit(ast)
The problem with this is that if you try to compile this code the compiler will generate a warning that the variable uu is initialized from an incompatible pointer type because we've now generated 2 anonymous union names.
This is probably related (same root cause?) with structure aliases getting their own types too:
typedef struct
{
int a;
} B, C;
becomes:
typedef struct
{
int a;
} B;
typedef struct
{
int a;
} C;
which means that B & C are their own types instead of aliases to the same underlying type.
Thanks for the report; I don't have an objection to fixing this, though it may turn out to be a bit tricky since the parser will create different AST entries.
PRs welcome
Are empty structs valid in C99? I thought not, despite many compilers accepting them. For me, pycparserext (I believe correctly) rejects this as a parse error. Not really the core of this issue, but just nitpicking the reproducer. The issue is reproducible without an empty struct:
struct a { int x; };
union {
struct a b;
} u, *uu = &u;
becomes
struct a
{
int x;
};
union
{
struct a b;
} u;
union
{
struct a b;
} *uu = & u;
In this case you get a valid struct definition, as opposed to the original example that emitted something that looked like a forward declaration of the struct.
This issue also causes errors when using a named struct
in the typedef
.
For example:
typedef struct MyStruct {
int a;
} myType, *pMyType;
compiles fine, but once once transformed to
typedef struct MyStruct {
int a;
} myType;
typedef struct MyStruct {
int a;
} *pMyType;
causes a compilation error:
error: redefinition of MyStruct
I'm a bit confused, as the code piece
typedef struct MyStruct {
int a;
} myType, *pMyType;
doesn't compile either on my gcc(Apple clang), with command gcc -std=c99
, and the error is also redefinition.
Thus it's just working perfectly on this named struct example, isn't it?