美文网首页
FORTRAN调用C函数的参数不一致问题-自动额外传参特性

FORTRAN调用C函数的参数不一致问题-自动额外传参特性

作者: 别有路 | 来源:发表于2022-09-20 10:14 被阅读0次

最近在debug的时候看到CMAQ ioapi的code, envgets.c中和ENVSTR函数和m3utilio.F中的接口参数不一致, 但是可以正常跑, 之前没注意过, 我大为震惊, code如下:

// ioapi/envgets.c
void ENVSTR( const char * lname, 
             const char * description, 
             const char * defaultval, 
             char       * eqname, 
             FINT       * status,
             FSTR_L       namlen, 
             FSTR_L       deslen, 
             FSTR_L       deflen, 
             FSTR_L       eqlen )
{
    ... ...
}
! ioapi/m3utilio.F
INTERFACE
    SUBROUTINE ENVSTR( LNAME, DESC, DEFAULT, EQNAME, STAT )
    CHARACTER*(*), INTENT(IN   ) :: LNAME
    CHARACTER*(*), INTENT(IN   ) :: DESC
    CHARACTER*(*), INTENT(IN   ) :: DEFAULT
    CHARACTER*(*), INTENT(  OUT) :: EQNAME
    INTEGER      , INTENT(  OUT) :: STAT
    END SUBROUTINE ENVSTR
END INTERFACE

然后自己做了个简单的测试

// echo.c
#include<stdio.h>

void echo_(const char *s1, const char *s2)
{
  printf("%s\n", s1);
  printf("%s\n", s2);
}

void echo2_(char *s1, char *s2, int l1, int l2)
{
  printf("%s\n", s1);
  printf("%s\n", s2);
    printf("%d\n", l1);
    printf("%d\n", l2);
}
! main.f90
PROGRAM main
implicit none
INTEGER :: a, b, c, e
CHARACTER(14) :: s1, s2
INTERFACE
  SUBROUTINE ECHO(s1, s2)
    CHARACTER(*) :: s1, s2
  END SUBROUTINE
  SUBROUTINE ECHO2(s1, s2)
    CHARACTER(*) :: s1, s2
  END SUBROUTINE
END INTERFACE

s1 = "1234567890123" ! // achar(0)
s2 = "world"

call ECHO(s1, s2)
call ECHO2(s1, s2)


END PROGRAM main
# makefile
test :
        icc -c -o echo.o echo.c
        ifort -c -o main.o main.f90
        ifort main.o echo.o -o main.exe

执行得:

1234567890123 world
world
14
14

可以发现几个问题:

  • FORTRAN和C的参数个数确实不需要匹配也ok
  • 字符串在从FORTRAN到C的时候是会出问题的(第一行直接打印s1有明显错误)
  • 会在FORTRAN的参数后面加上字符串的长度(我推测这个机制和上一点是有关系的)

然后经过查证, 在官方的doc里确实也提到了这个feature, 之前没注意到这么细

Oracle Chapter 11 C-FortranInterface

另外这个只是针对字符串的, 试了下对数组是不会带长度的, 但是参数不需要匹配就能跑是都行的, 只是其他情况大概会报错

相关文章

  • Fortran与C++交叉编程:Fortran如何调用C++动态

    Fortran程序中调用C++编写的动态库的问题分为两个子问题 Fortran调用c形式函数接口 为c++动态库编...

  • Objective-C 闭包声明(Block)

    本地变量 属性 方法参数 方法调用传参 C函数参数 类型定义

  • 031|JavaScript arguments对象

    上一节中,我们使用默认参数特性处理了调用者未传参数的问题。 这一节中,我们将要处理调用者传递了参数,但函数未定义参...

  • python函数

    python函数 什么是函数 函数语法 调用函数 函数参数形参与实参传参指定参数传参参数默认值可变参数参数解包参数...

  • Javascript学习笔记——8.3 函数的实参和形参

    函数声明里的参数叫形参,函数调用里的参数叫实参。 Javascript函数定义不指定形参的类型,函数调用也不对实参...

  • Shell 5. 函数

    函数的定义 函数的调用 调用函数并且传入参数 函数的参数 1. 位置参数 参数说明$#代表传入的参数个数$*所有参...

  • golang中nil有趣转化

    nil 函数自动转化 函数形参:nil; 猜想测试 得出结论当调用函数时候,实参是nil,会自动转化成形式参数类型...

  • 关于JS函数的参数小结

    参数分实参和虚参,定义函数时的参数叫虚参,调用函数时候传入参数的叫实参本文主要小结一下平时编写代码时候遇到参数问题...

  • 2017-3-12 JS 学习笔记

    函数的参数 函数调用,函数必须调用,函数名称() 函数的参数 一种实际参数;简称实参 一种形式参数,简称形参 函数...

  • Swift 调用 Objective-C 的可变参数函数

    Swift 调用 Objective-C 的可变参数函数 Swift 调用 Objective-C 的可变参数函数

网友评论

      本文标题:FORTRAN调用C函数的参数不一致问题-自动额外传参特性

      本文链接:https://www.haomeiwen.com/subject/apubortx.html