2017-10-24 3 views
0

私はCコードでも使用されるはずのC++で "ライブラリ"を書きます。私はこのようなプロセスを続けてきました。
- g ++コンパイラとgccコンパイラを使用しています(互換性があるため)。
- extern "C"をCコードで使用する関数で使用しました。
- 私のトップレベルは、Cコンパイラが理解できるシグネチャでラッパー関数を使用しています。
- 目的のファイルにコンパイルされたC++コード(g ++の場合)。
- クライアントコードファイルをgccでコンパイルしました。
- 編集:gcc(またはld)とリンクしようとしました(g ++ではない)。ソースファイルがあると機能を定義するCコードリンケージエラーからC++関数を呼び出す(リンクにgccを使用)

mymalloc.h

#include <stdlib.h> /* for size_t */ 

#ifdef __cplusplus 
extern "C" 
#endif 
void *mymalloc(size_t cbytes); 

#ifdef __cplusplus 
extern "C" 
#endif 
void myfree(void *ptr); 

allocator.cpp

#include "allocator.h" 
#include "mymalloc.h" 

Allocator * Allocator::instance = 0; 

extern "C" void *mymalloc(size_t cbytes){ 
    Allocator *allocator = Allocator::getInstance(); 
    return allocator->allocateFor(cbytes); 
} 

extern "C" void myfree(void *ptr){ 
    Allocator *allocator = Allocator::getInstance(); 
    allocator->freePtr(ptr); 
} 

... 

MCV例は、以下であろうCコードで使用されるもの、およびのメソッドそれ自体は他のC++のものを含んでいます。

私のCクライアントファイル(cclient.c)は、次のとおりです。

私は私が私のトップレベルでこれらのラッパー関数を持っているので、という印象の下に、その宣言は見ることができるので、だった
#include <stdio.h> 
#include "mymalloc.h" 

int main(void){ 
    void *p = mymalloc(500); 
    printf("%p\n", p); 
    return 0; 
} 

Cコードによって、すべてがOKでなければなりませんが、私はリンクエラーを取得しています:(サンプル/例が示さ)

./libmymalloc.a(allocator.o): In function `Allocator::getInstance()': 
allocator.cpp:(.text+0x3cf): undefined reference to `operator new(unsigned long)' 
allocator.cpp:(.text+0x3fa): undefined reference to `operator delete(void*, unsigned long)' 
./libmymalloc.a(allocator.o):(.data.DW.ref.__gxx_personality_v0[DW.ref.__gxx_personality_v0]+0x0): undefined reference to `__gxx_personality_v0' 

私はCLの賛成で、コンパイルとリンクしています方法アリティは、(最初​​の3件の回答後)

g++ -c allocator.cpp 
... (same for the rest .cpp files) 
gcc -c cclient.c 
gcc cclient.o allocator.o ...(all other c++ objectives)... 

編集がある:私は私がG ++を使用してリンクすることができることを知っています。私はCコンパイラにリンクする方法に興味があるので、gccと目的(またはそれらのライブラリ)だけがリンクできるようにしてください。

(この質問が重複かもしれないが、私はSO内の他のすべての質問を読んでいると私は私が間違って何をやっていた控除することができませんでした。)

+0

'allocator.h'には何がありますか? CからC++コードを呼び出すことは、本当に良い考えではありません。 –

+0

@NeilButterworth 'Allocator'クラスと' include'を他のヘッダ(C++)にします。はい、私はそれを認識しています。 – KyrSt

答えて

3

あなたはコマンドラインを投稿しませんでしたが、(g ++によって自動的に呼び出される)-lstdC++がそれらから抜けていると思います。

+0

'gcc'の代わりに' g ++ 'を使って動作させると、あなたはそれを暗示します。あなたの答えは実際には 'gcc'の代わりに' g ++ 'と単にリンクするだけでうまくいくと言えるでしょう。 –

2

これは、アロケータAllocatorは新しいを使用してのように見え、削除、およびこのリンクには、欠落している機能を満たすためのC++ライブラリは含まれていません。

2

あなたの問題はここにある:あなたがオブジェクトをリンクするためのCコンパイラを使用している

gcc cclient.o allocator.o ...(all other c++ objectives)... 


これは、C++やそれが使用するライブラリについては何も知りません。

g++ cclient.o allocator.o ...(all other c++ objectives)... 

オブジェクトをリンクするだけでなく、C++標準ライブラリ(新規および削除を含む)も含まれているので、これは機能するはずです。

+0

それは本当ですが、私はそれが疑問から推測されなかったと思いますが、(可能であれば)g ++をコンパイル(およびリンク)に使用してg ++を使用しないようにしたいと思います。 – KyrSt

関連する問題