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:
dot product in mex file

Subject: dot product in mex file

From: Toan Cao

Date: 3 Sep, 2013 02:34:08

Message: 1 of 7

Hi,
I am using function "ddot" in BLAS.h library for computing dot product between two 3D vectors in a C mex file. My usage for this function as follows:
------------------------------------------------------
....
#include "blas.h"
....
int dot_len, dot_inc1, dot_inc2 ;
mxArray *p_C1, *p_C2 ;
double *C1, *C2, Out ;
....
p_C1 = mxCreateDoubleMatrix(3,1, mxREAL);
p_C2 = mxCreateDoubleMatrix(3,1, mxREAL);
C1 = mxGetPr(p_C1);
C2 = mxGetPr(p_C2);
....
dot_len =3;
dot_inc1 =1;
dot_inc2 =1;
Out= ddot(&dot_len,C1,&dot_inc1,C2,&dot_inc2);
------------------------------------------------------------------
when i compile, i receive error:
" error C2664: 'ddot' : cannot convert parameter 1 from 'int *' to 'ptrdiff_t *'.
Types pointed to are unrelated; conversion requires reinterpret_cast, C-style cast or function-style cast"

Although my usage is followed the definition of this function:
DOUBLE PRECISION function ddot (integer N,
                                                 double precision, dimension(*) DX,
                                                 integer INCX,
                                                 double precision, dimension(*) DY,
                                                 integer INCY
                                                 )

So, if you have used this function, can you tell me what is the reason of my problem?
Thanks in advance!
Toan

Subject: dot product in mex file

From: James Tursa

Date: 3 Sep, 2013 06:14:06

Message: 2 of 7

"Toan Cao" <toancv3010@gmail.com> wrote in message <l03hr0$98m$1@newscl01ah.mathworks.com>...
> Hi,
> I am using function "ddot" in BLAS.h library for computing dot product between two 3D vectors in a C mex file. My usage for this function as follows:
> ------------------------------------------------------
> ....
> #include "blas.h"
> ....
> int dot_len, dot_inc1, dot_inc2 ;
> mxArray *p_C1, *p_C2 ;
> double *C1, *C2, Out ;
> ....
> p_C1 = mxCreateDoubleMatrix(3,1, mxREAL);
> p_C2 = mxCreateDoubleMatrix(3,1, mxREAL);
> C1 = mxGetPr(p_C1);
> C2 = mxGetPr(p_C2);
> ....
> dot_len =3;
> dot_inc1 =1;
> dot_inc2 =1;
> Out= ddot(&dot_len,C1,&dot_inc1,C2,&dot_inc2);
> ------------------------------------------------------------------
> when i compile, i receive error:
> " error C2664: 'ddot' : cannot convert parameter 1 from 'int *' to 'ptrdiff_t *'.
> Types pointed to are unrelated; conversion requires reinterpret_cast, C-style cast or function-style cast"
>
> Although my usage is followed the definition of this function:
> DOUBLE PRECISION function ddot (integer N,
> double precision, dimension(*) DX,
> integer INCX,
> double precision, dimension(*) DY,
> integer INCY
> )
>
> So, if you have used this function, can you tell me what is the reason of my problem?
> Thanks in advance!
> Toan

The BLAS versions that MATLAB uses can use 32-bit or 64-bit integer arguments depending on system and settings. Regardless of what the Fortran signature is, use mwSignedIndex for integer arguments in BLAS routines for MATLAB mex routines. mwSignedIndex will appropriately be set to a 32-bit or 64-bit integer for your particular setup. E.g.,

mwSignedIndex dot_len, dot_inc1, dot_inc2 ;


James Tursa

Subject: dot product in mex file

From: Toan Cao

Date: 3 Sep, 2013 13:45:08

Message: 3 of 7

> The BLAS versions that MATLAB uses can use 32-bit or 64-bit integer arguments depending on system and settings. Regardless of what the Fortran signature is, use mwSignedIndex for integer arguments in BLAS routines for MATLAB mex routines. mwSignedIndex will appropriately be set to a 32-bit or 64-bit integer for your particular setup. E.g.,
>
> mwSignedIndex dot_len, dot_inc1, dot_inc2 ;
>
>
> James Tursa

Hi James,
I already used mwSignedIndex type for 3 variables dot_len, dot_inc1, dot_inc2 but the problem is the same:
 " error C2664: 'ddot' : cannot convert parameter 1 from 'mwSignedIndex *' to 'ptrdiff_t *'
 Types pointed to are unrelated; conversion requires reinterpret_cast, C-style cast or function-style cast"

I also try to declare these variables with type ptrdiff_t after adding more one header <stddef.h>. The following error occur:
"fatal error LNK1120: 1 unresolved externals"

My Operating system is 64-bit, and the compiler is Microsoft Visual C++ 2008 SP1.
With your experience, can you show me what should i do ?
Thank you so much.

Toan

Subject: dot product in mex file

From: James Tursa

Date: 3 Sep, 2013 16:51:06

Message: 4 of 7

"Toan Cao" <toancv3010@gmail.com> wrote in message <l04p54$sp6$1@newscl01ah.mathworks.com>...
> > The BLAS versions that MATLAB uses can use 32-bit or 64-bit integer arguments depending on system and settings. Regardless of what the Fortran signature is, use mwSignedIndex for integer arguments in BLAS routines for MATLAB mex routines. mwSignedIndex will appropriately be set to a 32-bit or 64-bit integer for your particular setup. E.g.,
> >
> > mwSignedIndex dot_len, dot_inc1, dot_inc2 ;
> >
> >
> > James Tursa
>
> Hi James,
> I already used mwSignedIndex type for 3 variables dot_len, dot_inc1, dot_inc2 but the problem is the same:
> " error C2664: 'ddot' : cannot convert parameter 1 from 'mwSignedIndex *' to 'ptrdiff_t *'
> Types pointed to are unrelated; conversion requires reinterpret_cast, C-style cast or function-style cast"
>
> I also try to declare these variables with type ptrdiff_t after adding more one header <stddef.h>. The following error occur:
> "fatal error LNK1120: 1 unresolved externals"
>
> My Operating system is 64-bit, and the compiler is Microsoft Visual C++ 2008 SP1.
> With your experience, can you show me what should i do ?
> Thank you so much.
>
> Toan

I'm surprised the mwSignedIndex didn't work. That is always supposed to work for the MATLAB supplied BLAS libraries. But the fact that using ptrdiff_t didn't work and you got a link error even after the compiler told you that is what it was expecting leads me to believe there is something wrong in your setup or linking. What commands are you using to compile with? What specific BLAS library are you attempting to link with (the MATLAB supplied library or another one)?

James Tursa

Subject: dot product in mex file

From: Toan Cao

Date: 3 Sep, 2013 18:33:09

Message: 5 of 7

> I'm surprised the mwSignedIndex didn't work. That is always supposed to work for the MATLAB supplied BLAS libraries. But the fact that using ptrdiff_t didn't work and you got a link error even after the compiler told you that is what it was expecting leads me to believe there is something wrong in your setup or linking. What commands are you using to compile with? What specific BLAS library are you attempting to link with (the MATLAB supplied library or another one)?
>
> James Tursa

Hi James,

I write down here my code and hope that you can reveal my problem. The name of saved file is testC.
-----------------------------------------------------------------------
#include <stdio.h>
#include <math.h>
#include "mex.h"
#include "matrix.h"
#include <string.h>
#include "lapack.h"
#include "blas.h"

void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
    #define p_Errc plhs[0]
    #define p_x prhs[0]
    #define p_graph prhs[1]
    #define p_Rot_num prhs[2]
    #define p_Reg_num prhs[3]
    #define p_Wrot prhs[4]
    #define p_Wreg prhs[5]
    #define p_Wpos prhs[6]

    unsigned short i, j, k, l, x_len , nfields, graph_len;
    mwSignedIndex dot_len, dot_inc1, dot_inc2;
    mwSignedIndex dims[3];
    double *x,*Errc,*Errc_Rot,*Errc_Reg, *Errc_Pos, *RT_mat;
    double *C1, *C2, *C3;
    mxArray *p_RT, *p_Errc_Rot, *p_Errc_Reg, *p_Errc_Pos;
    mxArray *p_C1, *p_C2, *p_C3;
    double Wrot, Wreg, Wpos, sqr_Wrot, sqr_Wreg, sqr_Wpos;
    double Rot_num, Reg_num;
    
    if(nrhs < 1 || nrhs > 7) /* Check the number of arguments */
        mexErrMsgTxt("Wrong number of input arguments.");
    else if(nlhs > 1)
        mexErrMsgTxt("Too many output arguments.");
    else if(!mxIsStruct(p_graph))
        mexErrMsgTxt("graph is not a structure.");
    
    x = mxGetPr(p_x);
    x_len = mxGetM(p_x); /* Get the length of variable x */
    nfields = mxGetNumberOfFields(p_graph);
    graph_len = mxGetNumberOfElements(p_graph); /* Get the length of graph */
    
// mexPrintf("\n The length of variable x is:%d \n",x_len);
// mexPrintf("\n Number of graph elements is: %d\n",graph_len);
    if(x_len != 15*graph_len)
       mexErrMsgTxt("Number of input variables and number of graph variables are not equal.");
    
    Wrot = mxGetScalar(p_Wrot);
    Wreg = mxGetScalar(p_Wreg);
    Wpos = mxGetScalar(p_Wpos);
    sqr_Wrot = sqrt(Wrot);
    sqr_Wreg = sqrt(Wreg);
    sqr_Wpos = sqrt(Wpos);
    Rot_num = mxGetScalar(p_Rot_num);
    Reg_num = mxGetScalar(p_Reg_num);
    
    p_Errc_Rot = mxCreateDoubleMatrix(Rot_num,1, mxREAL);
    Errc_Rot = mxGetPr(p_Errc_Rot); // Rotation term
    p_Errc_Reg = mxCreateDoubleMatrix(Reg_num,1, mxREAL);
    Errc_Reg = mxGetPr(p_Errc_Reg); // Regularization term
    p_Errc_Pos = mxCreateDoubleMatrix(graph_len,1, mxREAL);
    Errc_Pos = mxGetPr(p_Errc_Pos); // Position term
    

    dot_len =3;
    dot_inc1 =1;
    dot_inc2 =1;
    for(k=0;k<=graph_len-1;k++)
    {
        p_C1 = mxCreateDoubleMatrix(3,1, mxREAL);
        p_C2 = mxCreateDoubleMatrix(3,1, mxREAL);
        p_C3 = mxCreateDoubleMatrix(3,1, mxREAL);
        C1 = mxGetPr(p_C1); // first column of rotation matrix
        C2 = mxGetPr(p_C2); // second column of rotation matrix
        C3 = mxGetPr(p_C3); // third column of rotation matrix
        for(i=0;i<=2;i++){
           C1[i] = x[i +0*3+k*3*5];
           C2[i] = x[i +1*3+k*3*5];
           C3[i] = x[i +2*3+k*3*5];
        }
        // PROBLEM OCCUR HERE
        Errc_Rot[6*k] = sqr_Wrot*ddot(&dot_len,C1,&dot_inc1,C2,&dot_inc2);
   /* Errc_Rot[6*k+1] = sqr_Wrot*ddot(&dot_len,C1,&dot_inc1,C3,&dot_inc2);
        Errc_Rot[6*k+2] = sqr_Wrot*ddot(&dot_len,C2,&dot_inc1,C3,&dot_inc2);
        Errc_Rot[6*k+3] = sqr_Wrot*(ddot(&dot_len,C1,&dot_inc1,C1,&dot_inc2)-1);
        Errc_Rot[6*k+4] = sqr_Wrot*(ddot(&dot_len,C2,&dot_inc1,C2,&dot_inc2)-1);
        Errc_Rot[6*k+5] = sqr_Wrot*(ddot(&dot_len,C3,&dot_inc1,C3,&dot_inc2)-1);
   */

        if(k<graph_len-1){ // Will be removed
           mxDestroyArray(p_C1);
           mxDestroyArray(p_C2);
           mxDestroyArray(p_C3);
        }
    }
    dims[0]= 3;
    dims[1]= 5;
    dims[2]= graph_len;
    // Create a 3D matrix of double type
    p_RT = mxCreateNumericArray(3, dims, mxDOUBLE_CLASS, mxREAL);
    RT_mat = (double *)mxGetData(p_RT);
    for(k=0; k<= graph_len -1; k++)
       for(j=0; j<=4;j++)
          for(i=0; i<=2;i++)
              RT_mat[i +j*3+k*3*5]= x[i +j*3+k*3*5];
  
    //-------------------------------------------
    p_Errc = mxCreateDoubleMatrix(3,1, mxREAL);
    Errc = (double *)mxGetData(p_Errc);
    memcpy(Errc, C1, 3*mxGetElementSize(p_C1));
    
    mxDestroyArray(p_RT);
    mxDestroyArray(p_Errc_Rot);
    mxDestroyArray(p_Errc_Reg);
    mxDestroyArray(p_Errc_Pos);
    //-------------------------------------------
    return;
}
-----------------------------------------------------------------------

When i save this file as testC.c and compile with command: mex testC.c.
=> The error is: fatal error LNK1120: 1 unresolved externals
However, when i save this file as testC.cpp and compile with command: mex testC.c.
=> The error is: error C2664: 'ddot' : cannot convert parameter 1 from 'mwSignedIndex *' to 'ptrdiff_t *'

But i can not detect where error comes ? How is your opinion ?
Thank you.

Toan

 

Subject: dot product in mex file

From: James Tursa

Date: 3 Sep, 2013 18:52:06

Message: 6 of 7

"Toan Cao" <toancv3010@gmail.com> wrote in message <l05a15$r2f$1@newscl01ah.mathworks.com>...

(snip)

> When i save this file as testC.c and compile with command: mex testC.c.
> => The error is: fatal error LNK1120: 1 unresolved externals
> However, when i save this file as testC.cpp and compile with command: mex testC.c.
> => The error is: error C2664: 'ddot' : cannot convert parameter 1 from 'mwSignedIndex *' to 'ptrdiff_t *'
>
> But i can not detect where error comes ? How is your opinion ?

Before I look at your code, I notice that your mex command does not include the BLAS library. You need to include this manually ... MATLAB does not automatically link this in for you. E.g., try this

lib_blas = [matlabroot '\extern\lib\win64\microsoft\libmwblas.lib'];
mex('testC.c',lib_blas)

James Tursa

Subject: dot product in mex file

From: Toan Cao

Date: 3 Sep, 2013 20:08:12

Message: 7 of 7

"James Tursa" wrote in message <l05b4m$grf$1@newscl01ah.mathworks.com>...
> "Toan Cao" <toancv3010@gmail.com> wrote in message <l05a15$r2f$1@newscl01ah.mathworks.com>...
>
> (snip)
>
> > When i save this file as testC.c and compile with command: mex testC.c.
> > => The error is: fatal error LNK1120: 1 unresolved externals
> > However, when i save this file as testC.cpp and compile with command: mex testC.c.
> > => The error is: error C2664: 'ddot' : cannot convert parameter 1 from 'mwSignedIndex *' to 'ptrdiff_t *'
> >
> > But i can not detect where error comes ? How is your opinion ?
>
> Before I look at your code, I notice that your mex command does not include the BLAS library. You need to include this manually ... MATLAB does not automatically link this in for you. E.g., try this
>
> lib_blas = [matlabroot '\extern\lib\win64\microsoft\libmwblas.lib'];
> mex('testC.c',lib_blas)
>
> James Tursa

Thanks James, the code works after adding BLAS library.
Uhmmmm, i am also noted that if i save the testC file as C file (testC.c), the code works for both types "mwSignedIndex" and "ptrdiff_t". However, if i save the testC file as C++ file (testC.cpp), the code only works for types "ptrdiff_t", not for "mwSignedIndex"

Toan

Toan

Tags for 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