Linking MS-MPI with MinGW (gfortran) RRS feed

  • Question

  • I am trying to cross-compile my MPI application, prog.exe, from Linux to Windows using a 32bit MinGW cross-compiler.

    To get my code to compile and link without complaints, in mpi.f90, I replaced INT_PTR_KIND() with 4 or 8, then compile mpi.f90 with the flag -fdefault-integer-8. Then I link the resulting mpi.o file with my MPI application.

    My MPI application now compiles and links without any complaints, but when I try to run the resulting executable under Windows (64bit 8.1 Pro), I get the error message "The procedure entry point mpi_init__ could not be located in the dynamic link library E:\prog.exe". Does anyone know what this means, and why I would get this message when the linker does not complain?

    • Edited by plasma314 Friday, July 10, 2015 12:29 AM
    Thursday, July 9, 2015 11:33 PM

All replies

  • I've found something that works, although not entirely satisfactory. To restate, my question was how to cross-compile my MPI code from Linux to Windows using a MinGW cross-compiler (a 32bit host is my main priority, but I was tinkering with 64bit as well). The MPI library I used was Microsoft MPI v6. I'm testing the final executable in 64bit Windows 8.1 Pro. These are the steps I took to accomplish this goal.

    First, as I previously mentioned, mpif.h and mpi.f90 provided by the Microsoft MPI v6 installation define parameters explicitly as 64bit integers, whereas my 32bit MinGW Linux-to-Windows cross-compiler has a default of 32bit integers (as well as other libraries my code is using). Therefore, I compile only mpi.f90 with the flag -fdefault-integer-8 and link the resulting mpi.o with my code. Then in my code, where calls to MPI functions are made I have to be careful that the control parameters that are expected to be 64bit are declared as KIND=8 (such as the error flag that is included as the last argument of every fortran MPI function). An alternative to this is to compile everything with -fno-range-check, but I don't know the side effects of doing this. 

    Second, INT_PTR_KIND(), found in mpif.h and mpi.f90, is not an intrinsic function in GCC, so I had to replace this with the number 4 (one could replace it with 8 if cross-compiling for 64bit Windows).

    Third, if someone is interested in cross-compiling for 64bit Windows, I found an additional step. In mpi.h, the line typedef __int64 MPI_Aint; I believe should be preceded by an #include <stdint.h>.

    Fourth, the msmpi.lib and msmpifec.lib files provided by the Microsoft MPI v6 installation, functions have two underscores at the end of their names rather than a single underscore, which is what the msmpi.dll in my Windows\System32 expects. To work around this, I followed the instructions in http://www.mingw.org/wiki/createimportlibraries and created my own import library, libmsmpi.a, from a msmpi.def file I hand wrote listing the functions my code needs with a single underscore after each name (e.g. mpi_init_). I link with libmsmpi.a and the resulting executable works on Windows. 

    Finally, my code was calling MPI_Allgather several times with MPI_IN_PLACE as the send buffer and MPI_DATATYPE_NULL as the send type. For some reason MS-MPI gave fatal errors when doing this. When MPI_IN_PLACE is used the send type is ignored anyways, so I simply changed MPI_DATATYPE_NULL to the same as the receive type and it no longer gives a fatal error.

    I still need to check the output to see that everything is as expected, but my code is compiling, linking and running now without complaints.

    • Proposed as answer by miro ilias Wednesday, August 26, 2015 6:27 PM
    • Unproposed as answer by miro ilias Wednesday, August 26, 2015 6:27 PM
    Saturday, July 11, 2015 1:42 AM
  • Solution: https://github.com/scisoft/autocmake/issues/85#issue-102874399

    • Proposed as answer by miro ilias Wednesday, August 26, 2015 6:19 PM
    • Edited by miro ilias Wednesday, August 26, 2015 6:28 PM
    Tuesday, August 25, 2015 9:51 AM