标签: intel-fortran

只有在使用Intel Visual Fortran编译时,子程序调用上的堆栈溢出,并且当由Compaq Visual Fortran编译时才会很好

使用Fortran .dll的相同源文件,我可以使用Compaq Visual Fortran 6.6C或Intel Visual Fortran 12.1.3.300(IA-32)编译它们.问题是英特尔二进制文件的执行失败,但与Compaq一起运行良好.我正在Windows 7 64位系统上编译32位..dll调用驱动程序是写入的C#.

_chkstk()当调用内部子例程(从.dll入口例程调用)时,失败消息来自可怕的调用.(SO回答chkstk())

有问题的程序被声明为(原谅固定文件格式)

  SUBROUTINE SRF(den, crpm, icrpm, inose, qeff, rev,  
 &               qqmax, lvtyp1, lvtyp2, avespd, fridry, luin,  
 &               luout, lurtpo, ludiag, ndiag, n, nzdepth, 
 &               unit, unito, ier)

  INTEGER*4 lvtyp1, lvtyp2, luin, luout, lurtpo, ludiag, ndiag, n, 
 &          ncp, inose, icrpm, ier, nzdepth
  REAL*8    den, crpm, qeff, rev, qqmax, avespd, fridry           
  CHARACTER*2  unit, unito
Run Code Online (Sandbox Code Playgroud)

并像这样调用:

      CALL SRF(den, crpm(i), i, inose, qeff(i), rev(i),  
 &             qqmax(i), lvtyp1, lvtyp2, …
Run Code Online (Sandbox Code Playgroud)

fortran arguments intel-fortran

6
推荐指数
1
解决办法
1517
查看次数

在Fortran中将逻辑类型转换为double

我正在寻找一种将逻辑类型变量转换为真实类型的防弹方式,这种方式可以在ifort和gfortran中使用.以下适用于ifort,但不适用于gfortran:

logical :: a
real :: b
a = .true.
b = dble(a)
Run Code Online (Sandbox Code Playgroud)

gfortran中抛出的错误是

b = dble(a)
         1
Error: 'a' argument of 'dble' intrinsic at (1) must be a numeric type
Run Code Online (Sandbox Code Playgroud)

显然,.true.应映射到1.d0和.false.到0.d0.这样做的最佳方法是什么?

fortran gfortran intel-fortran

6
推荐指数
2
解决办法
5004
查看次数

在 gfortran 中预处理 !DEC$ 指令

我有一个最初针对英特尔编译器的大型 Fortran 代码库。我现在正准备用 gfortran 进行编译。不幸的是,代码中充斥着 Intel 风格的预处理指令,例如:

!DEC$ IF DEFINED (MYDIRECTIVE)
   REAL, DIMENSION(:,:,:), ALLOCATABLE :: my_real_var
!DEC$ ENDIF
Run Code Online (Sandbox Code Playgroud)

从我通过谷歌搜索和 gfortran 文档可以看出,除了 C 风格的预处理之外,没有内部 gfortran 支持,例如:

#if defined MYDIRECTIVE
   REAL, DIMENSION(:,:,:), ALLOCATABLE :: my_real_var
#endif
Run Code Online (Sandbox Code Playgroud)

有没有其他人遇到过这个问题并提出了一个优雅的解决方案?显然,我可以编写一个 shell 脚本,在将代码传递给 gfortran 进行编译之前调用外部预处理器,但这对我来说似乎不是一个很好的解决方案。

有什么想法吗?谢谢大师!

preprocessor fortran gfortran intel-fortran

5
推荐指数
1
解决办法
3747
查看次数

在 Fortran 中捕获整数异常

有没有办法捕获整数异常,gfortran或者ifort像捕获浮点异常一样?

考虑这个简单的程序来计算阶乘:

program factorial
  use, intrinsic :: iso_fortran_env 

  implicit none
  integer(8)          :: fac
  real(REAL64)        :: facR
  integer,parameter   :: maxOrder = 30
  integer             :: i

  fac = 1 ; facR = 1.e0_REAL64
  do i=2,maxOrder
    fac=fac*i ; facR=facR*real(i,REAL64)
    write(*,*) i, fac, facR
  enddo ! i

end program
Run Code Online (Sandbox Code Playgroud)

在某些时候会出现溢出 -integer(8)如此处所示,它将发生在 21 左右。但是如果没有使用浮点数作为参考的计算,我无法确定......

fortran integer-overflow gfortran intel-fortran

5
推荐指数
1
解决办法
1387
查看次数

在 Windows x64 和 Intel Fortran 中使用 f2py

我试图通过 Intel Fortran 编译器在 Windows 8、x64 上使用 f2py 来实现。

我尝试过两件事:

1) 通过 Windows 64x 安装程序安装。http://www.lfd.uci.edu/~gohlke/pythonlibs/ NumPy 已正确安装,但执行 f2py -c --help-fcompiler 时未找到编译器 我得到:

Fortran compilers found:
Compilers available for this platform, but not found:
  --fcompiler=absoft    Absoft Corp Fortran Compiler
  --fcompiler=compaqv   DIGITAL or Compaq Visual Fortran Compil
  --fcompiler=g95       G95 Fortran Compiler
  --fcompiler=gnu       GNU Fortran 77 compiler
  --fcompiler=gnu95     GNU Fortran 95 compiler
  --fcompiler=intelem   Intel Fortran Compiler for 64-bit apps
  --fcompiler=intelev   Intel Visual Fortran Compiler for Itani
  --fcompiler=intelv    Intel Visual Fortran Compiler for …
Run Code Online (Sandbox Code Playgroud)

python fortran numpy f2py intel-fortran

5
推荐指数
0
解决办法
1887
查看次数

打开时默认状态为“未知”

我经常看到人们使用该OPEN语句而不明确指定STATUS. 在 Fortran 90 和 2008 标准中,这样说STATUS

如果指定 UNKNOWN,则状态取决于处理器。如果省略此说明符,则默认值为 UNKNOWN。

我将此解释为,如果STATUS省略,任何事情都可能发生,具体取决于您使用的机器。

然而,从进行一些测试来看,默认行为(当STATUS省略时)似乎是REPLACE. 但我找不到 gfortran 编译器手册(来自https://gcc.gnu.org/onlinedocs/)中记录的这种行为。

问题:这REPLACE确实是 gfortran 和 ifort 等流行编译器的默认行为吗?如果是这样,这实际上有记录吗(但我只是碰巧没有找到它)?

fortran gfortran intel-fortran

5
推荐指数
1
解决办法
2903
查看次数

如何在 Fortran 90 中向动态数组添加新元素

当我最初无法预测数组的确切大小时,我需要在 Fortran 90 中使用动态数组。所以我编写了一段代码,每次将新元素添加到数组末尾时,该代码都应该扩展可分配数组:

  subroutine DArray()

  double precision, dimension(:), allocatable :: list

  allocate(list(1))

  list(1) = 1.1

  call AddToList(list, 2.2)
  call AddToList(list, 3.2)
  call AddToList(list, 4.2)
  call AddToList(list, 5.2)

  print *, list(1)
  print *, list(2)
  print *, list(3)
  print *, list(4)
  print *, list(5)


  end



  subroutine AddToList(list, element)

  double precision :: element
  double precision, dimension(:), allocatable :: list
  double precision, dimension(:), allocatable :: clist

  if(allocated(list)) then
    isize = size(list)
    allocate(clist(isize+1))
    do i=1,isize
        clist(i) = list(i)
    end do
    clist(i+1) = element

    deallocate(list) …
Run Code Online (Sandbox Code Playgroud)

fortran dynamic-arrays fortran90 intel-fortran

5
推荐指数
1
解决办法
2万
查看次数

Fortran/C 互操作性使用可分配项将结构从 Fortran 传递到 C

我正在尝试将一个结构从 Fortran 传递到 C,其中 Fortran 中的结构有一个可分配的。我想在 fortran 中的结构内分配数组并在 C 中读取它。但是,当我尝试在 CI 中打印分配的数组时,收到错误消息分段错误(核心转储)。我使用的是英特尔编译器版本 19.0.1.144。

我对 C 比较陌生,所以为了测试这个想法,我在 fortran 中分配了一个一维数组并将其传递给 C。这非常有效。您可以在 fortran 代码中看到 ff 是可分配数组,并且为它分配了维度 ii(等于 5)。我初始化数组ff并使用类型(C_ptr)的指针来存储ff数组的地址。我在 C 中打印 ff ,它打印出正确的值 ff ,即 14.7,15.7,16.7,17.7,18.7。使用相同的想法,我声明了一个带有整数 ival、实数 cval 和可分配变量 dval 的结构体 data1。我正在为结构类型 data1 分配一个指针 pdata。我分配了指针和数组 dval。我在 C Main 中调用 fortran 来打印结构数量,当我打印数组 d (或 dval)时出现错误。另外,C中的ival和cval的值也不正确。

SUBROUTINE Simulation(ii,ffp,cdata) BIND(C)

   use, intrinsic  :: iso_c_binding

   integer(kind=4),  intent(in)  :: ii
   type(C_PTR),      intent(out) :: ffp
   real (C_double),  dimension(:), allocatable, target, save :: ff
   integer(kind=4) :: err, i

   Type :: data1 …
Run Code Online (Sandbox Code Playgroud)

c struct fortran fortran-iso-c-binding intel-fortran

5
推荐指数
1
解决办法
981
查看次数

如何指示 gfortran 仅使用可分配数组的矢量化(最高可用 SIMD)指令来编译循环?

当 gfortran 对方程(例如 x = y*z )进行向量化时,编译器将仅使用向量寄存器(例如 YMM)和向量操作码,当且仅当编译器知道所有数据 (x,y,z) 都可以是加载到所述向量寄存器上。然而,如果编译器不知道是否所有数据都可以加载到寄存器中,它将生成冗余代码,以便可以操作剩余的数据。

此冗余代码通常不会使用最高可用的 SIMD 向量寄存器,并且会使可执行文件膨胀。我还没有进行广泛的测试,但常见的推理使我相信它可能会导致 ICACHE 缺失或阻止函数/子例程内联优化。

我想删除这个冗余代码,因为我知道我的所有数据 (x,y,z) 将完美地适合 YMM 向量寄存器。

我之前曾在这里更详细地描述过我的观察结果:https: //www.cfd-online.com/Forums/main/231759-fortran- assembly-how-remove-redundant-non-vectorized-code.html

不过,我想在这里举一些简单的例子来展示我的观点。

对于以下操作:x(:) = y*z其中x,y,z都是可分配数组,编译器不知道该操作是否可以完全矢量化,因为它不知道数组的长度是多少。如果 x,y,z 是整数数组并且长度是 8 的倍数,我们可以推断整个操作可以简单地使用 AVX2 向量化操作来完成。然而,由于数组长度在编译时未知,编译器必须生成可用于任意长度数组的冗余代码。

上帝螺栓链接:https://gcc.godbolt.org/z/1fdzK8

这是为该x(:) = y*z部分生成的程序集:

.L7:
        vmovdqu ymm1, YMMWORD PTR [r13+0+rax]
        vpmulld ymm0, ymm1, YMMWORD PTR [r12+rax]
        vmovdqu YMMWORD PTR [r14+rax], ymm0
        add     rax, 32
        cmp     rdx, rax
        jne     .L7
        mov     rdx, r15
        and     rdx, -8
        lea     rax, [rdx+1]
        cmp     rdx, …
Run Code Online (Sandbox Code Playgroud)

fortran simd gfortran avx2 intel-fortran

5
推荐指数
1
解决办法
542
查看次数

使用 ifort 构建可执行共享库

有几个关于 SO 的精彩讨论已经涵盖了如何在 Linux 上生成可执行共享库:

在 C/C++ 中,这似乎相对简单;基本上有两个部分:

  1. 通过在库源代码中包含以下.interp内容,向 ELF添加一个部分(因为ld不包括共享库的部分):
    const char interp_section[] __attribute__((section(".interp"))) = "/path/to/dynamic/linker";
  2. 链接时设置适当的入口点,使用 -Wl,-e,entry_point

有谁知道如何使用 Fortran 编写的库来实现这一目标?具体来说,如何将一个.interp部分添加到使用编译的共享库中ifort

fortran shared-libraries intel-fortran

5
推荐指数
1
解决办法
75
查看次数