[flang-commits] [flang] [flang][debuginfo] Emit DW_AT_type for DW_TAG_string_type DIEs [3/3] (PR #231960)

Abid Qadeer via flang-commits flang-commits at lists.llvm.org
Thu Oct 15 02:17:28 PDT 2026


abidh wrote:

> Thank you @timsmith78. This is a great enhancement! I only have two questions.
> 
> 1. Should this be guarded on DWARF 5+? As the original issue [DIStringType does not have a way to represent underlying character type. #95440](https://github.com/llvm/llvm-project/issues/95440) notes, `DW_AT_type` on `DW_TAG_string_type` is a DWARF 5 feature.

We already emit other DWARF 5 constructs at lower versions (e.g. DW_TAG_generic_subrange and DW_AT_rank for assumed-rank arrays), so I think this is ok. If a version check is needed, it belongs in the backend under strict DWARF. It also reminds me that we need to tighten these things in the backend and then support -gstrict-dwarf in flang.

> 2. The `stringLengthExpression` of descriptor-based strings is now visibly inconsistent with the character type. Slightly out of scope, since the issue is pre-existing, but this PR is what makes the character kind visible and so exposes it. For example, with a deferred-length string:
> 
> ```fortran
> character(kind=4, len=:), allocatable :: deferred
> allocate(character(kind=4, len=7) :: deferred)    ! 7 characters = 28 bytes
> deferred = 4_"abcdefg"
> ```
> 
> `DW_AT_string_length` points at the descriptor's `elem_len` field, which Flang stores in _bytes_, so it yields 28 rather than 7. This PR now additionally declares the character to be 4 bytes wide:
> 
> ```
> 0x00000092:   DW_TAG_string_type
>                 DW_AT_string_length	(DW_OP_push_object_address, DW_OP_plus_uconst 0x8)   <=== yields 28, i.e. bytes (pre-existing)
>                 DW_AT_data_location	(DW_OP_push_object_address, DW_OP_deref)
>                 DW_AT_encoding	(DW_ATE_UCS)
>                 DW_AT_type	(0x0000008e "character(kind=4)")
> 0x0000008e:   DW_TAG_base_type
>                 DW_AT_name	("character(kind=4)")
>                 DW_AT_encoding	(DW_ATE_UCS)
>                 DW_AT_byte_size	(0x04)                                                   <=== inconsistent with the 28 above
> ```
> 
> It would be nice to fix it via something like,
> 
> metadata side:
> 
> ```
> stringLengthExpression: !DIExpression(DW_OP_push_object_address, DW_OP_plus_uconst, 8,
>                                       DW_OP_deref, DW_OP_constu, <kind>, DW_OP_div,
>                                       DW_OP_stack_value)
> ```
> 
> then the DWARF side should be as expected:
> 
> ```
> DW_AT_string_length	(DW_OP_push_object_address, DW_OP_plus_uconst 0x8, DW_OP_deref,
>                      DW_OP_constu 0x4, DW_OP_div, DW_OP_stack_value)
> ```

Agreed, elem_len is in bytes, so the length comes out kind times too large for non-default kinds. I tried your expression and gdb then shows character (7) instead of character (28). This can be done in this PR or as a follow-up.

https://github.com/llvm/llvm-project/pull/231960


More information about the flang-commits mailing list