Issues in Integrating Matlab generated cpp dll in C# application

Hi,
I have generated a cpp shared library using Matlab and integrated with C# application. I have started with a simple Matlab function to accept two numbers and return sum of those numbers. When I integrated with my C# application ,an Access Violation error is occurred and displays "Attempted to read or write protected memory"
Here is my C# code:
[DllImport(@"mclmcrrt8_3.dll")]
private static extern bool mclInitializeApplication_proxy(string options,Int32 count);
[DllImport(@"mclmcrrt8_3.dll")]
private static extern void mclTerminateApplication();
[DllImport("Add2nos.dll")]
private static extern bool Add2nosInitialize();
[DllImport("Add2nos.dll")]
private static extern void Add2nosTerminate();
[DllImport(@"mclmcrrt8_3.dll")]
private static extern IntPtr mxGetPr([In]IntPtr mxArray);
[DllImport(@"libmx.dll", CallingConvention = CallingConvention.Cdecl)]
private static extern IntPtr mxCreateDoubleScalar([In]double value);
[DllImport("Add2nos.dll", CallingConvention = CallingConvention.Cdecl)]
private static extern void mlxAdd2nos(int nargout, ref IntPtr c, [In]IntPtr a, [In]IntPtr b);
mclInitializeApplication_proxy("NULL", 0);//initialized successfully
Add2nosInitialize();//initialized successfully
IntPtr inValA = mxCreateDoubleScalar( 3.0 );
IntPtr inValB = mxCreateDoubleScalar(4.0);
IntPtr outVal = IntPtr.Zero;
mlxAdd2nos(1, ref outVal,inVal, inValB); //Exception generates here
When the dll function is called "Access violation Exception" occurs
My matlab version is : R2014a 64 bit Visual Studio : 2015 64 bit
Can any one tell me whats wrong with my code?
Thanks

5 Comments

Presumably your Cpp shared library is actually a C shared library?
That is, all the exported functions in your dll are wrapped in extern "C" {}
Pure C++ shared dll can only be called by C++ code compiled with the same compiler and compiling options.
Thanks for the reply
Yeah You are right.The function 'mlxAdd2Nos' is wrapped in extern C {} .
I compiled it as cpp shared library.
My Add2nos.h file is :
//
#ifndef __Add2nos_h
#define __Add2nos_h 1
#if defined(__cplusplus) && !defined(mclmcrrt_h) && defined(__linux__)
# pragma implementation "mclmcrrt.h"
#endif
#include "mclmcrrt.h"
#include "mclcppclass.h"
#ifdef __cplusplus
extern "C" {
#endif
#if defined(__SUNPRO_CC)
/* Solaris shared libraries use __global, rather than mapfiles
* to define the API exported from a shared library. __global is
* only necessary when building the library -- files including
* this header file to use the library do not need the __global
* declaration; hence the EXPORTING_<library> logic.
*/
#ifdef EXPORTING_Add2nos
#define PUBLIC_Add2nos_C_API __global
#else
#define PUBLIC_Add2nos_C_API /* No import statement needed. */
#endif
#define LIB_Add2nos_C_API PUBLIC_Add2nos_C_API
#elif defined(_HPUX_SOURCE)
#ifdef EXPORTING_Add2nos
#define PUBLIC_Add2nos_C_API __declspec(dllexport)
#else
#define PUBLIC_Add2nos_C_API __declspec(dllimport)
#endif
#define LIB_Add2nos_C_API PUBLIC_Add2nos_C_API
#else
#define LIB_Add2nos_C_API
#endif
/* This symbol is defined in shared libraries. Define it here
* (to nothing) in case this isn't a shared library.
*/
#ifndef LIB_Add2nos_C_API
#define LIB_Add2nos_C_API /* No special import/export declaration */
#endif
extern LIB_Add2nos_C_API
bool MW_CALL_CONV Add2nosInitializeWithHandlers(
mclOutputHandlerFcn error_handler,
mclOutputHandlerFcn print_handler);
extern LIB_Add2nos_C_API
bool MW_CALL_CONV Add2nosInitialize(void);
extern LIB_Add2nos_C_API
void MW_CALL_CONV Add2nosTerminate(void);
extern LIB_Add2nos_C_API
void MW_CALL_CONV Add2nosPrintStackTrace(void);
extern LIB_Add2nos_C_API
bool MW_CALL_CONV mlxAdd2nos(int nlhs, mxArray *plhs[], int nrhs, mxArray *prhs[]);
#ifdef __cplusplus
}
#endif
#ifdef __cplusplus
/* On Windows, use __declspec to control the exported API */
#if defined(_MSC_VER) || defined(__BORLANDC__)
#ifdef EXPORTING_Add2nos
#define PUBLIC_Add2nos_CPP_API __declspec(dllexport)
#else
#define PUBLIC_Add2nos_CPP_API __declspec(dllimport)
#endif
#define LIB_Add2nos_CPP_API PUBLIC_Add2nos_CPP_API
#else
#if !defined(LIB_Add2nos_CPP_API)
#if defined(LIB_Add2nos_C_API)
#define LIB_Add2nos_CPP_API LIB_Add2nos_C_API
#else
#define LIB_Add2nos_CPP_API /* empty! */
#endif
#endif
#endif
extern LIB_Add2nos_CPP_API void MW_CALL_CONV Add2nos(int nargout, mwArray& c, const mwArray& a, const mwArray& b);
#endif
#endif
The cpp function name is Add2nos which accepts mwArray argument type.
The definition of cpp function in Add2nos.h is:
extern LIB_Add2nos_CPP_API void MW_CALL_CONV Add2nos(int nargout, mwArray& c, const mwArray& a, const mwArray& b);
But i dont know exactly , how to pass C# data to mwArray .
Any help on this is appreciated.
Thanks
Since you are using C# to write your driver code, is it possible for you to compile your MATLAB code into a .NET assembly instead of a C++ shared library?
This may only be a matter of semantics, but I'll say it again:
A C++ shared library can only be used by C++ code compiled with the same compiler and compiling options. It can't be used from .Net. It can't be used from matlab. If you do you'll likely get access violations. That is because the C++ ABI is not standardised.
A C shared library has no such problem. You can create a C shared library from C++ code as long as you wrap all exported functions in extern "C" and that those functions only use standard C types and do not throw exceptions.
Yeah.I Got it .Thank you All...

Sign in to comment.

Answers (0)

Asked:

on 13 Jun 2016

Commented:

on 21 Jun 2016

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!