thorinn@DIKU.DK (Lars Henrik Mathiesen) (09/12/89)
Viz. skinfaxe% cat tst.c main() { unsigned char c; int i; for (i = 127; i < 130; i++) switch(c = i) { case 127: case 128: case 129: printf("%d\n", c); break; default: printf("default %d\n", c); } } skinfaxe% gcc -v -dr -O -traditional -o tst tst.c gcc version 1.35 /usr/lib/gnu/gcc-cpp -v -undef -D__GNUC__ -Dsparc -Dsun -Dunix -D__sparc__ -D__sun__ -D__unix__ -D__OPTIMIZE__ -traditional tst.c /tmp/cca01424.cpp GNU CPP version 1.35 /usr/lib/gnu/gcc-cc1 /tmp/cca01424.cpp -quiet -dumpbase tst.c -dr -O -traditional -version -o /tmp/cca01424.s GNU C version 1.35 (sparc) compiled by GNU C version 1.35. as -o tst.o /tmp/cca01424.s ld -o tst -e start -dc -dp /lib/crt0.o tst.o /usr/lib/gnu/gcc-gnulib -lc skinfaxe% tst 127 default 128 default 129 skinfaxe% cat tst.c.rtl ;; Function main (note 1 0 2 "" NOTE_INSN_DELETED) (note 2 1 3 "" NOTE_INSN_BLOCK_BEG) (insn 3 2 4 (set (reg/v:SI 65) (const_int 127)) -1 (nil) (nil)) (note 4 3 46 "" NOTE_INSN_LOOP_BEG) (jump_insn 46 4 47 (set (pc) (label_ref 5)) -1 (nil) (nil)) (barrier 47 46 45) (code_label 45 47 8 11) (note 8 45 30 "" NOTE_INSN_DELETED) (insn 30 8 31 (set (reg/v:QI 64) (subreg:QI (reg/v:SI 65) 0)) -1 (nil) (nil)) (insn 31 30 32 (set (reg:SI 68) (sign_extend:SI (reg/v:QI 64))) -1 (nil) (nil)) (insn 32 31 33 (set (reg:SI 69) (const_int 129)) -1 (nil) (nil)) (insn 33 32 34 (set (cc0) (compare (reg:SI 68) (reg:SI 69))) -1 (nil) (nil)) (jump_insn 34 33 35 (set (pc) (if_then_else (gtu (cc0) (const_int 0)) (label_ref 22) (pc))) -1 (nil) (nil)) (insn 35 34 36 (set (reg:SI 70) (sign_extend:SI (reg/v:QI 64))) -1 (nil) (nil)) (insn 36 35 37 (set (reg:SI 71) (const_int 127)) -1 (nil) (nil)) (insn 37 36 38 (set (cc0) (compare (reg:SI 70) (reg:SI 71))) -1 (nil) (nil)) (jump_insn 38 37 39 (set (pc) (if_then_else (geu (cc0) (const_int 0)) (label_ref 10) (pc))) -1 (nil) (nil)) (jump_insn 39 38 40 (set (pc) (label_ref 22)) -1 (nil) (nil)) (barrier 40 39 9) . . . . skinfaxe% As seen in insns 31 and 35, a sign-extend is generated for the switch value, even though it is unsigned. This only happens when -traditional is used. The problem seems to be in stmt.c, function emit_case_nodes(). For a single-valued case the parameter unsignedp is transmitted to emit_cmp_insn() through the call of do_jump_if_equal(). For case ranges emit_cmp_insn() is called directly with an argument of 0. I don't understand the type system well enough to be sure that `fixing' this is safe, but it sure looks like it needs fixing. -- Lars Mathiesen, DIKU, U of Copenhagen, Denmark [uunet!]mcvax!diku!thorinn Institute of Datalogy -- we're scientists, not engineers. thorinn@diku.dk