> > This works fine on gcc 3.4, however on gcc 4.0 it creates an error during > optimization. According to my investigation, the error occurs when there is a > division by a constant power of 2 which needs to be transformed into > shifting. > The error generated is: > > internal compiler error: in emit_cmp_and_jump_insn_1, at optabs.c:3599 >
The easiest thing to do is to debug gcc: set a breakpoint on fancy_abort, and and go up a few levels to emit_cmp_and_jump_insn_1(). Note the incoming rtx args (x and y) and mode. From the looks of the code in there it is looking for an instruction pattern that matches, and when no match is found, it tries a wider mode, until there are no wider modes, then it aborts. You need to find the mode and rtx arguments that are being passed in, and then understand why no matching instruction is found. For example, in your instruction pattern, (define_insn "cbranchsi4" [(set (pc) (if_then_else (match_operator 0 "comparison_operator" [(match_operand:SI 1 "register_operand" "r") (match_operand:SI 2 "nonmemory_operand" "r")]) (label_ref (match_operand 3 "" "")) (pc)))] "" "c%C0jump %1 %2 %3" [(set_attr "type" "branch") (set_attr "length" "1")] ) it isn't prepared to match a memory operand. Perhaps the optimizer pre-calculated a constant, and targeted the constant into memory rather than a register? In that case, there will be no match on the third argument because it is expecting a "nonmemoryoperand".