2014-10-16 55 views
3

我得到這個蘋果的Mach-O鏈接錯誤:架構arm64的未定義符號。將C調用到ObjC++文件中?

Undefined symbols for architecture arm64: 
    "_TestFunction", referenced from: 
     -[ViewController viewDidLoad] in ViewController.o 
ld: symbol(s) not found for architecture arm64 
clang: error: linker command failed with exit code 1 (use -v to see invocation) 

這裏的一切必要重現錯誤的步驟:

  1. 我創建了一個新的單一視圖通用Objective C的項目(Xcode的版本6.0.1(6A317)))。
  2. 我然後創建一個名爲TestClass的
  3. 一個新的ObjectiveC文件
  4. 變化TestClass.m到TestClass.mm
  5. 添加 「void TestFunction();」 我的.h
  6. 添加 「void TestFunction(){}」 我.mm
  7. 導入TestClass.h到我的ViewController.m並嘗試從我的viewDidLoad調用TestFunction()

我正在做一些核心音頻工作,需要在我的MIDI回調中做一些C++調用,所以我不能進行任何ObjectiveC方法調用,因爲它們會阻塞音頻線程。

也許Xcode視圖TestFunction()作爲一個C++調用,所以不會使它從一個純粹的ObjectiveC類?有什麼辦法告訴Xcode它是一個C函數嗎?

回答

11

您需要將您的C++函數標記爲extern "C"
之後,客觀的c代碼可以鏈接到該功能。

你TestClass.h應該是這樣的

#if defined __cplusplus 
extern "C" { 
#endif 

void TestFunction(); 

#if defined __cplusplus 
}; 
#endif 

的extern「C」,使一個函數名在C++中有「C」鍵(編譯器不裂傷的名稱),以便客戶端C代碼可以鏈接使用一個'C'兼容的頭文件來包含你的函數聲明(即使用)你的函數。您的函數定義包含在二進制格式中(由C++編譯器編譯),客戶端的「C」鏈接器將使用「C」名稱鏈接到該格式。

由於C++重載了函數名,而C沒有,C++編譯器不能只使用函數名作爲唯一的id鏈接,所以它通過添加有關參數的信息來破壞名稱。由於不能重載C中的函數名,因此AC編譯器不需要對名稱進行重新命名。當您聲明函數在C++中具有外部「C」鏈接時,C++編譯器不會將參數/參數類型信息添加到用於連鎖。

+1

解決了它謝謝你的信息! 我通過在我的項目中使用構建體系結構,讓我感到非常頭痛! – user3306249 2014-10-16 12:42:25

+0

你是怎麼知道這件事的?我在哪裏可以閱讀這樣的內容?謝謝你的回答,它爲我節省了很多時間。 – theFool 2016-07-27 08:56:08

+1

非常感謝你! – 2017-07-04 17:48:55

相關問題