segmentation-fault - 假定大小数组的段错误

标签 segmentation-fault fortran gfortran

执行以下代码时出现段错误:

program test

call sub ('dave')

end program test


subroutine sub (arr)

character (*) :: arr
character (20) :: upperc

arr = upperc (arr)

return

end subroutine sub


character (*) function upperc (str)

integer i, l
character (*) :: str

upperc = str
l = len (str)
do i = 1, l
  icode = ichar (str (i:i))
  if ((icode >= ichar ('a')).and.(icode <= ichar ('z'))) then
    upperc (i:i) = char (ichar ('A') + icode - ichar('a'))
  end if
enddo

return

end function upperc

seg 错误发生在以下行:

arr = upperc (arr)

这是编译和 GDB 运行时输出:

[dave@VM-15 ~]$ gfortran -g -Wall test.f90
[dave@VM-15 ~]$ gdb
GNU gdb (GDB) Red Hat Enterprise Linux 7.6.1-80.el7
Copyright (C) 2013 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.  Type "show copying"
and "show warranty" for details.
This GDB was configured as "x86_64-redhat-linux-gnu".
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
(gdb) file ./a.out
Reading symbols from /home/dave/a.out...done.
(gdb) run
Starting program: /home/dave/./a.out

Program received signal SIGSEGV, Segmentation fault.
0x00007ffff70f1fa3 in __memmove_ssse3_back () from /lib64/libc.so.6
Missing separate debuginfos, use: debuginfo-install glibc-    2.17-106.el7_2.8.x86_64 libgcc-4.8.5-4.el7.x86_64 libgfortran-4.8.5-4.el7.x86_64 libquadmath-4.8.5-4.el7.x86_64
(gdb) backtrace
#0  0x00007ffff70f1fa3 in __memmove_ssse3_back () from /lib64/libc.so.6
#1  0x000000000040078c in sub (arr='dave', _arr=4) at test.f90:13
#2  0x00000000004008e9 in test () at test.f90:3
#3  0x000000000040091f in main (argc=1, argv=0x7fffffffe7b3) at test.f90:5
#4  0x00007ffff6fc3b15 in __libc_start_main () from /lib64/libc.so.6
#5  0x0000000000400669 in _start ()
(gdb) q
A debugging session is active.

    Inferior 1 [process 20941] will be killed.
[dave@VM-15 ~]$

我有一种有趣的感觉,这与我传递文字有关,但也许不是。

为了解决这个问题,我尝试了以下方法,效果很好:

program test2

character(20) text

text = 'dave'

call sub (text)

end program test2


subroutine sub (arr)

character (*) :: arr
character (20) :: upperc

arr = upperc (arr)

return

end subroutine sub


character (*) function upperc (str)

integer i, l
character (*) :: str

upperc = str
l = len (str)
do i = 1, l
  icode = ichar (str (i:i))
  if ((icode >= ichar ('a')).and.(icode <= ichar ('z'))) then
    upperc (i:i) = char (ichar ('A') + icode - ichar('a'))
  end if
enddo

return

end function upperc

谁能告诉我这是怎么回事?

最佳答案

问题是子例程sub从程序test2写入变量text。当您没有将变量作为 sub 的参数,而只是像第一个程序 test 中那样提供 'dave' 时,Fortran 会覆盖内存中未分配为变量的区域。这会导致段错误。

下面您可以看到您的工作示例。请注意两个更改:

  1. 字符text的长度设置为6而不是20。这样做是为了证明它仍然可以组合在一起,因为子例程sub采用任意长度的参数。

  2. 我们将变量 text 的值写入控制台 2 倍,并通过 call sub(text) 更改它

program test3

character(6) text

text = 'dave'

write(*,*) text

call sub (text)

write(*,*) text

end program test3


subroutine sub (arr)

character (*) :: arr
character (20) :: upperc

arr = upperc (arr)

return

end subroutine sub


character (*) function upperc (str)

integer i, l
character (*) :: str

upperc = str
l = len (str)
do i = 1, l
  icode = ichar (str (i:i))
  if ((icode >= ichar ('a')).and.(icode <= ichar ('z'))) then
    upperc (i:i) = char (ichar ('A') + icode - ichar('a'))
  end if
enddo

return

end function upperc 

关于segmentation-fault - 假定大小数组的段错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40473127/

相关文章:

compiler-errors - 将gfortran与Intel MKL链接

c - 从文件读取数据到结构体中 (C)

C - 检查指针是否为 NULL 时出现段错误

c++ - 从 Fortran 调用 C++(链接问题?)

c - 为什么 Matlab 是用 C 而不是 Fortran 编写的?

Fortran 打印语句格式,空格太多

compiler-errors - 动态(可分配)向量的 gfortran 编译器错误

c - 填充 char* 数组时出现段错误

当数据复制/扫描/读取到未初始化的指针时崩溃或 "segmentation fault"

oop - 在 Fortran 2003 中使用 'class' 的效率?