Op 03-06-2021 om 00:50 schreef David Blaikie via Dwarf-Discuss:
On Fri, May 28, 2021 at 8:29 AM Joost van der Sluis via Dwarf-Discuss
<dwarf-discuss@lists.dwarfstd.org> wrote:
Now in Pascal there are 'properties'. Maybe you know these from c# which
has something alike. Basically a property is an alias in a structure
that links to other members of the same structure for reading, writing
and/or storage-information.

Hmm - so this isn't like C# where you can write arbitrary code for the
property? In this case it's only direct access - but you get to choose
whether it's read only, read-write, etc, compared to having the member
directly be public?

That might 'just work' with existing DWARF consumers/debuggers if you
had the alias as another member (as you say, with different access
level) that happens to have the same data_member_location as the
underlying member - you could add an extra/extension attribute to
describe it as being read only, etc.

I doubt the duplication of the data_member_location would be super
expensive - but I could be wrong. Might be worth measuring, especially
if this representational choice does get you "free" support in
existing DWARF consumers, compared to having to teach them about new
attributes, etc.

They can do both - direct access and arbitrary code. And I agree that in the case of direct access it is not that expensive.

Example:

type
    TMyClass=class
    private
      FProp: Integer;
      FPropIsStored: Boolean;
    protected
      function GetProp: Integer;
      function GetItem(const Index: Integer): string;
    public
      property IndividualItem[Index: Integer]: string read GetItem;
    published
      property Prop: Integer read GetProp stored FPropIsStored;
      property OtherProp: Integer read FProp write FProp;
      property Item2: string index 2 read GetItem;
    end;

var
    MyClass = TMyClass;

Reading MyClass.Prop effectively calls GetProp.

MyClass.Prop is read-only, and during streaming the information in
FPropIsStored is being used.

MyClass.OtherProp is read/write, and is more or less an alias for the
private FProp field.

MyClass.IndividualItem[6] is accessible like it is an array. And Item2
has a fixed index.

I want to encode this propery into the Dwarf debug-information.

First question I usually ask is: Is there any prior art? (does GCC
support this situation, what DWARF does it use to describe these
entities? What about other DWARF producers?)

Yes, that would be easy. But I do not know of any feature in C or C++ or any other language that is comparable to this functionality, except for C#, but that does not generate Dwarf debug-information. But I am well aware that do not know all existing languages that well. ;)

At this
moment we only generate debug-information for cases similar to
MyClass.OtherProp by duplicating the debug-information of FProp with
another visibility-class.

Ah, guess that's my suggestion above?

Yes.

I've added the following attributes:
    DW_AT_FPC_property_read (0x3230)
    DW_AT_FPC_property_write (0x3231)
    DW_AT_FPC_property_stored (0x3232)

And then those attributes contain a link to the corresponding
DW_TAG_members.

OK, so FW_AT_FPC_property_stored uses an address form, most likely a
CU-local one, like DW_FORM_ref4, etc?

Well, my current implementation always uses DW_FORM_ref_addr, but I now
realize that this should be a DW_FORM_ref4 most of the time.
It is possible to reference a member in a another CU, though. So local is not always possible.

This to keep the debug-information as compact as
possible. Furthermore I've added the tag DW_TAG_FPC_property (0x4230) or
else other debuggers may be confused when they encounter a DW_TAG_member
with only one or more of these specific fpc-attributes.

I'll also have to add something like DW_AT_FPC_property_index to store
the value of a fixed index.

I have two questions:
1. Am I on the good track, or did I miss something?

Sounds plausible.

2. Maybe implementation specific, but maybe someone might have an idea:
to generate the proposed debug-info, I need to add a label to every
DW_TAG_member.

The way LLVM deals with CU-local DIE references isn't with labels - it
precomputes the offsets of all the DIEs and uses the known offset for
the FORM value.

You can see that here: https://godbolt.org/z/hqdP4x5eG

.long 51 # DW_AT_type

But LLVM also uses labels and relocations without issue - especially
local labels (as Michael mentioned), section labels, and label
differences (the latter is all you'd need if you wanted to do
CU-relative references with labels instead of manually computing them)
- label differences are resolved at assembly time, so they don't exist
by the time the linker sees things & can't complicate that.

Yes, for cu-local references I can use local-labels and use their differences.

For cu-global I have to precompute the offsets for a global label, this must be doable.

Thank you and Michael for the input.

Using global labels inside these structures though, may
lead to all kinds of troubles, for example when a linker regards these
labels as the start of a new section. Or on Darwin/macOS. Calculating
the location of these tags is in principle possible I think, but
difficult. Any tips here?

This is a dwarfdump of the class-definition above with my current additions:

< 1><0x00000123>    DW_TAG_class_type
                        DW_AT_name                  TMyClass
                        DW_AT_byte_size             0x00000010
< 2><0x0000012e>      DW_TAG_inheritance
                          DW_AT_accessibility         DW_ACCESS_public
                          DW_AT_data_member_location  DW_OP_plus_uconst 0
                          DW_AT_type                  <GOFF=0x00005122>
< 2><0x00000137>      DW_TAG_member
                          DW_AT_name                  FProp
                          DW_AT_data_member_location  DW_OP_plus_uconst 8
                          DW_AT_accessibility         DW_ACCESS_private
                          DW_AT_type                  <GOFF=0x000000f3>
< 2><0x00000146>      DW_TAG_member
                          DW_AT_name                  FPropIsStored
                          DW_AT_data_member_location  DW_OP_plus_uconst 12
                          DW_AT_accessibility         DW_ACCESS_private
                          DW_AT_type                  <GOFF=0x000057a7>
< 2><0x0000015d>      <Unknown TAG value 0x4230>
                          DW_AT_name                  IndividualItem
                          <Unknown AT value 0x3230>   <GOFF=0x0000020c>
                          DW_AT_type                  <GOFF=0x000057c4>
< 2><0x00000175>      <Unknown TAG value 0x4230>
                          DW_AT_name                  Prop
                          <Unknown AT value 0x3230>   <GOFF=0x000001ad>
                          <Unknown AT value 0x3232>   <GOFF=0x00000146>
                          DW_AT_type                  <GOFF=0x000000f3>
< 2><0x00000187>      <Unknown TAG value 0x4230>
                          DW_AT_name                  OtherProp
                          <Unknown AT value 0x3230>   <GOFF=0x00000137>
                          <Unknown AT value 0x3231>   <GOFF=0x00000137>
                          DW_AT_type                  <GOFF=0x000000f3>
< 2><0x0000019e>      <Unknown TAG value 0x4230>
                          DW_AT_name                  Item2
                          <Unknown AT value 0x3230>   <GOFF=0x0000020c>
                          DW_AT_type                  <GOFF=0x000057c4>
< 2><0x000001ad>      DW_TAG_subprogram
                          DW_AT_name                  GetProp
                          DW_AT_prototyped            yes(1)
                          DW_AT_calling_convention
DW_CC_GNU_borland_fastcall_i386
                          DW_AT_external              yes(1)
                          DW_AT_accessibility         DW_ACCESS_protected
                          DW_AT_type                  <GOFF=0x000000f3>
                          DW_AT_low_pc                0x00404840
                          DW_AT_high_pc               0x00404867
< 3><0x000001ce>        DW_TAG_formal_parameter
                            DW_AT_name                  this
                            DW_AT_location              0x7678 DW_OP_breg6-8
                            DW_AT_artificial            yes(1)
                            DW_AT_type                  <GOFF=0x00000110>
< 3><0x000001dc>        DW_TAG_variable
                            DW_AT_name                  $result
                            DW_AT_location              0x7674 DW_OP_breg6-12
                            DW_AT_type                  <GOFF=0x000000f3>
< 3><0x000001ec>        DW_TAG_variable
                            DW_AT_name                  GETPROP
                            DW_AT_location              0x7674 DW_OP_breg6-12
                            DW_AT_type                  <GOFF=0x000000f3>
< 3><0x000001fc>        DW_TAG_variable
                            DW_AT_name                  RESULT
                            DW_AT_location              0x7674 DW_OP_breg6-12
                            DW_AT_type                  <GOFF=0x000000f3>
< 2><0x0000020c>      DW_TAG_subprogram
                          DW_AT_name                  GetItem
                          DW_AT_prototyped            yes(1)
                          DW_AT_calling_convention
DW_CC_GNU_borland_fastcall_i386
                          DW_AT_external              yes(1)
                          DW_AT_accessibility         DW_ACCESS_protected
                          DW_AT_type                  <GOFF=0x000057c4>
                          DW_AT_low_pc                0x00404870
                          DW_AT_high_pc               0x00404889
< 3><0x0000022d>        DW_TAG_formal_parameter
                            DW_AT_name                  this
                            DW_AT_location              0x7670 DW_OP_breg6-16
                            DW_AT_artificial            yes(1)
                            DW_AT_type                  <GOFF=0x00000110>
< 3><0x0000023b>        DW_TAG_variable
                            DW_AT_name                  $result
                            DW_AT_location              0x766806
DW_OP_breg6-24 DW_OP_deref
                            DW_AT_type                  <GOFF=0x000057c4>
< 3><0x0000024c>        DW_TAG_formal_parameter
                            DW_AT_name                  Index
                            DW_AT_location              0x7678 DW_OP_breg6-8
                            DW_AT_type                  <GOFF=0x000000f3>
< 3><0x0000025a>        DW_TAG_variable
                            DW_AT_name                  GETITEM
                            DW_AT_location              0x766806
DW_OP_breg6-24 DW_OP_deref
                            DW_AT_type                  <GOFF=0x000057c4>
< 3><0x0000026b>        DW_TAG_variable
                            DW_AT_name                  RESULT
                            DW_AT_location              0x766806
DW_OP_breg6-24 DW_OP_deref
                            DW_AT_type                  <GOFF=0x000057c4>



_______________________________________________
Dwarf-Discuss mailing list
Dwarf-Discuss@lists.dwarfstd.org
http://lists.dwarfstd.org/listinfo.cgi/dwarf-discuss-dwarfstd.org
_______________________________________________
Dwarf-Discuss mailing list
Dwarf-Discuss@lists.dwarfstd.org
http://lists.dwarfstd.org/listinfo.cgi/dwarf-discuss-dwarfstd.org

_______________________________________________
Dwarf-Discuss mailing list
Dwarf-Discuss@lists.dwarfstd.org
http://lists.dwarfstd.org/listinfo.cgi/dwarf-discuss-dwarfstd.org

Reply via email to