我想知道.cfi_remember_state是如何实现的。我知道它是伪操作,所以我想在组装时它会转换成几条指令。我感兴趣的是确切的指令用于实现它。我尝试了多种方法来解决这个问题。即:

  • 阅读GAS源代码。但是没有找到足够有用的东西。
  • 阅读GAS文档。但是.cfi_remember_state条目只是一个简单的玩笑(从字面上看)。
  • 试图找到一个gcc开关,它将使gcc从带有伪操作“expanded”的C代码生成asm。找不到适用于x86/x86-64的开关。 (顺便说一句,如果有人可以将我指向这样的开关,那就好了,顺便说一句。)
  • 关于SO的Google-fu &&搜索未产生任何有用的信息。

  • 在我看来,唯一的其他解决方案是读取已汇编的可执行文件的二进制文件并尝试推断出指令。但我想避免这样艰巨的任务。
    你们谁能给我启发,请问在x86和/或x86-64上如何实现它?也许与共享如何/在何处获取该信息一起,以便在需要时可以检查其他伪操作?

    最佳答案

    该指令是DWARF信息的一部分(实际上它所做的只是发出DW_CFA_remember_state指令)。摘录自DWARF3标准:



    您可以使用objdump播放DWARF信息。让我们从简单的void汇编程序文件开始:

      .text
    .globl main
      .type main, @function
    main:
    .LFB0:
    .cfi_startproc
    #.cfi_remember_state
    .cfi_endproc
    .LFE0:
      .size main, .-main
    

    gcc cfirem.s -c -o cfirem.o编译

    现在用objdump --dwarf cfirem.o分解生成的DWARF部分
    你会得到:
    00000018 00000014 0000001c FDE cie=00000000 pc=00000000..00000000
      DW_CFA_nop
      DW_CFA_nop
      ...
    

    如果您取消注释.cfi_remember_state,则会看到:
    00000018 00000014 0000001c FDE cie=00000000 pc=00000000..00000000
      DW_CFA_remember_state
      DW_CFA_nop
      DW_CFA_nop
      ...
    

    因此,它实际上不是在汇编程序指令中进行转换(尝试objdump -d来查看示例中根本没有汇编程序指令)。它以DWARF伪指令转换,当GDB之类的调试器处理您的变量位置,堆栈信息等时,将使用这些伪指令。

    关于gcc - .cfi_remember_state的实现,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/14582306/

    10-11 06:02