Search code examples
pythonvisual-c++fortrangfortranf2py

F2PY cannot compile Fortran with print or write


I'm having problems compiling Fortran into a Python extension module when the Fortran code includes print or write function calls.

I am on Windows 8.1 with gfortran (through mingw-w64) and the MSVC Compiler for Python 2.7 installed. The Python distribution in use is Anaconda.

test.f

subroutine test (a)

    integer, intent(out) :: a

    print *,"Output from test"

    a = 10

end subroutine test

Running f2py -c -m --fcompiler=gnu95 test test.f90 I see these errors:

test.o : error LNK2019: unresolved external symbol _gfortran_st_write referenced in function test_
test.o : error LNK2019: unresolved external symbol _gfortran_transfer_character_write referenced in function test_
test.o : error LNK2019: unresolved external symbol _gfortran_st_write_done referenced in function test_
.\test.pyd : fatal error LNK1120: 3 unresolved externals

But it works fine when I comment out the print (or write) statement.

A weird thing I've noticed is that it seems to be using Python for ArcGIS.

compile options: '-Ic:\users\[username]\appdata\local\temp\tmpqiq6ay\src.win-amd64-
2.7 -IC:\Python27\ArcGISx6410.3\lib\site-packages\numpy\core\include -IC:\Python
27\ArcGISx6410.3\include -IC:\Python27\ArcGISx6410.3\PC -c'
gfortran.exe:f90: test.f90

Any help would be greatly appreciated.


Solution

  • Answering my own question.

    Steps to fix:

    1. Ignore or scrub the mingw-w64 install. It wasn't needed as Anaconda comes with mingw
    2. Add C_INCLUDE_PATH to the Windows system environment variables and point that to the include folder located within the anaconda path (e.g. C:\userdata\[user]\Miniconda\include)
    3. Change --compiler=msvc to --compiler=mingw32
    4. In my case, it was attempting to use numpy from the ArcGIS install. To fix, I had to conda uninstall numpy, take note of all the packages it removed, and then conda install [list of packages that were previously removed]

    The Fortran code now compiles perfectly and can be called from Python.