Why does mxSetDoubles crash this MEX file?

2 visualizzazioni (ultimi 30 giorni)
Brian Bagenstose
Brian Bagenstose il 10 Dic 2019
Modificato: James Tursa il 12 Dic 2019
Here's the MEX function:
#include "mex.h"
void myFun(double *a, int array_size)
{
int i;
for (i=0;i<array_size;i++)
a[i] = a[i]+1;
}
void mexFunction( int nlhs, mxArray *plhs[],
int nrhs, const mxArray *prhs[])
{
int array_size;
double *a;
array_size = mxGetNumberOfElements(prhs[0]);
a = mxGetDoubles(prhs[0]);
myFun(a,array_size);
plhs[0] = mxCreateDoubleMatrix((mwSize) 1,(mwSize) array_size, mxREAL);
mxSetDoubles(plhs[0],a);
}
The result is as follows:
>> mex -R2018a simpleEx.c
Building with 'Microsoft Visual C++ 2017 (C)'.
MEX completed successfully.
>> simpleEx([5 4 2])
ans =
6 5 3
>> simpleEx([5 4 2])
ans =
7 6 4
>> simpleEx([5 4 2])
* MATLAB crashes with no log file*
Why does the memory get "cached" so the second time, the results are one higher than expected? And why does mxSetDoubles crash everything on the third run? I know it's that function because if I comment it out, it doesn't crash and the output is just zero's.
Thanks!

Risposte (1)

James Tursa
James Tursa il 11 Dic 2019
Modificato: James Tursa il 12 Dic 2019
This line is crashing your code:
mxSetDoubles(plhs[0],a);
You can't re-use data pointers this way. You have essentially shared the data pointers between plhs[0] and prhs[0] but MATLAB doesn't know that they are sharing data pointers. So when one variable gets deleted the data pointer becomes invalid. And when the other variable (now having an invalid data pointer) tries to access the data pointer it crashes. (You also created a permanent memory leak but that is another issue).
In addition, you generally shouldn't modify the data of a prhs[ ] variable in place as that can affect other variables. So myFun( ) is non-conforming.
In general, you should use mxDuplicateArray to generate a plhs[0] variable, and then modify the data of that variable in-place. E.g.,
array_size = mxGetNumberOfElements(prhs[0]);
plhs[0] = mxDuplicateArray(prhs[0]);
a = mxGetDoubles(plhs[0]);
myFun(a,array_size);

Categorie

Scopri di più su Write C Functions Callable from MATLAB (MEX Files) in Help Center e File Exchange

Tag

Prodotti


Release

R2019b

Community Treasure Hunt

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

Start Hunting!

Translated by