The Wayback Machine - https://web.archive.org/web/20110912141256/http://www.mathworks.com:80/help/techdoc/matlab_external/f33356.html
Skip to Main Content Skip to Search
Product Documentation

Fortran Source MEX-Files

The Components of a Fortran MEX-File

You create binary MEX-files using the mex build script. mex compiles and links source MEX-file files into a shared library called a binary MEX-file, which you can run from the MATLAB command line. Once compiled, you treat binary MEX-files like MATLAB functions.

This section explains the components of a source MEX-file, statements you use in a program source file. Unless otherwise specified, the term "MEX-file" refers to a source file.

The MEX-file consists of:

Gateway Routine

The gateway routine is the entry point to the MEX-file shared library. It is through this routine that MATLAB accesses the rest of the routines in your MEX-files. Use the following guidelines to create a gateway routine:

A Fortran MEX-file gateway routine looks like this:

C     The gateway routine.
      subroutine mexFunction(nlhs, plhs, nrhs, prhs)
      integer nlhs, nrhs
      mwpointer plhs(*), prhs(*)

Naming the Gateway Routine

The name of the gateway routine must be mexFunction.

Required Parameters

A gateway routine must contain the parameters prhs, nrhs, plhs, and nlhs described in the following table.

ParameterDescription
prhsAn array of right-hand input arguments.
plhsAn array of left-hand output arguments.
nrhsThe number of right-hand arguments, or the size of the prhs array.
nlhsThe number of left-hand arguments, or the size of the plhs array.

Declare prhs and plhs as type mxArray *, which means they point to MATLAB arrays. They are vectors that contain pointers to the arguments of the MEX-file.

You can think of the name prhs as representing the "parameters, right-hand side," that is, the input parameters. Likewise, plhs represents the "parameters, left-hand side," or output parameters.

Creating and Using Source Files

It is good practice to write the gateway routine to call a Computational Routine; however, this is not required. The computational code can be part of the gateway routine. If you use both gateway and computational routines, you can combine them into one source file or into separate files. If you use separate files, the gateway routine must be the first source file listed in the mex command.

The name of the file containing your gateway routine is important, as explained in Naming the MEX-File.

Name your Fortran source file with an uppercase .F file extension.

The Difference Between .f and .F Files.  Fortran compilers assume source files using a lowercase .f file extension have been preprocessed. On most platforms, mex makes sure the file is preprocessed regardless of the file extension. However, on Apple Macintosh platforms, mex cannot force preprocessing. Use an uppercase .F file extension to ensure your Fortran MEX-file is platform independent.

Using MATLAB Libraries

The MATLAB C/C++ and Fortran API Reference describes functions you can use in your gateway and computational routines that interact with MATLAB programs and the data in the MATLAB workspace. The MX Matrix Library functions provide access methods for manipulating MATLAB arrays. The MEX Library functions perform operations in the MATLAB environment.

Required Header Files

To use the functions in the C/C++ and Fortran API Reference library you must include the fintrf header file, which declares the entry point and interface routines. Put this statement in your source file:

#include "fintrf.h"

Naming the MEX-File

The binary MEX-file name, and hence the name of the function you use in MATLAB, is the name of the source file containing your gateway routine.

The file extension of the binary MEX-file is platform-dependent. You find the file extension using the mexext function, which returns the value for the current machine.

Computational Routine

The computational routine contains the code for performing the computations you want implemented in the binary MEX-file. Computations can be numerical computations as well as inputting and outputting data. The gateway calls the computational routine as a subroutine.

The programming requirements described in Creating and Using Source Files, Using MATLAB Libraries, and Required Header Files might also apply to your computational routine.

Preprocessor Macros

The MX Matrix and MEX libraries use the MATLAB preprocessor macros mwSize and mwIndex for cross-platform flexibility. mwSize represents size values, such as array dimensions and number of elements. mwIndex represents index values, such as indices into arrays.

MATLAB has an additional preprocessor macro for Fortran files, mwPointer. MATLAB uses a unique data type, the mxArray. Because you cannot create a new data type in Fortran, MATLAB passes a special identifier, created by the mwPointer preprocessor macro, to a Fortran program. This is how you get information about an mxArray in a native Fortran data type. For example, you can find out the size of the mxArray, determine whether or not it is a string, and look at the contents of the array. Use mwPointer to build platform-independent code.

The Fortran preprocessor converts mwPointer to integer*4 when building binary MEX-files on 32-bit platforms and to integer*8 when building on 64-bit platforms.

Using the Fortran %val Construct

The Fortran %val(arg) construct specifies that an argument, arg, is to be passed by value, instead of by reference. The %val construct is supported by most, but not all, Fortran compilers.

If your compiler does not support the %val construct, you must copy the array values into a temporary true Fortran array using the mxCopy* routines (for example, mxCopyPtrToReal8).

A %val Construct Example

If your compiler supports the %val construct, you can use routines that point directly to the data (that is, the pointer returned by mxGetPr or mxGetPi). You can use %val to pass this pointer's contents to a subroutine, where it is declared as a Fortran double-precision matrix.

For example, consider a gateway routine that calls its computational routine, yprime, by:

call yprime(%val(yp), %val(t), %val(y))

If your Fortran compiler does not support the %val construct, you would replace the call to the computational subroutine with:

C Copy array pointers to local arrays.
       call mxCopyPtrToReal8(t, tr, 1)
       call mxCopyPtrToReal8(y, yr, 4)
C
C Call the computational subroutine.
       call yprime(ypr, tr, yr)
C
C Copy local array to output array pointer.
       call mxCopyReal8ToPtr(ypr, yp, 4)

You must also add the following declaration line to the top of the gateway routine:

real*8 ypr(4), tr, yr(4)

Note that if you use mxCopyPtrToReal8 or any of the other mxCopy* routines, the size of the arrays declared in the Fortran gateway routine must be greater than or equal to the size of the inputs to the MEX-file coming in from MATLAB. Otherwise, mxCopyPtrToReal8 does not work correctly.

Data Flow in MEX-Files

The following examples illustrate data flow in MEX-files:

Showing Data Input and Output

Suppose your MEX-file myFunction has two input arguments and one output argument. The MATLAB syntax is [X] = myFunction(Y, Z). To call myFunction from MATLAB, type:

X = myFunction(Y, Z);

The MATLAB interpreter calls mexFunction, the gateway routine to myFunction, with the following arguments:

 Figure showing call to a MEX-function with the arguments nlhs, nrhs, plhs, and prhs.

Your input is prhs, a two-element array (nrhs = 2). The first element is a pointer to an mxArray named Y and the second element is a pointer to an mxArray named Z.

Your output is plhs, a one-element array (nlhs = 1) where the single element is a null pointer. The parameter plhs points at nothing because the output X is not created until the subroutine executes.

The gateway routine creates the output array and sets a pointer to it in plhs[0]. If the routine does not assign a value to plhs[0] but you assign an output value to the function when you call it, MATLAB generates an error.

Gateway Routine Data Flow Diagram

The following MEX Cycle diagram shows how inputs enter a MEX-file, what functions the gateway routine performs, and how outputs return to MATLAB.

In this example, the syntax of the MEX-file func is [C, D] = func(A,B). In the figure, a call to func tells MATLAB to pass variables A and B to your MEX-file. C and D are left unassigned.

The gateway routine func.F uses the mxCreate* functions to create the MATLAB arrays for your output arguments. It sets plhs[0] and plhs[1] to the pointers to the newly created MATLAB arrays. It uses the mxGet* functions to extract your data from your input arguments prhs[0] and prhs[1]. Finally, it calls your computational routine, passing the input and output data pointers as function parameters.

MATLAB assigns plhs[0] to C and plhs[1] to D.

Fortran MEX Cycle

Figure: Fortran MEX cycle

MATLAB Example timestwo.F

Let's look at an example, timestwo.F, found in your matlabroot/extern/examples/refbook folder. (Building MEX-Files explains how to create the binary MEX-file.) Its calling syntax is Y = timestwo(X), where X is a number. Type:

x = 99;
y = timestwo(x)

MATLAB displays:

y =
   198

The gateway routine validates the input arguments. This step includes checking the number, type, and size of the input arrays as well as examining the number of output arrays. If the inputs are not valid, call mexErrMsgIdAndTxt. For example:

C Check for proper number of arguments. 
      if(nrhs .ne. 1) then
         call mexErrMsgIdAndTxt ('timestwo.F', 'One input required.')
      elseif(nlhs .gt. 1) then
         call mexErrMsgIdAndTxt ('timestwo.F', 'Too many output arguments.')
      endif

C Check that the input is a number.
      if(mxIsNumeric(prhs(1)) .eq. 0) then
         call mexErrMsgIdAndTxt ('timestwo.F', 'Input must be a number.')
      endif

To create MATLAB arrays, call one of the mxCreate* functions, like mxCreateDoubleMatrix, mxCreateSparse, or mxCreateString. If it needs them, the gateway routine can call mxCalloc to allocate temporary work arrays for the computational routine. In this example:

C Create matrix for the return argument.
      plhs(1) = mxCreateDoubleMatrix(mrows,ncols,0)

In the gateway routine, you access the data in mxArray and manipulate it in your computational subroutine. For example, the expression mxGetPr(prhs[0]) returns a pointer of type double * to the real data in the mxArray pointed to by prhs[0]. You can then use this pointer like any other pointer of type double * in Fortran. For example:

C Create Fortran array from the input argument.
      inputptr = mxGetPr(prhs(1))
      call mxCopyPtrToReal8(inputptr,finput,nelements)

In this example, a computational routine, timestwo, performs the calculations:

C Call the computational subroutine.
      call timestwo(foutput, finput)

After calling your computational routine from the gateway, you can set a pointer of type mxArray to the data it returns. MATLAB recognizes the output from your computational routine as the output from the binary MEX-file.

C Load the data into outputptr, which is the output to MATLAB.
      call mxCopyReal8ToPtr(foutput,outputptr,nelements)

When a binary MEX-file completes its task, it returns control to MATLAB. MATLAB automatically destroys any arrays created by the MEX-file not returned through the left-hand side arguments.

In general, we recommend that MEX-file functions destroy their own temporary arrays and free their own dynamically allocated memory. It is more efficient to perform this cleanup in the source MEX-file than to rely on the automatic mechanism.

  


Recommended Products

Includes the most popular MATLAB recorded presentations with Q&A; sessions led by MATLAB experts.

 © 1984-2011- The MathWorks, Inc.    -   Site Help   -   Patents   -   Trademarks   -   Privacy Policy   -   Preventing Piracy   -   RSS