Sto provando a inizializzare il Matlab compiler Runtime (MCR) da python usando ctypes. Il mio obiettivo finale è quello di essere in grado di utilizzare una DLL C creata dal compilatore Matlab in python, ma il primo ostacolo che ho bisogno di superare è ottenere MCR attivo e funzionante.Ctypes Python: come passare NULL come argomento con format const char **
Sto usando Python 2.7.8, Matlab 2013a, MCR8.1.
snipit da mclbase.h per mostrare gli argomenti ecc
LIBMWMCLBASE_API_EXTERN_C bool mclInitializeApplication(const char** options, size_t count);
C equivalente di quello che sto cercando di fare
mclInitializeApplication(NULL,0)
Ecco i miei vari tentativi di chiamare la funzione in Python. Risultano inevitabilmente in TypeErrors o Windows Error 0xE06D7363. Non posso romperlo! Sono un principiante di Python quindi potrebbe esserci qualcosa di semplice che mi manca. Qualsiasi commento benvenuto!
# Initialize the MATLAB Compiler Runtime global state
from ctypes import *
libmcr=cdll.mclmcrrt8_1
# Load mclbase library
mcr_dll = cdll.LoadLibrary('C:\\Program Files\\MATLAB\\MATLAB Compiler Runtime\\v81\\bin\\win64\\mclbase.dll')
# Pick function we want to use
mclInit=mcr_dll.mclInitializeApplication
# Set up argument and results types
mclInit.argtypes = [POINTER(POINTER(c_char)),c_size_t]
# mclInit.argtypes = [POINTER(c_char_p),c_size_t] #different formatting attempt
mclInit.restype = c_bool
a=None
acast=cast(a,POINTER(c_char_p))
acast1=cast(a,POINTER(c_char))
acast2=cast(a,POINTER(POINTER(c_char)))
print 'a='
print a
print 'acast='
print acast
print 'acast1='
print acast1
print ''
# Try calling the function with various argument types
try:
b=mclInit(None,0)
except Exception as ex:
print ex
raw_input("Exception occurred. b=mclInit(None,0) didn't work. Press Enter to continue")
print ''
try:
b=mclInit(byref(acast),0)
except Exception as ex:
print ex
raw_input("b=mclInit(byref(acast),0) didn't work. Press Enter to continue")
print ''
try:
b=mclInit(acast,0)
except Exception as ex:
print ex
raw_input("b=mclInit(acast,0) didn't work. Press Enter to continue")
print ''
try:
b=mclInit(byref(acast1),0)
except Exception as ex:
print ex
raw_input("mclInit(byref(acast1) didn't work. Press Enter to continue")
print ''
try:
b=mclInit(acast1,0)
except Exception as ex:
print ex
raw_input("b=mclInit(acast1,0) didn't work. Press Enter to continue")
print ''
try:
b=mclInit(byref(acast2),0)
except Exception as ex:
print ex
raw_input("mclInit(byref(acast2) didn't work. Press Enter to continue")
print ''
try:
b=mclInit(acast2,0)
except Exception as ex:
print ex
raw_input("b=mclInit(acast2,0) didn't work. Press Enter to continue")
print ''
raw_input("Reached the end!!!! Press enter to close")
Edit: Solo l'aggiunta nel eccezioni pitone getta
a=
None
acast=
<__main__.LP_c_char_p object at 0x00000000034E68C8>
acast1=
<ctypes.LP_c_char object at 0x00000000034E6948>
[Error -529697949] Windows Error 0xE06D7363
Exception occurred. b=mclInit(None,0) didn't work. Press Enter to continue
argument 1: <type 'exceptions.TypeError'>: expected LP_LP_c_char instance instea
d of pointer to LP_c_char_p
b=mclInit(byref(acast),0) didn't work. Press Enter to continue
argument 1: <type 'exceptions.TypeError'>: expected LP_LP_c_char instance instea
d of LP_c_char_p
b=mclInit(acast,0) didn't work. Press Enter to continue
[Error -529697949] Windows Error 0xE06D7363
mclInit(byref(acast1) didn't work. Press Enter to continue
[Error -529697949] Windows Error 0xE06D7363
b=mclInit(acast1,0) didn't work. Press Enter to continue
argument 1: <type 'exceptions.TypeError'>: expected LP_LP_c_char instance instea
d of pointer to LP_LP_c_char
mclInit(byref(acast2) didn't work. Press Enter to continue
[Error -529697949] Windows Error 0xE06D7363
b=mclInit(acast2,0) didn't work. Press Enter to continue
EDIT 2
Così si scopre mi mancava una chiamata a mclmcrInitialize()
come @eryksun aveva sottolineato . Ora posso chiamare le funzioni (evviva!) Ma l'inizializzazione non ha esito positivo :(. Quindi alcuni progressi, ma ancora lavoro da fare! Ecco il codice nel caso in cui è utile a chiunque.Ho un numero di chiamate a mclIsMCRInitialized()
e mclGetLastErrorMessage()
in . là che sono bulking le cose un po ', ma potrebbe fornire utili informazioni di debug
from ctypes import *
libmcr=cdll.mclmcrrt8_1
# Load mclmcr library
mclmcr_dll = cdll.LoadLibrary('C:\\Program Files\\MATLAB\\MATLAB Compiler Runtime\\v81\\bin\\win64\\mclmcr.dll')
# Load mclbase library
mclbase_dll = cdll.LoadLibrary('C:\\Program Files\\MATLAB\\MATLAB Compiler Runtime\\v81\\bin\\win64\\mclbase.dll')
# Call mclmcrInitialize()
mclmcrInit = mclmcr_dll.mclmcrInitialize
mclmcrInit.argtypes = None
mclmcrInit.restypes = c_bool
a = mclmcrInit()
print "mclmcrInitialize returned "
print a
# call mclIsMCRInitialized()
mclIsMCRInit = mclbase_dll.mclIsMCRInitialized
mclIsMCRInit.argtypes = None
mclIsMCRInit.restype = c_bool
b = mclIsMCRInit()
print "mclIsMCRInitialized = "
print b
# Call mclGetLastErrorMessage()
mclGetLastErrMsg = mclbase_dll.mclGetLastErrorMessage
mclGetLastErrMsg.argtypes = None
mclGetLastErrMsg.restypes = c_char_p
err = mclGetLastErrMsg()
print "mcl last error returns "
print err
# call mclInitializeApplication(NULL,0)
mclInit = mclbase_dll.mclInitializeApplication
mclInit.argtypes = [POINTER(c_char_p),c_size_t]
mclInit.restype = c_bool
b = mclInit(None,0)
print "mclInitializeApplication returned "
print b
# call mclIsMCRInitialized()
mclIsMCRInit = mclbase_dll.mclIsMCRInitialized
mclIsMCRInit.argtypes = None
mclIsMCRInit.restype = c_bool
b = mclIsMCRInit()
print "mclIsMCRInitialized = "
print b
# Call mclGetLastErrorMessage()
mclGetLastErrMsg = mclbase_dll.mclGetLastErrorMessage
mclGetLastErrMsg.argtypes = None
mclGetLastErrMsg.restypes = c_char_p
err = mclGetLastErrMsg()
print "mcl last error returns "
print err
# Call mclTerminateApplication()
mclTerminate = mclbase_dll.mclTerminateApplication
mclTerminate.argtypes = None
mclTerminate.restype = c_bool
f = mclTerminate()
print "mclTerminateApp returned "
print f
Ecco l'output in pitone:
mclmcrInitialize returned
-2147483647
mclIsMCRInitialized =
False
mcl last error returns
124384774
mclInitializeApplication returned
False
mclIsMCRInitialized =
False
mcl last error returns
128050512
mclTerminateApp returned
True
È solo 'mclInit (None, 0)'. Il fatto che tu stia vedendo un'eccezione VC++ non gestita ('0xE06D7363', cioè" msc ") implica un problema più profondo. C'è qualcosa che deve essere eseguito prima di inizializzare MATLAB? Vedo riferimenti a 'mclmcrInitialize'. – eryksun
Per inciso, i ctypes non supportano le eccezioni C++ in generale. Stai vedendo solo l'eccezione VC++ perché Microsoft lo implementa usando un'eccezione di Windows gestita da ctypes. Normalmente un'eccezione C++ non gestita interromperebbe il processo. – eryksun
Penso che la mia esclusione di 'mclmcrInitialize' possa essere parte del problema.Ho seguito il modulo generale fornito qui [collegamento] (http://blogs.mathworks.com/loren/2011/02/03/creating-c-shared-libraries-and-dlls/) che non sembra menzionarlo ma ora so di cercarlo, sto vedendo molto riferimento ad esso. Ti riporterò se avrò tutto pronto e funzionante! – ClaireM