This is the mail archive of the gcc-bugs@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

RE: can't catch exceptions from inside dynamically loaded object


I have discovered that we can catch such exceptions if just *one*
instance of __register_frame_info() is *in use* throughout the address
space including the main executable and dynamically loaded shared
objects. This can be achieved by either one of:

    - link the main executable with "-export-dynamic" option of GNU ld.
    - link the main executable with libstdc++.so shared library

The first method has severe side effect on i586-pc-linux-gnu platform.
If same symbol is used in the main executable and the shared object, the
symbol in shared object will be always ignored. For example,

    add this code to "a.cpp" in my previous email
        void xxx() { cerr << "this is xxx() in A." << endl; }
    add this code to "b.cpp"
        void xxx() { cerr << "this is xxx() in B." << endl; }
    add this line to "b.cpp" before throwing an exception.
        xxx();

    on i586-pc-linux-gnu platform, the output from "a" will be:
        I am B.
        this is xxx() in A.
        caught int
    on sparc-sun-solaris2.5.1 platform, it will be:
        I am B.
        this is xxx() in B.
        caught int

The second method may not happy for me on some situation.

Above methods are far from *perfect* because they require special
compilation or environment for running. To achieve the perfect, there
should be no way other than modify "frame.c" to change how it maintains
a linked list headed by "struct object* objects".

Shigeru Kanemoto
HappySize, Inc.

> -----Original Message-----
> From: Paul Forgey [mailto:paulf@aphrodite.com]
> Sent: Friday, January 29, 1999 1:55 PM
> To: sgk@happysize.co.jp; egcs-bugs@cygnus.com
> Subject: Re: can't catch exceptions from inside dynamically loaded
> object
> 
> 
> I, too can reproduce this, at least on sparc-sun-solaris2.6, with
> egcs-2.91.60
> 
> Unlike Shigeru, I am in _desperate_ need of a response, and 
> will probably be
> here all night trying to track this down, as this is causing 
> a crisis point
> for our project.
> 
> 
> -----Original Message-----
> From: sgk@happysize.co.jp <sgk@happysize.co.jp>
> To: egcs-bugs@cygnus.com <egcs-bugs@cygnus.com>
> Date: Wednesday, January 27, 1999 5:13 AM
> Subject: can't catch exceptions from inside dynamically loaded object
> 
> 
> >I am not sure that this is an egcs bug or not.
> >I do not ask you to respond to this email.
> >I hope this helps.
> >
> >Shigeru Kanemoto
> >HappySize, Inc.
> >
> >---------------------------------------------------------
> >problem:
> >
> >I could not catch exceptions (in main executable) thrown from inside
> >dynamically loaded shared object (with dlopen()). This happens on
> >i586-pc-linux-gnu platform (redhat linux 5.1) with many 
> versions of egcs
> >and binutils including one listed below. I have not yet fully tested,
> >but it seems that the same problem happens on i586-sun-solaris2.6
> >platform (Solaris 2.6 for Intel). However, 
> sparc-sun-solaris2.5.1 and 2.
> >6 are good.
> >
> >platform: i586-pc-linux-gnu (redhat linux 5.1)
> >libc version: glibc 2.0.7
> >egcs version: 1.1.1
> >binutils version: 2.9.1.0.19a
> >
> >---
> >The "static struct object* objects" of "egcs/gcc/frame.c" 
> exists both in
> >the main executable and the shared object. On the *bad* 
> platform, each
> >EH FRAME of each binary files will be registered to each 
> "static struct
> >object* objects" of each binaries. On the *good* platform, 
> all EH FRAME
> >will be registered to "static struct object* objects" of the main
> >executable.
> >
> >I think this may be a problem of ld.so or even my command line of
> >compiling shared object. But I can not determine.
> >
> >---
> >Example:
> >
> >With the following code, executing "./a" produces output like:
> >    % ./a
> >    I am B.
> >    Abort (core dumped)
> >    %
> >on i586-pc-linux-gnu (the "Abort" is by default terminate()).
> >And,
> >    % ./a
> >    I am B.
> >    caught int
> >    %
> >on sparc-sun-solaris2.5.1.
> >
> >===a.cpp===
> >#include <iostream>
> >#include <cstdlib>
> >#include <dlfcn.h>
> >
> >main()
> >{
> >    void *handle = dlopen("./b.so", RTLD_LAZY);
> >    void (*thrower)() = (void(*)())dlsym(handle, "thrower");
> >    try {
> >        (*thrower)();
> >    }
> >    catch (int&) {
> >        cerr << "caught int" << endl;
> >        exit(1);
> >    }
> >    catch (...) {
> >        cerr << "caught unknown" << endl;
> >        exit(2);
> >    }
> >    exit(0);
> >}
> >
> >===b.cpp===
> >#include <iostream>
> >
> >extern "C" void
> >thrower()
> >{
> >    cerr << "I am B." << endl;
> >    throw int(1);
> >}
> >
> >===Makefile===
> >all: a b.so
> >a: a.cpp
> >        g++ -o a a.cpp -ldl
> >b.so : b.cpp
> >        g++ -shared -fPIC -o b.so b.cpp
> >
> 


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]