This is the mail archive of the elfutils-devel@sourceware.org mailing list for the elfutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH] backends: Hook abi_cfi for arm.


Hi Roland,

IIUC your mail is talking about what return_address_register means in DWARF.
But DWARF return_address_register does not need to be guessed by elfutils, it
is always present in CIE, if there is any DWARF FDE/CIE found.

The discussion here was what elfutils ebl_abi_cfi() should return (what is the
"elfutils return_address_register").  That is described in elfutils by:
libebl/libebl.h:
   This function can also fill in ABI_INFO->return_address_register with the
   DWARF register number that identifies the actual PC in machine state.
   If there is no canonical DWARF register number with that meaning, it's
   left unchanged (callers usually initialize with (Dwarf_Word) -1).
   This value is not used by CFI per se.

This would correspond to your suggested value 15 (PC) for ARM.
But no elfutils code uses that value.  I have no idea if systemtap uses it.

Besides that .ARM.exidx assumes return address is in LR plus .debug_frame has
return address set to LR by GCC:
  Return address column: 14
I have included an example ARM output at the bottom of this mail.
Existing CIEs do not matter much for the elfutils return_address_register
value, as you wrote below:


On Thu, 29 Aug 2013 22:32:31 +0200, Roland McGrath wrote:
> But that's really neither here nor there.  It doesn't matter what the
> compiler does for some particular FDEs (or for all that it emits).  All that
> matters is that the number you choose for a particular CIE is the one that
> its FDEs describe correctly for rematerializing the return address

I agree elfutils return_address_register does not matter for CIE as CIE
contains its own value.  Then remains the question what is elfutils
return_address_register good for.

My unwinder patchset keeps PC value independently from the DWARF register set
as some archs (ppc/s390) do not have any DWARF register assigned for PC.


> There is readelf -u in binutils and see
> 	https://wiki.linaro.org/KenWerner/Sandbox/libunwind#unwinding_on_ARM
> (actual spec in
> 	http://infocenter.arm.com/help/topic/com.arm.doc.ihi0038a/IHI0038A_ehabi.pdf
> ).  And you can look at .debug_frame tables.

Thanks for the pointers, great info.


> 	mov r0, lr
> 	mov lr, #0
> 	bx r0
> 
> Now, it would be correct enough to say that return_address_register is r0,
> that r0's rule is same-value, and that lr's rule is undefined (or is
> register r0, if you like).  That is not entirely precise, since it says the
> caller's value of r0 was knowable when in fact it's undefined.  But as to
> the return address and lr, it's perfectly correct and precise.  In actual
> fact, the compiler would never generate code like that because the hardware
> makes it optimal always to use "bx lr" for return (it has a call/return
> prediction stack and "bx lr" is specifically recognized as "return").
> 
> So it's not really clear which is "better", because it depends on what your
> goals are.  

The goal is IMO to unwind as much inferior code as possible.

You are describing various non-standard ARM code cases.  But those should have
their own .ARM.exidx or .debug_frame entry so elfutils return_address_register
does not matter then.

In the example below with -fasynchronous-unwind-tables it does not matter what
elfutils return_address_register is set to.  But without
-fasynchronous-unwind-tables the unwind will be successful only if elfutils
return_address_register is set to 14 (when .debug_frame is not available).

Discussing hypothetical unwinder (maybe the systemtap one behaves that way?).
My current pending elfutils unwinder aborts unwind if neither .eh_frame nor
.debug_frame is found as it expects -fasynchronous-unwind-tables is in use.


Thanks,
Jan


000084d4 <main>:
    84d4:       e52db004        push    {fp}            ; (str fp, [sp, #-4]!)
    84d8:       e28db000        add     fp, sp, #0
    84dc:       e3a03000        mov     r3, #0
    84e0:       e1a00003        mov     r0, r3
    84e4:       e24bd000        sub     sp, fp, #0
    84e8:       e49db004        pop     {fp}            ; (ldr fp, [sp], #4)
    84ec:       e12fff1e        bx      lr
000084f0 <__libc_csu_init>:

Unwind table index '.ARM.exidx' at offset 0x568 contains 5 entries:

This entry is present only with -fasynchronous-unwind-tables:
0x84d4 <main>: 0x809b8080
  Compact model index: 0
  0x9b      vsp = r11
  0x80 0x80 pop {r11}

Contents of the .debug_frame section:

00000000 0000000c ffffffff CIE
  Version:               1
  Augmentation:          ""
  Code alignment factor: 2
  Data alignment factor: -4
  Return address column: 14

  DW_CFA_def_cfa: r13 ofs 0

00000010 00000014 00000000 FDE cie=00000000 pc=000084d4..000084f0
  DW_CFA_advance_loc: 4 to 000084d8
  DW_CFA_def_cfa_offset: 4
  DW_CFA_offset: r11 at cfa-4
  DW_CFA_advance_loc: 4 to 000084dc
  DW_CFA_def_cfa_register: r11

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]