From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 9910 invoked by alias); 31 Aug 2004 13:57:14 -0000 Mailing-List: contact gcc-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Archive: List-Post: List-Help: Sender: gcc-owner@gcc.gnu.org Received: (qmail 9883 invoked from network); 31 Aug 2004 13:57:12 -0000 Received: from unknown (HELO atrey.karlin.mff.cuni.cz) (195.113.31.123) by sourceware.org with SMTP; 31 Aug 2004 13:57:12 -0000 Received: by atrey.karlin.mff.cuni.cz (Postfix, from userid 29025) id EC40D4B42EA; Tue, 31 Aug 2004 15:57:11 +0200 (CEST) Date: Tue, 31 Aug 2004 14:48:00 -0000 From: Zdenek Dvorak To: Steven Bosscher Cc: gcc@gcc.gnu.org Subject: Re: On -ftrapv vs. libcalls... Message-ID: <20040831135711.GA19870@atrey.karlin.mff.cuni.cz> References: <200408221254.28457.stevenb@suse.de> Mime-Version: 1.0 Content-Type: text/plain; charset=us-ascii Content-Disposition: inline In-Reply-To: <200408221254.28457.stevenb@suse.de> User-Agent: Mutt/1.5.6i X-SW-Source: 2004-08/txt/msg01625.txt.bz2 Hello, > Could anyone please help me get some insight into the following > problem. > > Consider, > > int > mulv(int a, int b) > { > return a * b; > } > > compiled with -ftrapv. This gives the following code in the .rtl dump > on ia64. > > (insn 18 17 19 1 (set (reg:DI 120 out0) > (reg:DI 345)) -1 (nil) > (insn_list:REG_LIBCALL 21 (nil))) > > (insn 19 18 20 1 (set (reg:DI 121 out1) > (reg:DI 347)) -1 (nil) > (nil)) > > (call_insn/u 20 19 21 1 (parallel [ > (set (reg:DI 8 r8) > (call (mem:DI (symbol_ref:DI ("__mulvdi3") [flags 0x41]) [0 S8 A64]) > (const_int 1 [0x1]))) > (clobber (reg:DI 320 b0)) > (clobber (scratch:DI)) > (clobber (scratch:DI)) > ]) -1 (nil) > (expr_list:REG_EH_REGION (const_int -1 [0xffffffffffffffff]) > (nil)) > (expr_list (use (reg:DI 1 r1)) > (expr_list (use (reg:DI 121 out1)) > (expr_list (use (reg:DI 120 out0)) > (nil))))) > > (insn 21 20 22 1 (set (reg:DI 349) > (reg:DI 8 r8)) -1 (nil) > (insn_list:REG_RETVAL 18 (expr_list:REG_EQUAL (mult:DI (reg:DI 345) > (reg:DI 347)) > (nil)))) > > > Note the __mulvdi3 libcall. At the first opportunity to do so, the > first jump pass, we collapse it to a normal MULT insn: > > (insn 16 15 17 0 (set (reg:SI 348 [ b ]) > (mem/i:SI (reg/f:DI 344) [0 b+0 S4 A32])) -1 (nil) > (nil)) > > (insn 17 16 21 0 (set (reg:DI 347 [ b ]) > (sign_extend:DI (reg:SI 348 [ b ]))) -1 (nil) > (nil)) > > (insn 21 17 22 0 (set (reg:DI 349) > (mult:DI (reg:DI 345 [ a ]) > (reg:DI 347 [ b ]))) 105 {muldi3} (nil) > (nil)) > (insn 22 21 23 0 (set (reg:SI 339 [ T.0 ]) > (subreg:SI (reg:DI 349) 0)) -1 (nil) > (nil)) > > [ this also happens on x86 and amd64, but there the problem is not > as obvious - apparently ia64 doesn't even have that function in > libgcc so it causes a link failure without libcall notes. ] > > Without -ftrapv we never emit it, we just always generate a normal > MULT insn, never the libcall: > > (insn 14 13 15 1 (set (reg:SI 345) > (mem/i:SI (reg/f:DI 335 virtual-stack-vars) [0 a+0 S4 A32])) -1 (nil) > (nil)) > > (insn 15 14 16 1 (set (reg:SI 346) > (mem/i:SI (reg/f:DI 344) [0 b+0 S4 A32])) -1 (nil) > (nil)) > > (insn 16 15 17 1 (set (reg:SI 339 [ T.0 ]) > (mult:SI (reg:SI 345) > (reg:SI 346))) -1 (nil) > (nil)) > > I'm trying to get rid of libcall notes, so I would really like to know > and understand why we emit a libcall with -ftrapv. With my patch, we > cannot fold the libcall anymore, so it's a show stopper for removing > libcalls that we emit the (apparently?) unnecessary libcall. > > Is there a way to avoid emiting a libcall in this case? > > Not emitting the libcall would be good in any case since it would > improve the initially generated RTL with -ftrapv... my understanding is that with -ftrapv we call the library function that causes trap on overflow -- on rtl we no longer know whether the operands of multiplication are unsigned or not, so we cannot emit MULT for it. What I do not understand is why it is legal to turn the libcall back into MULT. Zdenek