让我们假设我有以下代码:
module eval_mod
implicit none(type, external)
private
public :: eval
abstract interface
real pure function real_function_t(x)
real, intent(in) :: x
end function
end interface
contains
pure function eval(f, x) result(res)
procedure(real_function_t) :: f
real, intent(in) :: x
real :: res
res = f(x)
end function
end module
program main
use iso_fortran_env, only: stdout => output_unit
use eval_mod, only: eval
implicit none(type, external)
write(stdout, *) eval(double, 2.)
write(stdout, *) eval(triple, 2.)
contains
pure real function double(x)
real, intent(in) :: x
double = 2. * x
end function
pure real function triple(x)
real, intent(in) :: x
triple = 3. * x
end function
end program
并用CCD_ 1进行编译。
如果我将断点设置为eval_mod::eval
,我想看看调用了哪个函数参数eval
。
我实际看到的是
Breakpoint 2, eval_mod::eval (f=0x7fffffffced8, x=2) at main.F90:17
如果我取下地址并回答这个问题,我应该能够通过以下操作在符号表中看到函数名称:
info symbol 0x7fffffffced8
不幸的是,我收到一个错误
No symbol matches 0x7fffffffced8.
如何查看作为参数传递的函数的函数名?
附言:我使用gfortran 7.5.0和gdb 11.1。
double
和triple
是内部函数(在主程序中(。由于父作用域中变量的主机关联,传递内部函数很棘手。因此,它们通常使用蹦床来实现。你看到的地址就是蹦床的地址,换句话说,就是一个所谓的暴徒。蹦床比实际调用的功能。
地址很可能指向堆栈中放置蹦床代码的某个位置。在该代码中,您可能会找到一个带有实际函数地址的跳转指令。
另请参阅Steve Lionel博士Fortran在"Think,Thank,Thunk"中的这篇精彩文章