共用方式為


處理 IDL 文件中的 #defines

此頁面描述為何使用 #define 定義的符號會從 MIDL 編譯程式產生 H 檔案中消失,以及可以執行哪些動作。 此說明適用於 MIDL 處理的任何檔案,例如 *.idl、*.acf、*.h 檔案。

#define 符號的消失是 MIDL 將輸入檔的前置處理委派給預處理器的結果。 根據預設,預處理器是來自建置環境的 C/C++ 預處理器。 前置處理之後,MIDL 接收到的輸入流只包含 #line 預處理指令。 特別是,預處理器會展開輸入檔中的所有巨集定義,因此 MIDL 無法偵測其存在。 因此,當 MIDL 將類型定義從輸入檔複寫到產生的 H 檔案時,不會復寫 #defines。 因此,如果要稍後從產生的 H 檔案使用 #defines,請勿直接在 IDL 檔案中使用它們。

建議使用下列四種因應措施:

  • 使用 const 宣告規格。
  • 使用在 IDL 檔案中匯入或包含的個別標頭檔,並且稍後在 C 原始程式碼中包含它們。
  • 在IDL檔案中使用列舉常數。
  • 使用 cpp_quote 在產生的頭檔中重現 #define

您可以使用 IDL 常數宣告語法來重現顯示常數。 請注意,IDL 常數宣告中的 const 與 C/C++ const 語意不同,而且只會為 IDL 編譯引進具名常數。 例如:

const short ARRSIZE = 10

此範例指定 arrSIZE 是值為 10 的常數。 具名常數可用於IDL陣列宣告子,以及 C 程式設計人員會使用顯式定義的其他地方。 此外,此語法會導致在頭文件中產生下列這一行:

#define ARRSIZE 10

另一個處理 **#**define 語句的方法,是將它們封裝在個別頭檔中、專門用於 **#**define 語句的檔案或只包含類型定義的檔案中。 只包含預處理器指示詞的檔案,可由IDL檔案和 C 來源檔案安全地包含。 雖然 MIDL 編譯器所產生的標頭檔案中不會出現指令,但 C 原始程式碼可以包含這些個別的標頭檔案。 同樣地,具有 **#**define 語句和一般類型定義的頭檔可以從您的IDL檔案匯入。 此方法透過將 **#**define 和 typedef 陳述式封裝在 H 檔案中,使得 **#**define 符號不直接用於匯入的 IDL 檔案。 將標頭或IDL檔案匯入至另一個IDL檔案,可防止 typedef 語句複寫到 MIDL 所產生的 H 檔案(這與 **#**include 語句相反)。 此方法允許在 C 程式碼中同時參考原始標頭文件和產生的 H 檔案,避免出現重複定義的問題。

在IDL檔案中使用列舉常數也有效。 這些常數可用於IDL中的常數表達式,例如,在陣列宣告子中。 C 編譯程式預處理器在 MIDL 編譯的初期階段不會移除列舉常數,因此 MIDL 編譯程式所產生的頭檔提供列舉常數。 請考慮下列語句:

typedef enum midlworkaround { MAXSTRINGCOUNT = 300 };

C 預處理器在 MIDL 編譯期間不會移除此語句,並將 typedef 複寫至產生的 H 檔案。 常數 MAXSTRINGCOUNT 可供包含由 MIDL 編譯器生成的標頭檔案的 C 語言原始碼程式使用。

最後,MIDL 的 cpp_quote 指示詞可用來將任意字串直接寫出到產生的 H 檔案中。 例如,要取得在此頁面上先前用 cpp_quote的具名常數,可以使用下列語句:

cpp_quote ("#define ARRSIZE 10")

此語句會導致在頭檔中產生下列這一行:

#define ARRSIZE 10