From patchwork Mon Jan 10 18:45:29 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Subject: [trans-mem] error on inlined asms From: Aldy Hernandez X-Patchwork-Id: 78192 Message-Id: <4D2B53C9.5080201@redhat.com> To: gcc-patches@gcc.gnu.org, Richard Henderson Date: Mon, 10 Jan 2011 12:45:29 -0600 In the following test, we correctly error at -O0 because inline_death() has an unsafe construct and is being called from an atomic transaction. This error is triggered at ipa_tm_diagnose_transaction() because the diagnostic machinery (diagnose_tm*) has marked inline_death() as possibly entering irrevocable mode. However, at any optimization level, we don't error because we no longer have an irrevocable function call, instead the ASM has been inlined into the transaction. Since the asm complaining code gets run before inlining (diagnose_tm*), we don't notice the asm that ends up inside the transaction. static inline void inline_death () { __asm__ (""); } void tranfunction () { __transaction { inline_death (); } } My fix is to notice ASMs that have been inlined into transactions at IPA time, since we're iterating over the transaction code anyhow. OK for branch? * trans-mem.c (ipa_tm_diagnose_transaction): Do not allow asms in atomic transactions. Index: testsuite/c-c++-common/tm/inline-asm.c =================================================================== --- testsuite/c-c++-common/tm/inline-asm.c (revision 0) +++ testsuite/c-c++-common/tm/inline-asm.c (revision 0) @@ -0,0 +1,17 @@ +/* { dg-do compile } */ +/* { dg-options "-fgnu-tm -O1" } */ + +static inline void +inline_death () +{ + __asm__ (""); /* { dg-error "asm not allowed" } */ +} + +void +tranfunction () +{ + __transaction + { + inline_death (); + } +} Index: trans-mem.c =================================================================== --- trans-mem.c (revision 168123) +++ trans-mem.c (working copy) @@ -3929,6 +3929,13 @@ ipa_tm_diagnose_transaction (struct cgra gimple stmt = gsi_stmt (gsi); tree fndecl; + if (gimple_code (stmt) == GIMPLE_ASM) + { + error_at (gimple_location (stmt), + "asm not allowed in atomic transaction"); + continue; + } + if (!is_gimple_call (stmt)) continue; fndecl = gimple_call_fndecl (stmt);