Fortran 程序接收信号SIGBUS:访问内存对象的未定义部分

Fortran 程序接收信号SIGBUS:访问内存对象的未定义部分,fortran,runtime-error,gfortran,bus-error,Fortran,Runtime Error,Gfortran,Bus Error,我有这个简单的Fortran代码和一个函数,我在主程序中显式地提供了一个参数。代码如下: implicit none real*8 rrr,x external tttt x = rrr(10) end function rrr(seed) integer seed, k real*8 rrr k = 7 seed = 16807 * ( seed - k * 127773 ) - (k * 2836) print*,se

我有这个简单的Fortran代码和一个函数,我在主程序中显式地提供了一个参数。代码如下:

   implicit none

   real*8 rrr,x
   external tttt

   x = rrr(10)

   end

   function rrr(seed)
   integer seed, k
   real*8 rrr
   k = 7
   seed = 16807 * ( seed - k * 127773 ) - (k * 2836)
   print*,seed
   rrr = seed / 2.
   end
它进行编译,但在运行时会产生以下错误:

Program received signal SIGBUS: Access to an undefined portion of a memory object.

Backtrace for this error:
#0  0x10f43bfe6
#1  0x10f43b7ac
#2  0x7fff89740529
#3  0x10f433d78
#4  0x10f433e2c
#5  0x10f433e6e
Bus error: 10

知道是什么导致了这个错误吗?我使用gfortran编译代码。

您正在修改函数中的种子。您不能这样做,因为它是常量
10
。如果传递了不可定义的内容,则不能在函数中修改
seed
。常量文字是不可定义的。变量通常为

另外,不要使用外部函数。使用模块,或将函数放入“包含”部分,使其成为内部函数。这样,调用方将具有显式接口,并可以检查代码的正确性

特别是,如果使用函数参数
intent(In)
并检查接口,则可以自动避免所犯的错误。即使没有模块,如果启用所有警告和错误检查,许多编译器也可以发现问题。例如,gfortran中的
-g-fcheck=all-Wall-fbacktrace

为您修复:

   real*8 :: x
   integer :: iseed

   iseed = 10
   x = rrr(iseed)

   contains

     function rrr(seed)
       real*8 :: rrr
       integer, intent(in) :: seed
       integer :: kk

       k = 7
       seed = 16807 * ( seed - k * 127773 ) - (k * 2836)

       print *,seed
       rrr = seed / 2.
     end function

   end program

@Vladimir F,很抱歉我是个外行,但是我该如何解决这个问题呢?@user3578925您可以将所需的内容作为变量传递,或者对伪参数使用
value
属性,或者创建本地副本。我很确定我们最近看到了一个非常类似/有用的问题,但我无法立即找到它。但是对于
value
您需要明确的接口。好的,如果我使用y=10,然后执行“x=rrr(y)”就行了。老实说,我不明白。我可以用显式数字调用子例程,也就是说,我可以“调用任何东西(10,输出)”,只要在子例程中将数字10定义为整数,这就行了。问题是你在函数内部修改它!不能修改常量文本
10
。您必须简单地接受这一点,这是一条Fortran规则。
real*8
不是有效的Fortran,也从来不是任何ISO Fortran标准的一部分。