The following code snippet will cause an ICE within the compiler. This occurred with GDC 4.8 head as of October 4th. ==== struct a { char[1] b; } a c; void main() { pragma(msg, typeof(*c.b.ptr)); pragma(msg, typeof(c.b.ptr)); pragma(msg, typeof(c.b)); if (*c.b.ptr) return; return; } ==== The type used by GCC for *c.b.ptr is char[1LU] when it should be char as reported by D's type system. $ gdc test.d char char* char[1LU] test.d: In function ‘D main’: test.d:8: error: mismatching comparison operand types char[1] int if (D.2039 != 0) goto <D.2040>; else goto <D.2041>; test.d:8: internal compiler error: verify_gimple failed 0x98f4af verify_gimple_in_seq(gimple_statement_d*) ../../gcc-4.8-20121007/gcc/tree-cfg.c:4531 0x828cb4 gimplify_body(tree_node*, bool) ../../gcc-4.8-20121007/gcc/gimplify.c:8232 0x829005 gimplify_function_tree(tree_node*) ../../gcc-4.8-20121007/gcc/gimplify.c:8319 0x6d1147 cgraph_analyze_function ../../gcc-4.8-20121007/gcc/cgraphunit.c:643 0x6d3f8e cgraph_analyze_functions ../../gcc-4.8-20121007/gcc/cgraphunit.c:928 0x6d4e50 finalize_compilation_unit() ../../gcc-4.8-20121007/gcc/cgraphunit.c:2071 0x61c704 d_write_global_declarations ../../gcc-4.8-20121007/gcc/d/d-lang.cc:643 Please submit a full bug report, with preprocessed source if appropriate. Please include the complete backtrace with any bug report. See <http://gcc.gnu.org/bugs.html> for instructions.
This is a bug in the frontend. It should not be generating code like this: ==== if (c.b) { .... } Where the condition is a non-scalar type.
When dealing with "if (c.b)" GDC does the correct thing and throws an error. In this case b is of type char[1] and we're taking the pointer using .ptr . The type then becomes char*. After which we dereference it into what should be a 'char' a valid scalar. However, GDC returns the original type char[1]. Which is what generates the error shown. To help contrast this, if we remove the struct and do === char[1] d; void main() { if (*d.ptr) return; return; } It compiles without an error even though it should be equivalent to the previous operation. Derefencing a pointer of static char[1].
(In reply to comment #2) > When dealing with "if (c.b)" GDC does the correct thing and throws an error. > > In this case b is of type char[1] and we're taking the pointer using .ptr . > The type then becomes char*. After which we dereference it into what should be > a 'char' a valid scalar. > > However, GDC returns the original type char[1]. Which is what generates the > error shown. > > To help contrast this, if we remove the struct and do > > === > > char[1] d; > > void main() > { > if (*d.ptr) return; > return; > } > > It compiles without an error even though it should be equivalent to the > previous operation. Derefencing a pointer of static char[1]. That's because: *d.ptr Becomes: PtrExp (SymOffExp (d)) And: *c.b.ptr Becomes: PtrExp (AddrExp (c.b)) It is the later that suffers this bug, see PtrExp::optimize. http://d.puremagic.com/issues/show_bug.cgi?id=8913
https://github.com/D-Programming-Language/dmd/pull/1382
Can we close this?
Fixed with recent frontend merge.