Date: Thu, 15 Sep 1994 18:57:02 +0800 From: pierre AT phi DOT la DOT tce DOT com (Pierre Willard) To: bug-gcc AT prep DOT ai DOT mit DOT edu, djgpp-announce AT sun DOT soe DOT clarkson DOT edu Subject: bug division in gcc-2.6.0 expmed.c Reply-To: pierre AT la DOT tce DOT com gcc-2.6.0 generates bad code for some division operations. Around line 2865 of expmed.c, there is the following code : rtx t1, t2, t3; t1 = expand_shift (RSHIFT_EXPR, compute_mode, op0, build_int_2 (size - 1, 0), NULL_RTX, 0); t2 = expand_shift (RSHIFT_EXPR, compute_mode, t1, build_int_2 (size - lgup, 0), NULL_RTX, 1); t3 = force_operand (gen_rtx (PLUS, compute_mode, op0, t2), This is intended to do a signed division by a power of 2. The bug is that in the first expand_shift, the shift count has to be (lgup -1) and not (size - 1). I checked in gcc-2.5.8, the code was correct. So the above code should be : rtx t1, t2, t3; t1 = expand_shift (RSHIFT_EXPR, compute_mode, op0, build_int_2 (lgup - 1, 0), NULL_RTX, 0); t2 = expand_shift (RSHIFT_EXPR, compute_mode, t1, build_int_2 (size - lgup, 0), NULL_RTX, 1); t3 = force_operand (gen_rtx (PLUS, compute_mode, op0, t2), In gcc-2.5.8, there is this useful comment (lost in gcc-2.6.0) : /* Here we need to add OP1-1 if OP0 is negative, 0 otherwise. This can be computed without jumps by arithmetically shifting OP0 right LOG-1 places and then shifting right logically SIZE-LOG bits. The resulting value is unconditionally added to OP0. Let me know your comments. Thanks Pierre Willard