2011-09-11 32 views
3

iPhoneアプリケーションのObjective-CコードとC++コードの両方から呼び出せるユーティリティ関数を作成しようとしています。 ObjectiveC++(.mm)としてコンパイルできないサードパーティのC++クラスがあります。私はヘッダーファイルに関数を宣言し、次にそれらを定義する.cファイルを持っています。私は3倍のスペルエラーをチェックしましたが、何らかの理由でリンカが関数の定義を見つけることができません。Objective-Cコードのextern "C"を使用したリンカエラー

は、ここでCのヘルパー関数のヘッダーです:

#ifndef FILE_LOADER_H 
#define FILE_LOADER_H 

#if __cplusplus 
extern "C" { 
#endif 

void * loadDataFromFile(const char * szFilename, bool bDocument); 
void * loadImageFromFile(const char * szFilename, bool bDocument); 
void loadMeshFromFile(const char *szFilename, void* pMesh); 

#if __cplusplus 
} // Extern C 
#endif 

#endif 

そしてここで.cファイルです:

#include "FileLoader.h" 
#include <objc/objc.h> 
#include <objc/message.h> 
#include <Foundation/Foundation.h> 


void * loadDataFromFile(const char * szFilename, bool bDocument) 
{ 
    Class loaderClass = NSClassFromString(@"Loader"); 
    void * pReturnVal = objc_msgSend(loaderClass, NSSelectorFromString(@"loadDataFromFile:document"), szFilename, bDocument); 
    return pReturnVal; 
    //return [Loader loadDataFromFile:szFilename document:bDocument]; 
} 
void * loadImageFromFile(const char * szFilename, bool bDocument) 
{ 
    Class loaderClass = NSClassFromString(@"Loader"); 
    void * pReturnVal = objc_msgSend(loaderClass, NSSelectorFromString(@"loadImageFromFile:document"), szFilename, bDocument); 
    return pReturnVal; 
    //return (void*)[Loader loadImageFromFile:szFilename document:bDocument]; 
} 
void loadMeshFromFile(const char *szFilename, void* pMesh) 
{ 
    Class loaderClass = NSClassFromString(@"Loader"); 
    objc_msgSend(loaderClass, NSSelectorFromString(@"loadMeshFromFile:mesh"), szFilename, pMesh); 
    //[Loader loadMeshFromFile:szFilename mesh:pMesh]; 
} 

私はとのextern "C" なしでコンパイルしようとしました、リンカーのエラー結果は同じです。

誰かが私が間違っていることについていくつかの光を当てることができますか?

リンカエラー:

Undefined symbols for architecture i386: 
"loadMeshFromFile(char const*, void*)", referenced from: 

UPDATE:私は誰も私を伝えることができ、実際のObjectiveCコードがなかったにもかかわらず、客観Cとしての私のソースファイルをコンパイルすることによって、問題を解決するように見えたた理由上記のソースファイルはCコードとしてコンパイルされませんか?

+0

共有ライブラリのアーキテクチャをチェックしてください。ほとんどの場合、プログラムのagaistとアーム共有ライブラリをリンクしていた可能性があります。何らかのアームターゲット(デバイス)に切り替えてください。 –

+0

リンカーの問題があるので、.hファイルが正常に動作していると思います。それ以外の場合は、コンパイルステージで未定義の関数を取得します。私はあなたがリンカを起動する方法を見直すでしょう、おそらくあなたはこれらの関数の.oがありません? – Miguel

+0

@Dyno Fu:近づくと、あなたは奇妙な警告に気づかされたというコメントを受けました:sourcecode.cのファイル '$(PROJECT_DIR)/XLoaderTest/Utility/FileLoader.c'をアーキテクチャi386用に処理するルールはありません。奇妙なXcodeの問題、任意の提案? – dewhacker

答えて

7

は、CおよびC++の翻訳のためのCリンケージを指定するには、次の構築物を使用し:

#if !defined(__cplusplus) 
#define MONExternC extern 
#else 
#define MONExternC extern "C" 
#endif 
// declare loadMeshFromFile 
MONExternC void loadMeshFromFile(char const*, void*); 

この宣言は、C、にObjC、C++、にObjC++と互換性があります。

+0

同じリンカエラーを試してもまだ運がいいわけがありません。問題はこの警告で上記のコメントにある可能性があります。プロジェクト$(PROJECT_DIR)/XLoaderTest/Utility/FileLoader.cを処理するルールはありません。プロジェクトの設定以来意味をなさないアーキテクチャi386のsourcecode.cです。アクティブなアーキテクチャに設定されていますarmv6、armv7 – dewhacker

0

アーキテクチャを再確認してください。リンカーの問題は、.cファイルをコンパイルしているのではなく、リンケージが分からないということです。だからここで何が起こるか...

コンパイラは、.cファイルを正しくコンパイルする方法を見つけることができません。 リンカーは外部のCリンケージを見て、「わかりましたか?それは.cファイルがオブジェクトコードにコンパイルされていないためです。

ビルドフェーズを確認する必要があります。ターゲットに移動し、アクティブなターゲットを選択し、コンパイルフェーズで何が起こっているかを確認してください - 私の推測は何とかターゲット(リリースまたはデバッグ)このファイルはarmの代わりにi386ターゲットとして追加されているので、混乱してコンパイルルールを見つけることができません(i386をターゲットにしていないので、コンパイルルールはありません)。

あなたが私にどんなターゲットのスナップショットを示している場合など、全てが他の障害が発生した場合、アームのためのブランドの新しいターゲットを作ってみて、あなたがそのようにそれを使用するか、またはデバッグへのリリースからターゲットを切り替えることができるかどうかを確認あなたは私が多分もっと役に立つことができるためにコンパイルしています:)。がんばろう!

関連する問題