2013-06-24 29 views
3

我有一個暴露的函數具有以下簽名德里DLL:其中記錄的方式規定如何使用ctypes訪問返回在Delphi dll中編碼的自定義類型的函數?

Function MyFunc(ObjID : Cardinal) : TMyRec; stdcall; 

type TMyRec = record 
    Count : Cardinal; 
    Items : array of TMyItemRec; 
end; 

type TMyItemRec = record 
    ID : Cardinal; 
    Params : array of String; 
end; 

現在我的問題是:我怎麼能存取權限MYFUNC的結果用Python ctypes調用dll?我編寫模仿類型

from ctypes import * 
class TMyItemRec(Structure): 
    _fields_ = [("ID", c_int), ("Params", POINTER(c_wchar_p))] 

class TMyRec(Structure): 
    _fields_ = [("Count", c_int), ("Params", POINTER(TMyItemRec))] 

但是當我嘗試這樣讀取數據兩大類:

my_dll = windll.Script 

def GetMyRec(ID): 
    my_dll.MyFunc.argtypes = [c_uint] 
    my_dll.MyFunc.restype = TClilocRec 

    return my_dll.Script_GetClilocRec(ID) 

我收到訪問衝突錯誤。

回答

5

您無法將Delphi託管類型(如動態數組)傳遞給非Delphi代碼。你不能指望用這些數據類型調用函數。

您將需要重新設計您的界面。你需要使用簡單的類型和包含簡單類型的記錄。如果你需要數組,那麼你必須傳遞一個指向第一個元素的指針和長度,而不是使用Delphi特定的託管類型。使用Windows API作爲您如何設計互操作接口的模板。

您需要處理的另一件事是函數返回值在Delphi中的處理方式與在大多數其他Windows編譯器中的處理方式不同。因此,不適合寄存器的記錄將需要作爲var參數傳遞,而不是作爲函數返回值傳遞。

+0

謝謝你的回覆。你最後一段的含義是什麼?我可以有一個小的代碼示例嗎? –

+0

我的意思是,如果記錄大於寄存器的大小,那麼函數返回值將由Delphi和其他工具以不同方式處理。所以不要將記錄作爲返回值傳遞。 –

+0

也許他也可能使用OLE類似數據類型和var-arrays –

相關問題