fortran错误回溯导致where循环

fortran错误回溯导致where循环,fortran,gfortran,sigfpe,Fortran,Gfortran,Sigfpe,我正在编写一个大型fortran代码,在使用fast选项编译之前(为了在大型数据库上执行测试),我通常使用“警告”选项进行编译,以便检测和回溯所有问题 因此,通过gfortran-fbacktrace-ffpe trap=invalid、zero、overflow、underflow-Wall-fcheck=all-ftrapv-g2编译,我得到了以下错误: Program received signal SIGFPE: Floating-point exception - erroneous

我正在编写一个大型fortran代码,在使用fast选项编译之前(为了在大型数据库上执行测试),我通常使用“警告”选项进行编译,以便检测和回溯所有问题

因此,通过
gfortran-fbacktrace-ffpe trap=invalid、zero、overflow、underflow-Wall-fcheck=all-ftrapv-g2
编译,我得到了以下错误:

Program received signal SIGFPE: Floating-point exception - erroneous arithmetic operation.
Backtrace for this error:
 #0  0x7fec64cdfef7 in ???
 #1  0x7fec64cdf12d in ???
 #2  0x7fec6440e4af in ???
 #3  0x7fec64a200b4 in ???
 #4  0x7fec649dc5ce in ???
 #5  0x4cf93a in __f_mod_MOD
    at /f_mod.f90:132
 #6  0x407d55 in main_loop_
    at main.f90:419
 #7  0x40cf5c in main_prog
    at main.f90:180
 #8  0x40d5d3 in main
    at main.f90:68
代码f_mod.f90:132的部分包含一个where循环:

! Compute s parameter
do i = 1, Imax
   where (dprim .ne. 1.0)
      s(:,:,:, :) = s(:,:,:, :) +vprim(:,:,:, i,:)*dprim(:,:,:, :)*dprim(:,:,:, :)/(1.0 -dprim(:,:,:, :))
   endwhere
enddo
但我看不出有任何错误。所有其他位置都是指向此部件的子程序的调用。当然,因为这是一个SIGFPE错误,所以在编译
gfortran-g1
时,我不得不在执行时遇到问题。(我在linux上使用gfortran 6.4.0)

此外,这个错误会随着代码完全不同部分的修改而出现和消失。因此,问题来自这个where循环?或者从其他地方回来,回溯是错误的?如果是这样的话,我怎样才能发现这个错误呢

编辑:


因为,我不能在一个最小的例子中重现这个错误(他们正在工作),所以我认为问题出在其他地方。但是如何在大型代码中发现问题呢?

当代码随着SIGFPE而消亡时,使用每个单独的 可能的陷阱,以了解它是否为FE_DIVBYZERO,FE_无效, FE_溢出或FE_下溢。如果是下溢,则改变 你的面具是'1-dprim.ne。0’

PS:当整个数组引用时,不要使用数组节表示法 可以改用

PPS:您可能需要在外部计算dprim*drpim/(1-dprim)
由于它是循环不变的,所以使用do循环。

由于代码将随着SIGFPE而消亡,请使用每个单独的 可能的陷阱,以了解它是否为FE_DIVBYZERO,FE_无效, FE_溢出或FE_下溢。如果是下溢,则改变 你的面具是'1-dprim.ne。0’

PS:当整个数组引用时,不要使用数组节表示法 可以改用

PPS:您可能需要在外部计算dprim*drpim/(1-dprim)
因为它是循环不变的。请发布实际的消息和堆栈跟踪,并尝试隔离一个。此外,此错误随着代码完全不同部分的修改而出现和消失。这看起来可疑,需要更真实的MCVE。我用完整的消息和回溯编辑了我的问题。但我无法生成MCVE,也无法隔离问题。这就是我来寻求帮助的原因。我知道,在没有MCVE的情况下,要提供帮助并不容易,但我已经没有想法了。我将扩展WHERE语句。屏蔽可能会隐藏您的问题。至少要消除代码中的错误。打印where语句中使用的不同数组的实际大小(即打印形状,最好还打印lbounds和ubounds)?请发布实际消息和堆栈跟踪,并尝试隔离a。“此外,此错误会随着代码完全不同部分的修改而出现和消失。”这看起来很可疑,更需要一个真正的MCVE。我用完整的信息和回溯编辑了我的问题。但我无法生成MCVE,也无法隔离问题。这就是我来寻求帮助的原因。我知道,在没有MCVE的情况下,要提供帮助并不容易,但我已经没有想法了。我将扩展WHERE语句。屏蔽可能会隐藏您的问题。至少要消除代码中的错误。打印where语句中使用的不同数组的实际大小(即打印形状,最好还打印lbounds和ubounds)?我不确定这是否回答了问题。OP做错了什么?@Vladimir,没有密码,人们只能猜测SIGFPE的原因。如果OP does-ffpe trap=invalid,则会在表达式中为NaN设置陷阱。OP现在可以查看s、dprim、vprim中的一个是如何获得NaN值的。同样,我怀疑SIGFPE是由-ffpe trap=underflow引起的。同样,在没有代码访问的情况下,我怀疑OP是否真的需要担心陷入下溢,因为gfortran支持逐渐取消下溢,除非使用IEEE模块更改掩码。下溢是否会打印错误的算术运算?不管怎样,这就是我的观点,当没有人知道真正的答案时,为什么要回答?你只是冒着否决票或标志的风险。SIGFPE的错误消息来自操作系统,而不是gfortran,所以我不知道。我唯一的兴趣是帮助OP了解他/她的问题。我认为“不要使用你不理解的选项”是一个不恰当的回答。@RN,鉴于弗拉基米尔反对我给你关于如何隔离问题的想法,我犹豫是否提供任何额外的帮助。问问自己,下溢是否是我的算法的实际问题?如果否,则从-ffpe trap=”中删除标志。我不确定这是否回答了问题。OP做错了什么?@Vladimir,没有密码,人们只能猜测SIGFPE的原因。如果OP does-ffpe trap=invalid,则会在表达式中为NaN设置陷阱。OP现在可以查看s、dprim、vprim中的一个是如何获得NaN值的。同样,我怀疑SIGFPE是由-ffpe trap=underflow引起的。同样,在没有代码访问的情况下,我怀疑OP是否真的需要担心陷入下溢,因为gfortran支持逐渐取消下溢,除非使用IEEE模块更改掩码。下溢是否会打印错误的算术运算?不管怎样,这就是我的观点,当没有人知道真正的答案时,为什么要回答?你只是冒着否决票或标志的风险。SIGFPE的错误消息来自操作系统,而不是gfortran,所以我不知道。我唯一的兴趣是帮助OP了解他/她的问题。我认为“不要使用你不理解的选项”是一个不恰当的回答。@RN,鉴于弗拉基米尔反对我给你关于如何隔离问题的想法,我犹豫是否提供任何额外的帮助。问问自己,下溢是否是我的算法的实际问题?如果否,则从-ffpe trap=中删除该标志。