Passing a C++ object's member function to a C function expecing a function pointer!

Discussion in 'C++' started by James Vanns, Jan 20, 2004.

  1. James Vanns

    James Vanns Guest

    Sounds nasty doesn't it!! Well it's kinda what I need to do! I have an
    external C struct (external to the C++ project/classes etc.) which is
    wants a function ptr assigned to one of it's members:

    struct blah {
    int (func_ptr*) (int a, int b, float c);
    }; etc...

    However, my code is in C++ and a wish to assign a non-static member
    function (I know I can do this) to this struct member! Can this be
    done!? Some how with pointers or references? What about the STL's
    mem_func stuff?

    Can anyone shed some light on this?

    Cheers

    Jim
     
    James Vanns, Jan 20, 2004
    #1
    1. Advertising

  2. James Vanns

    Jeff Flinn Guest

    James,

    "James Vanns" <> wrote in message
    news:...
    > Sounds nasty doesn't it!! Well it's kinda what I need to do! I have an
    > external C struct (external to the C++ project/classes etc.) which is
    > wants a function ptr assigned to one of it's members:
    >
    > struct blah {
    > int (func_ptr*) (int a, int b, float c);
    > }; etc...
    >
    > However, my code is in C++ and a wish to assign a non-static member
    > function (I know I can do this)


    And how could that be?

    The closest "non-static member function" would have the signature:

    int (*fnc_ptr)( ThisClass*, int, int, float );

    Where would the this pointer come from?

    > to this struct member! Can this be
    > done!? Some how with pointers or references? What about the STL's
    > mem_func stuff?


    "mem_fun" results in a function object with an operator(), not even close to
    a
    static function pointer.

    > Can anyone shed some light on this?


    The best you can do is to define a global or static function that uses a
    global or static instance/reference/pointer to forward the call to it's
    non-static member function with the passed in arguments.

    The best approach depends on what your really trying to do. Perhaps you
    could give more details as to what your attempting to do.

    Jeff F
     
    Jeff Flinn, Jan 20, 2004
    #2
    1. Advertising

  3. James Vanns

    Evan Carew Guest

    Re: Passing a C++ object's member function to a C function expecinga function pointer!

    Jim,

    Glad to see you are looking in to adding C++ to a C project. Without
    going into the issues related to seperate compilers, I'm going to assume
    you are using the GCC tool chain to compile both the C & C++ code. That
    being the case, some example code follows after your questions. The
    basic thing to take away is that you are compiling a C interface to your
    C++ library, then linking your application with the g++ linker.

    James Vanns wrote:
    > Sounds nasty doesn't it!! Well it's kinda what I need to do! I have an
    > external C struct (external to the C++ project/classes etc.) which is
    > wants a function ptr assigned to one of it's members:
    >
    > struct blah {
    > int (func_ptr*) (int a, int b, float c);
    > }; etc...
    >
    > However, my code is in C++ and a wish to assign a non-static member
    > function (I know I can do this) to this struct member! Can this be
    > done!? Some how with pointers or references? What about the STL's
    > mem_func stuff?
    >
    > Can anyone shed some light on this?
    >
    > Cheers
    >
    > Jim


    First, lets define a simple C++ class in a header file:

    //simple.h A simple C++ class
    //
    #include <string>
    #include <complex>

    using namespace std;

    class simple{
    public:
    simple();
    int func1( int flags );
    int func2(string s, complex<double> c);
    friend simple operator+(const simple&, const simple&);
    private:
    int member1;
    double member2;
    string member3;
    };

    Next, lets define the class:

    //simple++.C implementation file
    #include "simple.h"

    simple::simple(){
    member1 = 0;
    member2 = 0;
    member3 = "This is a dummy string";
    }
    int simple::func1(int flags){
    member1 |= flags;
    return member1;
    }
    int simple::func2(string s, complex<double> c){
    member3 = s;
    member2 = c.real();
    return (int)member2;
    }
    simple operator+(const simple& lhs, const simple& rhs){
    simple tempvar;
    return tempvar;
    }

    Ok, now lets wrap it in some C code that will be compiled with the C++
    compiler, to start, we'll describe the interface in a header:

    //simple_api.h C API simple class


    #ifdef __cplusplus
    extern "C" {
    #endif
    //Do everything through a pointer
    typedef void* SIMPLE_HANDLE;

    //The equavalent of new();
    SIMPLE_HANDLE Screate();
    //The equavalent of delete();
    void sfree(SIMPLE_HANDLE sh);
    //the first function
    int sfunc1(SIMPLE_HANDLE sh, int flags);
    //the second function
    int sfunc2(SIMPLE_HANDLE sh, const char *s, double re, double im);
    //the overloaded operator
    void sadd(SIMPLE_HANDLE sh,
    SIMPLE_HANDLE const lhs, SIMPLE_HANDLE const rhs);
    #ifdef __cplusplus
    }
    #endif

    Then, we'll implement it in a ".c" file:

    //simple_api.c
    #include "simple_api.h"
    #include "simple.h"

    extern "C"{
    SIMPLE_HANDLE Screate(){ return new simple; }
    void sfree(SIMPLE_HANDLE sh){ delete static_cast<simple*>(sh);}
    int sfunc1(SIMPLE_HANDLE sh, int flags){
    return static_cast<simple*>(sh)->func1(flags);
    }
    int sfunc2(SIMPLE_HANDLE sh, const char *s, double re, double im){
    complex<double> cd(re, im);
    return static_cast<simple*>(sh)->func2(s, cd);
    }
    void sadd(SIMPLE_HANDLE sh,
    SIMPLE_HANDLE const lhs, SIMPLE_HANDLE const rhs){
    *static_cast<simple*>(sh) = *static_cast<simple*>(lhs) +
    *static_cast<simple*>(rhs);
    }
    }

    And finally, we'll write an application in C which uses the C++ library
    through the C code:

    #include "simple_api.h"

    int main(){
    SIMPLE_HANDLE sh, sh2, sh3;
    int flags = 1;
    int retval = 0;

    sh = Screate();
    sh2 = Screate();
    sh3 = Screate();
    retval = sfunc1(sh, flags);
    retval = sfunc2(sh, "Testing ...", 1, 2);
    retval = sfunc1(sh2, flags);
    retval = sfunc2(sh2, "Testing ...", 3, 4);
    sadd(sh3, sh, sh2);
    sfree(sh); /* Strictly speaking, not needed in this code example */
    sfree(sh2); /* Strictly speaking, not needed in this code example */
    sfree(sh3); /* Strictly speaking, not needed in this code example */
    return 0;
    }


    Ok, all done, time to compile & link. The following log shows how my
    make file did it:


    [root@angus sample]# make
    gcc -c sample.c
    g++ -c simple_api.c
    g++ -c simple++.C
    g++ -O2 -o sample sample.o simple_api.o simple++.o
     
    Evan Carew, Jan 20, 2004
    #3
  4. James Vanns

    David Harmon Guest

    On 20 Jan 2004 04:49:02 -0800 in comp.lang.c++,
    (James Vanns) was alleged to have written:
    >However, my code is in C++ and a wish to assign a non-static member
    >function (I know I can do this) to this struct member!


    It's not what you don't know that hurts, it's what you know that isn't
    so.

    This issue is covered in Marshall Cline's C++ FAQ. See the topic
    "[30.2] How do I pass a pointer to member function to a signal handler,
    X event callback, etc?" It is always good to check the FAQ before
    posting. You can get the FAQ at:
    http://www.parashift.com/c -faq-lite/
     
    David Harmon, Jan 20, 2004
    #4
  5. Re: Passing a C++ object's member function to a C function expecinga function pointer!

    David Harmon wrote:

    > This issue is covered in Marshall Cline's C++ FAQ.
    > See the topic "[30.2] How do I pass a pointer to member function
    > to a signal handler, X event callback, etc?"


    # [30.2] What is "static typing,"
    and how is it similar/dissimilar to Smalltalk?

    > It is always good to check the FAQ before posting.
    > You can get the FAQ at:
    >
    > http://www.parashift.com/c -faq-lite/
     
    E. Robert Tisdale, Jan 20, 2004
    #5
  6. James Vanns

    red floyd Guest

    Re: Passing a C++ object's member function to a C function expecinga function pointer!

    E. Robert Tisdale wrote:
    > David Harmon wrote:
    >
    >> This issue is covered in Marshall Cline's C++ FAQ.
    >> See the topic "[30.2] How do I pass a pointer to member function
    >> to a signal handler, X event callback, etc?"

    >
    >
    > # [30.2] What is "static typing,"
    > and how is it similar/dissimilar to Smalltalk?
    >
    >> It is always good to check the FAQ before posting.
    >> You can get the FAQ at:
    >>
    >> http://www.parashift.com/c -faq-lite/

    >


    Yep. The topic they wanted was 33.2.
     
    red floyd, Jan 20, 2004
    #6
  7. James Vanns

    David Harmon Guest

    On Tue, 20 Jan 2004 21:11:09 GMT in comp.lang.c++, red floyd
    <> was alleged to have written:
    >Yep. The topic they wanted was 33.2.


    Time for me to wget a new copy of the FAQ.
     
    David Harmon, Jan 21, 2004
    #7
  8. James Vanns

    Evan Carew Guest

    Re: Passing a C++ object's member function to a C function expecinga function pointer!

    red floyd wrote:
    > E. Robert Tisdale wrote:
    >
    >> David Harmon wrote:
    >>
    >>> This issue is covered in Marshall Cline's C++ FAQ.
    >>> See the topic "[30.2] How do I pass a pointer to member function
    >>> to a signal handler, X event callback, etc?"

    >>
    >>
    >>
    >> # [30.2] What is "static typing,"
    >> and how is it similar/dissimilar to Smalltalk?
    >>
    >>> It is always good to check the FAQ before posting.
    >>> You can get the FAQ at:
    >>>
    >>> http://www.parashift.com/c -faq-lite/

    >>
    >>

    >
    > Yep. The topic they wanted was 33.2.
    >
    >

    Hmm... A pretty anemic example, don't you think?

    Evan
     
    Evan Carew, Jan 21, 2004
    #8
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Newsgroup - Ann
    Replies:
    5
    Views:
    629
    John Carson
    Jul 30, 2003
  2. Fraser Ross
    Replies:
    4
    Views:
    1,067
    Fraser Ross
    Aug 14, 2004
  3. Replies:
    8
    Views:
    562
    PJP of NYC
    May 24, 2005
  4. Stephen Howe
    Replies:
    2
    Views:
    298
    Stephen Howe
    Nov 6, 2012
  5. somenath
    Replies:
    2
    Views:
    170
    somenath
    Aug 29, 2013
Loading...

Share This Page