How can I make memory persistent between calls to a MEX-file in MATLAB?
11 Ansichten (letzte 30 Tage)
Ältere Kommentare anzeigen
MathWorks Support Team
am 25 Okt. 2013
Beantwortet: James Tursa
am 2 Jan. 2024
I would like to know if memory allocated with mxCalloc remains persistent between calls to a MEX-file.
Akzeptierte Antwort
MathWorks Support Team
am 25 Okt. 2013
By default, in a MEX-file, mxCalloc generates non-persistent mxCalloc data. In other words, the memory management facility automatically de-allocates the memory as soon as the MEX-file ends. If you want the memory to persist after the MEX-file completes, call mexMakeMemoryPersistent after calling mxCalloc. If you write a MEX-file with persistent memory, be sure to register a mexAtExit function to free allocated memory in the event your MEX-file is cleared.
For example:
// test.c
#include <stdlib.h>
#include "mex.h"
static double *myarray = NULL;
double *pr;
void exitFcn() {
if (myarray != NULL)
mxFree(myarray);
}
void mexFunction(int nlhs,mxArray *plhs[],int nrhs, const mxArray *prhs[])
{
if (nrhs<1 | mxIsChar(prhs[0]))
mexErrMsgTxt("Must have one non-string input");
if (myarray==NULL) {
/* since myarray is initialized to NULL, we know
this is the first call of the MEX-function
after it was loaded. Therefore, we should
set up myarray and the exit function. */
/* Allocate array. Use mexMackMemoryPersistent to make the allocated memory persistent in subsequent calls*/
mexPrintf("First call to MEX-file\n");
myarray = mxCalloc(1,8);
mexMakeMemoryPersistent(myarray);
mexAtExit(exitFcn);
}
mexPrintf("Old string was '%f'.\n",myarray[0]);
pr = mxGetPr(prhs[0]);
mexPrintf("New string is '%f'.\n",pr[0]);
memcpy((char*)myarray,(char*)mxGetPr(prhs[0]), sizeof(double));
}
You can compile this MEX-file with the following command:
mex test.c
To run the MEX-file, pass in a single number. For example:
test(3)
Repetitive calls to the test MEX-file will show that the previous input is stored between calls. To clear the MEX-file from memory, use the command:
clear mex
For more information on persistent variables in MEX-files, refer to the relevent documentation by entering the following at the MATLAB prompt:
doc mexMakeArrayPersistent
and
doc mexMakeMemoryPersistent
0 Kommentare
Weitere Antworten (1)
James Tursa
am 2 Jan. 2024
So, the accepted answer has bugs. Namely:
- They don't include the header for memcpy
- They don't check the input argument properly
Either of these can lead to a MATLAB crash if the input isn't as expected. Corrected and more robust code that doesn't rely on the messy memcpy and can correctly handle unexpected or missing input argument is:
// test.c
#include "mex.h"
static double *myarray = NULL;
void exitFcn() {
if (myarray != NULL)
mexPrintf("Free'ing the persistent memory\n");
mxFree(myarray);
}
void mexFunction(int nlhs,mxArray *plhs[],int nrhs, const mxArray *prhs[])
{
if (myarray==NULL) {
/* since myarray is initialized to NULL, we know
this is the first call of the MEX-function
after it was loaded. Therefore, we should
set up myarray and the exit function. */
/* Allocate array. Use mexMakeMemoryPersistent to make the allocated memory persistent in subsequent calls*/
mexPrintf("First call to MEX-file\n");
myarray = mxCalloc(1,8);
mexMakeMemoryPersistent(myarray);
mexAtExit(exitFcn);
}
mexPrintf("Old value was '%f'.\n",myarray[0]);
if( nrhs ) {
if (!mxIsNumeric(prhs[0]) || mxGetNumberOfElements(prhs[0]) == 0)
mexErrMsgTxt("Input must be non-empty numeric");
myarray[0] = mxGetScalar(prhs[0]);
mexPrintf("New value is '%f'.\n",myarray[0]);
}
}
0 Kommentare
Siehe auch
Kategorien
Mehr zu Write C Functions Callable from MATLAB (MEX Files) finden Sie in Help Center und File Exchange
Produkte
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!