This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

DW_CFA_val_expression CFI instruction not recognized by TI Clang compiler 2.1.2

Hello,

I'm trying to use DW_CFA_val_expression CFI instruction in my assembly file and linker emits following warning:

warning #99922: unrecognized call frame instruction 0x16; cannot read remainder of this section (.debug_frame + 0x115)

Other CFI instructions don't cause any warnings (for example DW_CFA_def_cfa_expression).

GCC compiler does not have any problem with this instruction and call stack unwinds correctly. I also searched for DW_CFA_val_expression in LLVM Clang (llvm.org) compiler sources and it seems that DW_CFA_val_expression  is supported. If there is a person with access to TI's Clang compiler source code, could you please verify if this instruction is supported?

Thanks!

  • The assembler directives related to Dwarf debug information are not documented.  They are not intended for direct use by customers.  That said, I'll see what I can find out.

    Thanks and regards,

    -George

  • I'll see what I can find out.

    tiarmclang never emits DW_CFA_val_expression, and the linker has no code for handling it.

    Thanks and regards,

    -George

  • Hi George,

    Thank you for your reply.

    I am aware that DW_CFA_val_expression is not emitted by tiarmclang compiler, because for assembler generated from C code it is not necessary. It is me who is using this instruction (and also DW_CFA_def_cfa_expression, about which tiarmclang does not complain) in our assembler sources, to allow unwinding the exception/interrupt call stack. In such case all the registers are saved in RTOS structures when interrupted task gets swapped-out.

    DW_CFA_* instructions are encoded as a stream of bytes in an assembler file, for example:

    .cfi_escape 0x16 /* DW_CFA_val_expression */, 14 , 5, \
    0x0C /* DW_OP_const4u */, 0xF9, 0xFF, 0xFF, 0xFF

    Above sequence tells the unwinder that for current call stack frame the LR register (14) value is a constant 0xFFFFFFF9.

    Another example:

    .cfi_escape 0x16 /* DW_CFA_val_expression */, 10 /* R10 */, 4, \
    0x7D /* DW_OP_breg13 */, 24, \
    0x06 /* DW_OP_deref */, \
    0x06 /* DW_OP_deref */

    Above sequence tells the unwinder that R10 value can be found at the location:

    **(uint32_t *)(SP + 24)

    SP is the stack pointer (reg13 in the expression).

    .cfi_escape allows to create complex expressions to recreate the value of a register in the current stack frame. Apart from .cfi_escape I also use other directives, such as: .cfi_def_cfa or .cfi_offset.

    To clarify: .cfi_* are GNU assembler directives (and also LLVM Clang's assembler directives), while DW_CFA_* are part of DWARF 3.0 specification which, I assumed, TI Clang toolchain fully supports.

    The question is why tiarmclang is ok with DW_CFA_def_cfa_expression, but not with DW_CFA_val_expression, for example this expression does not cause any warnings:

    .cfi_escape 0x0f /* DW_CFA_def_cfa_expression */, 3, \
    0x7d /* DW_OP_breg13 */, 0, \
    0x06 /* DW_OP_deref */

    Thank you and best regards,

    Sylwester

  • Unfortunately, the linker does not support DW_CFA_val_expression (0x16) as an input to the .cfi_escape directive.  The linker is only tested to support what the compiler emits. 

    Thanks and regards,

    -George