From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 5548 invoked by alias); 22 Apr 2003 01:06:01 -0000 Mailing-List: contact gcc-prs-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Archive: List-Post: List-Help: Sender: gcc-prs-owner@gcc.gnu.org Received: (qmail 5528 invoked by uid 71); 22 Apr 2003 01:06:01 -0000 Resent-Date: 22 Apr 2003 01:06:01 -0000 Resent-Message-ID: <20030422010601.5523.qmail@sources.redhat.com> Resent-From: gcc-gnats@gcc.gnu.org (GNATS Filer) Resent-Cc: gcc-prs@gcc.gnu.org, gcc-bugs@gcc.gnu.org, sunil.k.davasam@intel.com Resent-Reply-To: gcc-gnats@gcc.gnu.org, sunil.k.davasam@intel.com Received: (qmail 5089 invoked by uid 48); 22 Apr 2003 01:04:49 -0000 Message-Id: <20030422010449.5080.qmail@sources.redhat.com> Date: Tue, 22 Apr 2003 01:06:00 -0000 From: sunil.k.davasam@intel.com Reply-To: sunil.k.davasam@intel.com To: gcc-gnats@gcc.gnu.org Cc: sunil.k.davasam@intel.com X-Send-Pr-Version: gnatsweb-2.9.3 (1.1.1.1.2.31) X-GNATS-Notify: sunil.k.davasam@intel.com Subject: libstdc++/10448: Bug in dynamic_cast algorithm X-SW-Source: 2003-04/txt/msg00913.txt.bz2 List-Id: >Number: 10448 >Category: libstdc++ >Synopsis: Bug in dynamic_cast algorithm >Confidential: no >Severity: serious >Priority: medium >Responsible: unassigned >State: open >Class: sw-bug >Submitter-Id: net >Arrival-Date: Tue Apr 22 01:06:01 UTC 2003 >Closed-Date: >Last-Modified: >Originator: sunil.k.davasam@intel.com >Release: unknown-1.0 >Organization: >Environment: UnitedLinux 1.0 (ia64) >Description: There is a bug in dynamic_cast algorithm. Based on ABI document, the function __dynamic_cast () takes 4 arguments. Here is prototype: extern "C" void* __dynamic_cast ( const void *sub, const abi:: __class_type_info *src, const abi::__class_type_info *dst, std::ptrdiff_t src2dst_offset ); The 4th argument "src2dst_offset" is a static hint about the location of the source subobject with respect to the complete object; special negative values for 4th argument are: -1 : no hint -2 : src is not a public base of dst -3 : src is a multiple public base type but never a virtual base type. Gcc compiler generates "-2" for 4th argument for the attached testcase. The testcase passes ,if you just compile and run. But, it fails when we change the value of 4th argument for __dynamic_cast() function from "-2" to "-1". Basically, If we don't provide any hint to dynamic_cast algorithm, it doesn't work properly atleast for this testcase. I don't know whether gcc compiler generates "-1" for any case, but this is an interoperability problem. Because, if some other compiler generates "-1" and link with gcc libraries, the application gives wrong output or sometimes segmentation fault. >How-To-Repeat: cmd> g++ -v Reading specs from /usr/lib/gcc-lib/ia64-suse-linux/3.2/specs Configured with: ../configure --enable-threads=posix --prefix=/usr --with-local-prefix=/usr/local --infodir=/usr/share/info --mandir=/usr/share/man --libdir=/usr/lib --enable-languages=c,c++,f77,objc,java,ada --enable-libgcj --with-gxx-include-dir=/usr/include/g++ --with-slibdir=/lib --with-system-zlib --enable-shared --enable-__cxa_atexit ia64-suse-linux Thread model: posix gcc version 3.2 cmd> g++ tt.cpp cmd> a.out C3() C2() C3() C2() C3() C2() Catching bad_cast Exception. cmd> g++ -S tt.cpp Open the file tt.s and change the 4th argument of __dynamic_cast() function from "-2" to "-1" cmd> g++ tt.s cmd> a.out C3() C2() C3() C2() C3() C2() >Fix: >Release-Note: >Audit-Trail: >Unformatted: ----gnatsweb-attachment---- Content-Type: text/plain; name="tt.cpp" Content-Disposition: inline; filename="tt.cpp" #include #include #include struct C11 { virtual int f1() { return 11; } virtual ~C11() { printf("%sC%d()\n", "~", 11); } C11() { printf("%sC%d()\n", "", 11); } }; struct C3 { virtual int f4() { return 3; } virtual int f2() { return 3; } // int i; C3() { printf("%sC%d()\n", "", 3); } }; struct C2: virtual C3 { C2() { printf("%sC%d()\n", "", 2); } }; C2 x2_3(C11 *ptrC11) { C2 tmp_C2; tmp_C2 = dynamic_cast(*ptrC11); return tmp_C2; } int main() { try { C2 ref_obj2, tmp_ref_obj2; C11 *tmp_ref_ptrC11; tmp_ref_ptrC11 = (C11 *)&ref_obj2; tmp_ref_obj2 = x2_3(tmp_ref_ptrC11); } catch(std::bad_cast) { printf("Catching bad_cast Exception.\n"); } return 0; }