Got Questions? Get Answers.
Discover MakerZone

MATLAB and Simulink resources for Arduino, LEGO, and Raspberry Pi

Learn more

Discover what MATLAB® can do for your career.

Opportunities for recent engineering grads.

Apply Today

Thread Subject:
Pass structure data using mex

Subject: Pass structure data using mex

From: Yi

Date: 28 Dec, 2012 23:27:09

Message: 1 of 3

Hi there, I'm writing a c-mex code to output a structure data from a structure matrix. The code works ok in the sense that I can see the returning data in Matlab. But when I run clear or run the code again, it just crashes the matlab.

I used a 1x3 structure matrix as input:

input(1).field_1='a1';
input(1).field_2=1.11;
input(1).field_3=[1,1,1];

input(2).field_1='a2';
input(2).field_2=2.22;
input(2).field_3=[2,2,2];

input(3).field_1='a3';
input(3).field_2=3.33;
input(3).field_3=[3,3,3];


and the c code I used looks like this:


#include "mex.h"
#include "matrix.h"

void mexFunction(int nlhs, mxArray *plhs[],int nrhs, const mxArray *prhs[])
{
const char **fnames;
int ifield, nfields;
mwSize dims[2]={1,1};
mwIndex nstruct=0;
mxArray *tmp_f1, *tmp_f2, *tmp_f3;

/* Check for proper number of arguments */
if (nrhs != 1) {
mexErrMsgTxt("One input arguments required.");
} else if (nlhs > 1) {
mexErrMsgTxt("Too many output arguments.");
} else if ((mxIsStruct(prhs[0]) != 1)){
mexErrMsgTxt("Input must be a structure matrix.");
}
    
nfields = mxGetNumberOfFields(prhs[0]);
fnames = (const char **)mxCalloc(nfields, sizeof(fnames));

for(ifield=0; ifield<nfields; ifield++)
{
fnames[ifield] = mxGetFieldNameByNumber(prhs[0],ifield);
}

plhs[0] = mxCreateStructArray(2, dims, nfields, fnames);
    
mxFree((void *)fnames);
    
const int namedim[2]={1,1};
tmp_f1=mxCreateCharArray(2,namedim);
tmp_f2=mxCreateDoubleMatrix(1,1,mxREAL);
tmp_f3=mxCreateDoubleMatrix(1,3,mxREAL);
    
tmp_f1 = mxGetFieldByNumber(prhs[0],nstruct,0);
tmp_f2 = mxGetFieldByNumber(prhs[0],nstruct,1);
tmp_f3 = mxGetFieldByNumber(prhs[0],nstruct,2);
    
mxSetFieldByNumber(plhs[0], nstruct, 0, tmp_f1);
mxSetFieldByNumber(plhs[0], nstruct, 1, tmp_f2);
mxSetFieldByNumber(plhs[0], nstruct, 2, tmp_f3);
}

After running, I can see input(1) exactlly in matlab. But I cannot run command like clear or something that might change the memory.

Is there anyone might have any idea about this problem?

Subject: Pass structure data using mex

From: Bruno Luong

Date: 29 Dec, 2012 08:55:10

Message: 2 of 3

You have to make deep copy of the field because it belongs to another variable.
Also you do not need to create the fields.

Bruno

#include "mex.h"
#include "matrix.h"

void mexFunction(int nlhs, mxArray *plhs[],int nrhs, const mxArray *prhs[])
{
    const char **fnames;
    int ifield, nfields;
    mwSize dims[2]={1,1};
    mwIndex nstruct=0;
    mxArray *tmp_f1, *tmp_f2, *tmp_f3;
    const int namedim[2]={1,1};
    
    /* Check for proper number of arguments */
    if (nrhs != 1) {
        mexErrMsgTxt("One input arguments required.");
    } else if (nlhs > 1) {
        mexErrMsgTxt("Too many output arguments.");
    } else if ((mxIsStruct(prhs[0]) != 1)){
        mexErrMsgTxt("Input must be a structure matrix.");
    }
    
    nfields = mxGetNumberOfFields(prhs[0]);
    fnames = (const char **)mxCalloc(nfields, sizeof(fnames));
    
    for(ifield=0; ifield<nfields; ifield++)
    {
        fnames[ifield] = mxGetFieldNameByNumber(prhs[0],ifield);
    }
    
    plhs[0] = mxCreateStructArray(2, dims, nfields, fnames);
    
    mxFree((void *)fnames);
    
    tmp_f1 = mxDuplicateArray(mxGetFieldByNumber(prhs[0],nstruct,0));
    tmp_f2 = mxDuplicateArray(mxGetFieldByNumber(prhs[0],nstruct,1));
    tmp_f3 = mxDuplicateArray(mxGetFieldByNumber(prhs[0],nstruct,2));
    
    mxSetFieldByNumber(plhs[0], nstruct, 0, tmp_f1);
    mxSetFieldByNumber(plhs[0], nstruct, 1, tmp_f2);
    mxSetFieldByNumber(plhs[0], nstruct, 2, tmp_f3);
}

Subject: Pass structure data using mex

From: Yi

Date: 30 Dec, 2012 21:19:10

Message: 3 of 3

Thank you soooooo much Bruno!!! It solves the problem!!!

"Bruno Luong" <b.luong@fogale.findmycountry> wrote in message <kbmb5e$m57$1@newscl01ah.mathworks.com>...
> You have to make deep copy of the field because it belongs to another variable.
> Also you do not need to create the fields.
>
> Bruno

Tags for this Thread

No tags are associated with this thread.

What are tags?

A tag is like a keyword or category label associated with each thread. Tags make it easier for you to find threads of interest.

Anyone can tag a thread. Tags are public and visible to everyone.

Contact us