4

Recently, I was working on a project where some C++ subroutines are called by Fortran scripts (A Fortran solver intends to have some data-post-processing capability which is from a lib developed in C++). The following procedures replay the error producing process. Here I use quite simple Fortran and C++ scripts for a easy and clear demonstration.

A simple Fortran main program calls a CXX subroutine: The CXX subroutine - sub1.cxx:

    #include <stdio.h>
    using namespace :: std;
    extern "C" void func_c_();
    void func_c_()
    {
         printf("%d\n", 100);
    }

The Fortran main program - sub2.f90:

    program func_fortran
          implicit none
          call func_c()
    end program func_fortran

Compile them:

    g++ -c sub1.cxx
    gfortran -o test sub2.f90 sub1.o

We get the executable - test. Up to now, there is no problem.

Then we replace the sub1.cxx by sub1.1.cxx. It looks like:

    #include <iostream>
    using namespace :: std; 
    extern "C" void func_c_();
    void func_c_()
    {
         cout << "I am a CXX." << endl;
    }

The Fortran main program is totally the same with the previous one. We did not touch it.

Now we compile the codes:

    g++ -c sub1.1.cxx
    gfortran -o test sub2.f90 sub1.1.o

We can obtain sub1.1.o. But the error messages are thrown out:

    sub1.1.o: In function `func_c_':
    sub1.1.cxx:(.text+0xa): undefined reference to `std::cout'
    sub1.1.cxx:(.text+0xf): undefined reference to `std::basic_ostream<char, std::char_traits<char> >& std::operator<< <std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&, char const*)'
    sub1.1.cxx:(.text+0x14): undefined reference to `std::basic_ostream<char, std::char_traits<char> >& std::endl<char, std::char_traits<char> >(std::basic_ostream<char, std::char_traits<char> >&)'
    sub1.1.cxx:(.text+0x1c): undefined reference to `std::ostream::operator<<(std::ostream& (*)(std::ostream&))'
    sub1.1.o: In function `__static_initialization_and_destruction_0(int, int)':
    sub1.1.cxx:(.text+0x46): undefined reference to `std::ios_base::Init::Init()'
    sub1.1.cxx:(.text+0x55): undefined reference to `std::ios_base::Init::~Init()'
    collect2: error: ld returned 1 exit status

Compared with sub1.cxx, it seems some C++ standards in sub1.1.cxx e.g. std::cout can not be recognized. Any one could figure this problem out? Additionally, here I did not use the iso_c_binding from Fortran 2013. I tried this features in some other cases but it does not work either.

Weather Vane
  • 33,872
  • 7
  • 36
  • 56
  • 2
    The FORTRAN linker doesn't know to link against the C++ runtimes, which is why you see those errors. Your first C++ snippet was essential just C code, which may explain why it managed to link. – Mansoor Dec 16 '19 at 20:35
  • 2
    Please - Fortran has officially been spelt Fortran (i.e. lower case) for almost 3 decades now. – Ian Bush Dec 16 '19 at 21:12
  • Hi, Mansoor, hi, Lan Bush, thanks for the comments. Please see what Francesco posted. That is the right solution. In order to make a compatible compiling between C and C++, the link flag -lstdc++ should be used. – Hacunamatata Dec 17 '19 at 07:56

1 Answers1

7

You need to link the executable against the c++ standard library:

g++ -c sub1.1.cxx
gfortran -o test sub2.f90 sub1.1.o -lstdc++

With gfortran/g++ you can also use g++ to link against the fortran library:

g++ -c sub1.1.cxx
gfortran -c sub2.f90
g++ -o test sub1.o  sub2.o -lgfortran
francesco
  • 7,189
  • 7
  • 22
  • 49
  • 1
    Hi @Hacunamatata if this or any answer has solved your question please consider [accepting it](https://stackoverflow.com/help/someone-answers) by clicking the check-mark. This indicates to the wider community that you've found a solution and gives some reputation to both the answerer and yourself. There is no obligation to do this. – francesco Dec 16 '19 at 22:36
  • Hi, Fransesco. Many thanks for the comment. Now it works. I used to add the flag - -lstdc++ right after gfortran instead appending it to the last. Apparently, it is not the right way to define the linking behavior. Again, thanks for your kind comment. – Hacunamatata Dec 17 '19 at 07:52
  • @Hacunamatata Yes, order is important, see, e.g., [here](https://stackoverflow.com/a/409402/8769985) – francesco Dec 17 '19 at 08:18
  • The link you give here is really helpful. Thanks. – Hacunamatata Dec 17 '19 at 08:45