1

I'm working on getting gfortran working in place of the Intel Fortran compiler for MATLAB on Windows 10. The GCC style of name mangling, at least for gfortran, is to make the symbol name all lowercase and append an underscore; "mxIsNumeric800" becomes mxisnumeric800_. To get MATLAB to recognize the symbols, they have to omit the appended underscore (easy, just add -fno-underscoring to the compiler options) and consist entirely of uppercase alphanumeric characters (difficult, but possible).

I've been able to fix this capitalization issue by using the method described in this answer, but I can't get the exported symbols to remain uppercase. Here are the exported symbols for a mex file compiled with gfortran (part of output of dumpbin /exports timestwo.mexw64):

ordinal hint RVA      name

      1    0 00001510 mexfilerequiredapiversion
      2    1 000013E0 mexfunction
      3    2 000013C0 timestwo

and the same file compiled with the Intel Fortran compiler:

ordinal hint RVA      name

      1    0 00001150 MEXFILEREQUIREDAPIVERSION
      2    1 00001000 MEXFUNCTION

The Intel compiler handles exports via a linker option /EXPORT:FOO which is used twice, once for MEXFUNCTION and once for MEXFILEREQUIREDAPIVERSION. I've tried using a .def file consisting of

EXPORTS
MEXFUNCTION
MEXFILEREQUIREDAPIVERSION

but linking it (as opposed to a .def file with lowercase or camelcase symbols) doesn't change anything. I've also tried adding to my linker script:

EXTERN(MEXFUNCTION,MEXFILEREQUIREDAPIVERSION);
PROVIDE(mexfunction = MEXFUNCTION);
PROVIDE(mexfilerequiredapiversion = MEXFILEREQUIREDAPIVERSION);

but this doesn't change anything.

How can I modify these symbols to be uppercase?

zaen
  • 326
  • 3
  • 14
  • You were already recommended to use `BIND(C,name="")`. Does it not work for you? Why? Potential duplicate: https://stackoverflow.com/questions/55499662/does-symbol-capitalization-matter-in-object-files-with-a-linked-dll – Vladimir F Героям слава Apr 04 '19 at 18:19
  • @VladimirF No, MATLAB crashes when I attempt to run the program with BIND(C,name=""). The problem in my other question was separate; internal symbols needed to be uppercase to work with provided libraries. This question is about exported symbols from the final mex file, which are not defined in any libraries. – zaen Apr 04 '19 at 18:23
  • @VladimirF There are symbols that are exported from the final .mexw64 file which are the output of ld, e.g. `MEXFUNCTION`. Those symbols are what this question is about. There are other symbols which are not exported but are used in linking the Fortran source to the MATLAB libraries, e.g. `MXISNUMERIC800`. When I use Bind(C) anywhere in my source, as prescribed by any tutorial I can find, MATLAB freezes for a couple of seconds and crashes with no error output. When I rename symbols in the linker script, it doesn't crash, it just complains no gateway function has been defined. – zaen Apr 04 '19 at 19:35
  • Looks like you need to contact the MathWorks. – Steve Apr 04 '19 at 19:49
  • I have a feeling you are most likely calling your function wrong. That is the only reason I can imagine why it would crash! `BIND(C,name="symbolName")` should work if you feed it with the correct arguments. – kvantour Apr 05 '19 at 08:08

1 Answers1

0

I've solved the specific problem I was having, but the solution isn't satisfactory (gfortran-compiled mex files still cause MATLAB to crash).

As it turns out, there are a few ways to accomplish manual symbol capitalization. One, which I thought didn't work but have since discovered otherwise, is BIND(C,NAME=""). A mex function like subroutine mexfunction(nlhs, plhs, nrhs, prhs) bind(C,name="MEXFUNCTION") will result in an uppercase MEXFUNCTION symbol which can be exported.

An alternate way is to alias the symbol in an export definition (.def) file. A file containing

EXPORTS
MEXFUNCTION = mexfunction
MEXFILEREQUIREDAPIVERSION = mexfilerequiredapiversion

included when running the linker will also result in the desired symbols being exported. Either of these is a solution to the question, even if it's not a solution to the overall problem I'm trying to solve.

Using either of these methods results in a mex function that crashes MATLAB when run. The crash occurs when memcpy from VCRUNTIME140.dll runs at the beginning of the mex function, resulting in an access violation. I was able to get MATLAB to output a crash dump by building the mex function with debugging symbols.

Unfortunately, it looks like there's even more to getting gfortran working with MATLAB than just linking the correct libraries and using the correct symbols.

zaen
  • 326
  • 3
  • 14
  • Final update: I've gotten gfortran working, at least for timestwo. It turns out the cygwin MinGW preprocessor wasn't defining `__LP64__`, so variables of the type mwPointer were being assigned the wrong size in bytes. When the program tried to run mxCopyPtrToReal8, it would read in too few bytes, which resulted in an access violation. The key to finding this out was using `call mexPrintf()` several times to see how far the function was getting. – zaen Apr 09 '19 at 00:54