Quuxplusone / LLVMBugzillaTest

0 stars 0 forks source link

Polymorphic return types conflict with virtual base class, causes executable to segfault #9995

Closed Quuxplusone closed 13 years ago

Quuxplusone commented 13 years ago
Bugzilla Link PR9660
Status RESOLVED FIXED
Importance P normal
Reported by Ethan Tira-Thompson (ejtttje@gmail.com)
Reported on 2011-04-08 13:16:40 -0700
Last modified on 2011-04-10 13:21:25 -0700
Version trunk
Hardware Macintosh MacOS X
CC andersca@icloud.com, dgregor@apple.com, kremenek@apple.com, llvm-bugs@lists.llvm.org
Fixed by commit(s)
Attachments test.cc (795 bytes, application/octet-stream)
Blocks
Blocked by
See also
Created attachment 6422
sample code

In the attached sample code, there is a 'Cloneable' interface to provide
'clone()'.

Another class 'Base' inherits virtually from Cloneable, providing a Base*
clone(), and a third class 'Derived' inherits from Base, providing its own
Derived* clone().

When Derived::clone() is called, the code generated by clang will crash, as
shown in this log from gdb running the attached sample code

(gdb) run
Starting program: /Users/ejt/test
Reading symbols for shared libraries ++. done
Base clone works!

Program received signal EXC_BAD_ACCESS, Could not access memory.
Reason: KERN_PROTECTION_FAILURE at address: 0x00007fff70ec2990
0x00007fff70ec2990 in vtable for __cxxabiv1::__class_type_info ()
(gdb) bt
#0  0x00007fff70ec2990 in vtable for __cxxabiv1::__class_type_info ()
#1  0x00000001000016fb in main (argc=1, argv=0x7fff5fbff730) at test.cc:26

All of the elements described above are necessary to reproduce this bug.
Cloneable must provide the function prototype, Base must use virtual
inheritance, and Base must update the return type.  If any one of these items
is removed, then the crash does not occur.  Also, as noted in the above output,
Base::clone() can be called successfully, it is only the Derived::clone() which
crashes.

g++ and llvm-g++ will compile this code for successful execution.

This issue occurs identically with both the Apple clang (Apple clang version
2.0 (tags/Apple/clang-137) (based on LLVM 2.9svn)) as well as the latest svn
(revision 129132)

Thanks!
Quuxplusone commented 13 years ago

Attached test.cc (795 bytes, application/octet-stream): sample code

Quuxplusone commented 13 years ago

cloned to rdar://problem/9258154

Quuxplusone commented 13 years ago
There are two bugs here:

1. We're not devirtualizing the call to Derived::clone.
2. We're generating an incorrect member function vtable index for
Derived::clone.

I'm looking at 2 right now.
Quuxplusone commented 13 years ago

2 has been fixed in 129252. Will look at the devirtualization next.

Quuxplusone commented 13 years ago

The devirtualization has been fixed in revision 129253.