2013-05-07 27 views
2

返回結構我有一個DLL寫在C出口這樣的功能:錯誤從DLL函數在Python

typedef struct testResult_t { 
    int testId; 
    int TT; 
    double fB; 
    double mD; 
    double mDL; 
    int nS; 
    int nL; 
} TestResult; 

TestResult __stdcall dummyTest(){ 
    TestResult a = {0}; 
    a.testId = 3; 
    return a; 
}; 

我用Python調用函數是這樣的:

class TestResult(Structure): 
    _fields_ = [ 
     ("testId", c_int), 
     ("TT", c_int), 
     ("fB", c_double), 
     ("mD", c_double), 
     ("mDL", c_double), 
     ("nS", c_int), 
     ("nL", c_int) 
    ] 

astdll.dummyTest.restype = TestResult 
result = astdll.dummyTest() 
print "Test ID: %d" % (result.testId) 

我執行腳本時出現此錯誤:

Traceback (most recent call last): 
    File "ast.py", line 330, in <module> 
    main() 
    File "ast.py", line 174, in main 
    result = astdll.dummyTest() 
    File "_ctypes/callproc.c", line 941, in GetResult 
TypeError: an integer is required 

任何想法有什麼問題?

+0

你應該顯示一切。你已經省略了重要的細節。我們看不到'astdll'是什麼。更大的問題是不同的C編譯器對於返回大型結構體有不同的ABI。值得注意的是MSVC和GCC對你的功能有不同的ABI。使用引用參數ctypes.byref返回結構是設計此接口的最佳方法。 – 2013-05-08 02:47:30

回答

0

對不起,我無法重現您的問題(Windows 7 x64,32位Python 2.7.3)。我會描述我爲了重現您的問題所嘗試的內容,希望它能幫助您。

我在Visual C++ Express 2008中創建了一個名爲「CDll」的新項目和解決方案。該項目被設置爲編譯爲C代碼並使用stdcall調用約定。除了東西VC++ 2008自動生成的,它有以下兩個文件:

CDll.h:

#ifdef CDLL_EXPORTS 
#define CDLL_API __declspec(dllexport) 
#else 
#define CDLL_API __declspec(dllimport) 
#endif 

typedef struct testResult_t { 
    int testId; 
    int TT; 
    double fB; 
    double mD; 
    double mDL; 
    int nS; 
    int nL; 
} TestResult; 

TestResult CDLL_API __stdcall dummyTest(); 

CDll.cpp(是的,我知道分機 '的.cpp',但我不」 t認爲重要):

#include "stdafx.h" 
#include "CDll.h" 

TestResult __stdcall dummyTest() { 
    TestResult a = {0}; 
    a.testId = 3; 
    return a; 
}; 

然後,我編譯和構建的DLL。然後我試圖加載並調用該函數具有以下Python腳本:

from ctypes import Structure, c_int, c_double, windll 

astdll = windll.CDll 

class TestResult(Structure): 
    _fields_ = [ 
     ("testId", c_int), 
     ("TT", c_int), 
     ("fB", c_double), 
     ("mD", c_double), 
     ("mDL", c_double), 
     ("nS", c_int), 
     ("nL", c_int) 
    ] 

astdll.dummyTest.restype = TestResult 
result = astdll.dummyTest() 
print "Test ID: %d" % (result.testId) 

當我運行該腳本,我得到了輸出Test ID: 3


首先想到我對你的問題可能是,你正試圖加載使用CDLL時,你應該使用windll的DLL,但是當我嘗試使用CDLL,我得到了一個完全不同的錯誤信息。您沒有向我們展示您如何加載DLL,但我懷疑您正在使用windll,正如我上面所做的那樣。

+0

這是問題所在,我正在使用oledll加載庫。非常感謝你!! – Jorge 2013-05-08 08:19:48

+0

@Jorge請注意,你的函數只能從使用MS大結構返回值ABI的編譯器中調用。 – 2013-05-08 12:30:07

+0

盧克,請你看看我的問題[鏈接](http://stackoverflow.com/questions/20773602/returning-struct-from-c-dll-to-python)?這是非常類似的問題,不同的是我在我的結構中有字符串,它讓我頭痛幾天 – Aleksandar 2013-12-25 14:36:24