[Lldb-commits] [lldb] Use `llvm::APInt` for `VariantMember` Discriminants (PR #188487)

Jonas Devlieghere via lldb-commits lldb-commits at lists.llvm.org
Fri Apr 10 05:02:09 PDT 2026


================
@@ -2596,8 +2597,31 @@ bool VariantMember::IsDefault() const { return !discr_value; }
 
 VariantMember::VariantMember(DWARFDIE &die, lldb::ModuleSP module_sp) {
   assert(die.Tag() == llvm::dwarf::DW_TAG_variant);
-  this->discr_value =
-      die.GetAttributeValueAsOptionalUnsigned(DW_AT_discr_value);
+
+  DWARFFormValue discr_form;
+  die.GetDIE()->GetAttributeValue(die.GetCU(), DW_AT_discr_value, discr_form);
+
+  // rust can output 128-bit discrs (e.g. NonNull<u128>) as `DW_FORM_block1`.
+  // there is a `data16`, but the DIE function treats it as a block anyway.
+  // Handling is included for it just in case rust's output changes to the
+  // `data16` version
+  dw_form_t form = discr_form.Form();
+  if ((form == DW_FORM_block1 && discr_form.Unsigned() == 16) ||
+      form == DW_FORM_data16) {
+    const uint8_t *block_data = discr_form.BlockData();
+
+    llvm::ArrayRef<uint64_t> data =
+        llvm::ArrayRef(reinterpret_cast<const uint64_t *>(block_data), 2);
----------------
JDevlieghere wrote:

This assumes the host and DWARF byte order match. I think you want something like:

```
    DataExtractor extractor(block_data, 16, die.GetCU()->GetByteOrder(),
                             die.GetCU()->GetAddressByteSize());
    lldb::offset_t offset = 0;
    uint64_t lo = extractor.GetU64(&offset);
    uint64_t hi = extractor.GetU64(&offset);
    uint64_t words[] = {lo, hi};
    this->discr_value = llvm::APInt(128, words);
```

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


More information about the lldb-commits mailing list