From 22bf03adcd87d035bbd9b581693050842a096e77 Mon Sep 17 00:00:00 2001 From: jamborm Date: Thu, 3 Nov 2011 13:53:29 +0000 Subject: 2011-11-03 Martin Jambor * ipa-prop.c (type_change_info): New fields offset, object, known_current_type and multiple_types_encountered. (extr_type_from_vtbl_ptr_store): New function. (check_stmt_for_type_change): Use it, set multiple_types_encountered if the result is different from the previous one. (detect_type_change): Renamed to detect_type_change_1. New parameter comp_type. Set up new fields in tci, build known type jump functions if the new type can be identified. (detect_type_change): New function. * tree.h (DECL_CONTEXT): Comment new use. * testsuite/g++.dg/ipa/devirt-c-1.C: Add dump scans. * testsuite/g++.dg/ipa/devirt-c-2.C: Likewise. * testsuite/g++.dg/ipa/devirt-c-7.C: New test. * testsuite/g++.dg/ipa/devirt-c-8.C: Likewise. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@180825 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/testsuite/g++.dg/ipa/devirt-c-8.C | 82 +++++++++++++++++++++++++++++++++++ 1 file changed, 82 insertions(+) create mode 100644 gcc/testsuite/g++.dg/ipa/devirt-c-8.C (limited to 'gcc/testsuite/g++.dg/ipa/devirt-c-8.C') diff --git a/gcc/testsuite/g++.dg/ipa/devirt-c-8.C b/gcc/testsuite/g++.dg/ipa/devirt-c-8.C new file mode 100644 index 00000000000..309644d92ac --- /dev/null +++ b/gcc/testsuite/g++.dg/ipa/devirt-c-8.C @@ -0,0 +1,82 @@ +/* Verify that ipa-cp correctly detects the dynamic type of an object + under construction when doing devirtualization. */ +/* { dg-do run } */ +/* { dg-options "-O3 -fno-early-inlining -fno-inline -fdump-ipa-cp -fdump-tree-optimized" } */ + +extern "C" void abort (void); + +class A +{ +public: + int data; + A(); + virtual int foo (int i); +}; + +class B : public A +{ +public: + B(); + virtual int foo (int i); +}; + +class C : public A +{ +public: + virtual int foo (int i); +}; + +int A::foo (int i) +{ + return i + 1; +} + +int B::foo (int i) +{ + return i + 2; +} + +int C::foo (int i) +{ + return i + 3; +} + +static int __attribute__ ((noinline)) +middleman (class A *obj, int i) +{ + return obj->foo (i); +} + +int __attribute__ ((noinline,noclone)) get_input(void) +{ + return 1; +} + +inline __attribute__ ((always_inline)) A::A () +{ + if (middleman (this, get_input ()) != 2) + abort (); +} + +inline __attribute__ ((always_inline)) B::B () +{ +} + +static void bah () +{ + class B b; +} + +int main (int argc, char *argv[]) +{ + int i; + + for (i = 0; i < 10; i++) + bah (); + return 0; +} + +/* { dg-final { scan-ipa-dump "Discovered a virtual call to a known target.*A::foo" "cp" } } */ +/* { dg-final { scan-tree-dump-times "OBJ_TYPE_REF" 0 "optimized"} } */ +/* { dg-final { cleanup-ipa-dump "cp" } } */ +/* { dg-final { cleanup-tree-dump "optimized" } } */ -- cgit v1.2.1