解決延伸模組中自動化中的函式/屬性名稱衝突

在本主題中,“object” 會以 ADSI 用戶端檢視物件的方式表示對象整體。 也就是說,ADSI 及其所有擴充功能。

具有相同參數的相同函式名稱

如果物件中的兩個或多個雙重 IDispatch 介面支援相同名稱的屬性或方法,例如 Func1,則會使用下列準則來判斷調用。 如果用戶端具有其中一個支援 Func1 方法的雙重介面指標,而且如果自動化 環境支援 vtable 存取,則 Func1 會直接透過 ADSI vtable 存取來叫用。

如果上述任一條件為 false,則會呼叫 IDispatch::GetIDsOfNamesIDispatch::Invoke 來叫用 Func1。

如需詳細資訊和用戶端如何將指標新增至雙重介面,以及支援 vtable 存取的環境類型描述,請參閱 ADSI 延伸模組模型中的晚期系結與 Vtable 存取。

因為所有擴充對象都會將 IDispatch 函式重新導向回匯總工具,因此匯總工具會控制叫用 Func1函式。 規則如下:

  • 如果有任何介面,而且在匯總工具 (ADSI) 中只支援稱為 Func1 的函式,匯總工具會叫用自己的 Func1
  • 否則,匯總工具會依登錄中列出的順序逐一查看其每個延伸模組,並尋找第一個實作稱為 Func1 函式的延伸模組。 第一個延伸模組中的多個雙重 IDispatch 介面可能會有一個稱為 Func1 的函式,但不太可能。 延伸模組必須決定應該一律在自動化中叫用哪一 個 Func1

具有不同參數的相同函式名稱

上一節討論如何解決函式名稱衝突,也就是在自動化中發生函式名稱時,具有相同函式名稱和相同參數清單的函式名稱,例如數位、類型和順序。 如果兩個函式的名稱相同,但參數不同,該怎麼辦? 如果 ADSI 用戶端使用 IDispatch::GetIDsOfNames 叫用函式,而不使用多個名稱來指定參數,ADSI 擴充功能模型就無法釐清函式。 根據上述所討論的解析配置,透過其中一個介面支援此函式的登錄中的第一個延伸模組會叫用此函式的版本,而且呼叫可能會失敗或產生不正確的結果。

例如:

  • Extn1 (第一個位於類別 CA 下的登錄 – 較高優先順序) 支援 IInterface1
  • Extn2 (CA 類別下登錄中的第三個 – 優先順序較低) 支援 IInterface2
  • IInterface1 支援 Method1(int param1, int param2)
  • IInterface2 支援 Method1(int param1)

ADSI 用戶端具有 類別 CA 物件的 IDispatch 介面指標。 它想要叫用 IInterface2::Method1。 如果用戶端呼叫 “pDispatch-GetIDsOfNames>(IID_NULL, rgszNames, 1, MY_LCID, rgDispId)” ,只要將函式名稱 “Method1” 儲存在 rgszNames[0],則 IInterface1::Method1 而不是叫用所需的 IInterface2::Method1 ,而函式會失敗,因為參數數目不同。

為了將這個問題降到最低,延伸模塊開發人員可以使用自己的特定標識元為其函式名稱加上前置詞,並避免使用相同名稱但不同參數的介面設計。

如果發生名稱衝突,則如果介面是雙重介面,ADSI 用戶端可以透過直接 Vtable 存取來避免問題。 如果無法直接存取 vtable,ADSI 用戶端應該使用多個名稱呼叫 IDispatch::GetIDsOfNames,並指定函式名稱,以及先前所述的數位 rgszNames 中的參數。

Visual Basic 5 不會呼叫具有多個名稱的 IDispatch::GetIDsOfNames 函 式。 也就是說,它只會將函式名稱傳遞至 GetIDsOfNames,但不會傳遞自變數。 不過,如果介面是雙重介面,Visual Basic 5 可讓使用者透過直接 vtable 存取來叫用函式,而不是叫用 IDispatch::GetIDsOfNames 函式。 開發人員應盡可能使用直接 Vtable 存取。

如需名稱衝突解決的詳細資訊,請參閱 解決函式名稱衝突的範例。