From patchwork Thu Nov 18 16:25:55 2010 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Alexander Monakov X-Patchwork-Id: 72117 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) by ozlabs.org (Postfix) with SMTP id 596A9B719D for ; Fri, 19 Nov 2010 03:26:08 +1100 (EST) Received: (qmail 7283 invoked by alias); 18 Nov 2010 16:26:05 -0000 Received: (qmail 7271 invoked by uid 22791); 18 Nov 2010 16:26:04 -0000 X-SWARE-Spam-Status: No, hits=-1.9 required=5.0 tests=AWL, BAYES_00, FSL_RU_URL, TW_KC, T_RP_MATCHES_RCVD X-Spam-Check-By: sourceware.org Received: from smtp.ispras.ru (HELO smtp.ispras.ru) (83.149.198.201) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Thu, 18 Nov 2010 16:25:58 +0000 Received: from ispserv.ispras.ru (ispserv.ispras.ru [83.149.198.72]) by smtp.ispras.ru (Postfix) with ESMTP id 61F0C5D40DB for ; Thu, 18 Nov 2010 19:21:46 +0300 (MSK) Received: from monoid.intra.ispras.ru (winnie.ispras.ru [83.149.198.236]) by ispserv.ispras.ru (Postfix) with ESMTP id BC5BC3FC48 for ; Thu, 18 Nov 2010 19:25:55 +0300 (MSK) Date: Thu, 18 Nov 2010 19:25:55 +0300 (MSK) From: Alexander Monakov To: gcc-patches@gcc.gnu.org Subject: [PR45652] sel-sched: don't rename into regs with non-null REG_BASE_VALUE Message-ID: User-Agent: Alpine 2.00 (LNX 1167 2008-08-23) MIME-Version: 1.0 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Hi, Register renaming in selective scheduler may affect alias information because a part of it is tied to registers (as opposed to MEMs) via REG_BASE_VALUE. We cannot update it on the fly, because it would invalidate all computed availability sets. Therefore, we have to avoid using registers with non-null REG_BASE_VALUE for renaming. The following patch implements that. It only affects renaming of hard registers (before reload, we would use a fresh pseudo for renaming). I think the biggest impact is that we will not be able to use registers that can hold incoming arguments and are not assigned somewhere in the function. However, on ia64 the total amount of renaming in spec 2k6 is the same with the patch, with +1/-1 differences on a couple of files (i.e. we almost always can pick another register). Bootstrapped on ia64-linux with sel-sched enabled for -O2, regtest is in progress. OK if that passes? 2010-11-18 Alexander Monakov PR rtl-optimization/45652 * alias.c (get_reg_base_value): New. * rtl.h (get_reg_base_value): Add prototype. * sel-sched.c (init_regs_for_mode): Use it. Don't use registers with non-null REG_BASE_VALUE for renaming. testsuite: * gcc.dg/pr45652.c: New. diff --git a/gcc/alias.c b/gcc/alias.c index 2e0ac06..e8c01b4 100644 --- a/gcc/alias.c +++ b/gcc/alias.c @@ -1291,6 +1291,14 @@ record_set (rtx dest, const_rtx set, void *data ATTRIBUTE_UNUSED) reg_seen[regno] = 1; } +/* Return REG_BASE_VALUE for REGNO. Selective scheduler uses this to avoid + using hard registers with non-null REG_BASE_VALUE for renaming. */ +rtx +get_reg_base_value (unsigned int regno) +{ + return VEC_index (rtx, reg_base_value, regno); +} + /* If a value is known for REGNO, return it. */ rtx diff --git a/gcc/rtl.h b/gcc/rtl.h index 3e1df2c..22721a2 100644 --- a/gcc/rtl.h +++ b/gcc/rtl.h @@ -2508,6 +2508,7 @@ extern rtx find_base_term (rtx); extern rtx gen_hard_reg_clobber (enum machine_mode, unsigned int); extern rtx get_reg_known_value (unsigned int); extern bool get_reg_known_equiv_p (unsigned int); +extern rtx get_reg_base_value (unsigned int); #ifdef STACK_REGS extern int stack_regs_mentioned (const_rtx insn); diff --git a/gcc/sel-sched.c b/gcc/sel-sched.c index 70e831d..83d8c23 100644 --- a/gcc/sel-sched.c +++ b/gcc/sel-sched.c @@ -1139,6 +1139,9 @@ init_regs_for_mode (enum machine_mode mode) /* Can't use regs which aren't saved by the prologue. */ || !TEST_HARD_REG_BIT (sel_hrd.regs_ever_used, cur_reg + i) + /* Can't use regs with non-null REG_BASE_VALUE, because adjusting + it affects aliasing globally and invalidates all AV sets. */ + || get_reg_base_value (cur_reg + i) #ifdef LEAF_REGISTERS /* We can't use a non-leaf register if we're in a leaf function. */ diff --git a/gcc/testsuite/gcc.dg/pr45652.c b/gcc/testsuite/gcc.dg/pr45652.c new file mode 100644 index 0000000..8f55f0c --- /dev/null +++ b/gcc/testsuite/gcc.dg/pr45652.c @@ -0,0 +1,39 @@ +/* { dg-do run { target powerpc*-*-* ia64-*-* x86_64-*-* } } */ +/* { dg-options "-O2 -fselective-scheduling2" } */ + +struct S { + double i[2]; +}; + +void __attribute__ ((noinline)) checkcd (struct S x) +{ + if (x.i[0] != 7.0 || x.i[1] != 8.0) + __builtin_abort (); +} + +void __attribute__ ((noinline)) testvacd (int n, ...) +{ + int i; + __builtin_va_list ap; + __builtin_va_start (ap, n); + for (i = 0; i < n; i++) + { + struct S t = __builtin_va_arg (ap, struct S); + checkcd (t); + } + __builtin_va_end (ap); +} + +void +testitcd (void) +{ + struct S x = { { 7.0, 8.0 } }; + testvacd (2, x, x); +} + +int +main () +{ + testitcd (); + return 0; +}