This is the mail archive of the fortran@gcc.gnu.org mailing list for the GNU Fortran project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: ISO C binding and character variables


Hi Steve,

Steve Ellcey wrote:
> It fails on IA64 HP-UX because this platform has a different parameter
> passing mechanism for 'char x' and for 'char x[]'.
>
> C seems to be handling it as a simple variable and Fortran seems
> to be handling it as an aggregate (array).
>
> Should the C code be rewritten to make my_char an array?
> Or is the Fortran translation to the C type wrong?
>   

Let's start how Fortran handles characters: Character variables have
intrinsically a length (len=...) and are not zero terminated. Thus a
scalar character variable can have any size.
Additionally, one can create an array of these variables.

For C binding Fortran 2003 defined that only length-one character
variables are allowed; if one wants to pass a string, one needs to use
an array. (Fortunately one can use "abcd" (= lenght-4 scalar string) as
argument for a length-1 size-4 array.

As everybody was thinking of strings, we missed the fact that one can
pass also a single byte as scalar character.

Thus: This is a bug that we treat a single character as array.

Actually, I have the feeling we treat characters completely wrong.

For the following program
----------------
use iso_c_binding
implicit none
interface
  subroutine bar(a) bind(c)
    import
    character(c_char),value :: a
  end subroutine bar
end interface
 character(c_char) :: z
 z = 'a'
 call bar(z)
end
----------------

I would expect the following (C file produced by NAG f95)
----------------
  extern void bar(char a_);
  static char z_[1];
  *z_ = 97;
  bar( *z_);
----------------

However, gfortran produces the following:
----------------
  char z[1:1]; // ok
  z[1]{lb: 1 sz: 1} = 97; // Ok
  bar (z, 1); // wrong
----------------

The normal Fortran call is (<character variable>,<length>), however, I
believe the <length> part should not be there! Additionally, we pass a
character array instead of a scalar.

Similarly for:
----------------subroutine foo(a) bind(C)
use iso_c_binding
implicit none
 character(c_char), value :: a
 print *, a
end subroutine foo
----------------

Here, we should produce something like (NAG f95):
----------------
void foo(char a_)
----------------

but gfortran produces:
----------------
foo (a, _a)
----------------

which has again too many arguments. (I don't quickly see whether this is
scalar or an array, but I think it is an array.)

Thanks for the report.


Tobias


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]