代码之家  ›  专栏  ›  技术社区  ›  malat

dladdr:指向函数的指针vs指向对象的指针

  •  6
  • malat  · 技术社区  · 9 年前

    希望这是一个相当简单的C++问题(不是语言律师的问题)。

    如何使用GNU扩展 dladdr 在C++中?通常用C编写以下内容:

    #ifndef _GNU_SOURCE
    #define _GNU_SOURCE
    #endif
    #include <dlfcn.h>
    
    static void where_am_i() {}
    
    int main()
    {
      Dl_info info;
      dladdr( (void*)&where_am_i, &info );
    
      return 0;
    }
    

    然而,使用clang可以看到演员阵容可能无效:

    $ clang --version
    Debian clang version 3.6.2-3 (tags/RELEASE_362/final) (based on LLVM 3.6.2)
    Target: x86_64-pc-linux-gnu
    Thread model: posix
    $ clang -Wpedantic -o foo foo.cpp -ldl
    foo.cpp:11:11: warning: cast between pointer-to-function and pointer-to-object is an extension [-Wpedantic]
      dladdr( (void*)&where_am_i, &info );
              ^~~~~~~~~~~~~~~~~~
    1 warning generated.
    

    这个警告对我来说似乎是合理的,那么有没有办法解决这个问题呢?

    1 回复  |  直到 9 年前
        1
  •  2
  •   eerorika    9 年前

    没有标准的方法可移植地将函数指针转换为 void* 因此,没有标准的便携使用方法 dladdr

    [expr.reinterpret.cast] /8(标准草案)

    有条件地支持将函数指针转换为对象指针类型,反之亦然。这种转换的含义是由实现定义的,但如果实现支持双向转换,则将一种类型的prvalue转换为另一种类型,然后再转换回来(可能具有不同的cv限定),将产生原始指针值。


    因为您已经依赖于提供 dladdr地址 空洞* 。在这种情况下,您可能希望通过编译而不使用 -Wpedantic 选项-或使用至少有条件支持转换的标准版本。如果不支持转换,则不支持转换 dladdr地址 .