diff mbox series

[3/9] livepatch-build: fix detection of structure sizes

Message ID 20240429145654.71669-4-roger.pau@citrix.com (mailing list archive)
State New
Headers show
Series livepatch-build-tools: some bug fixes and improvements | expand

Commit Message

Roger Pau Monne April 29, 2024, 2:56 p.m. UTC
The current runes assume that in the list of DWARF tags DW_AT_byte_size will
come after DW_AT_name, but that's not always the case.  On one of my builds
I've seen:

    <b618>   DW_AT_name        : (indirect string, offset: 0x3c45): exception_table_entry
    <b61c>   DW_AT_declaration : 1
 <1><b61c>: Abbrev Number: 5 (DW_TAG_const_type)
    <b61d>   DW_AT_type        : <0xb617>
 <1><b621>: Abbrev Number: 14 (DW_TAG_pointer_type)
    <b622>   DW_AT_byte_size   : 8

Instead of assuming such order, explicitly search for the DW_AT_byte_size tag
when a match in the DW_AT_name one is found.

Signed-off-by: Roger Pau Monné <roger.pau@citrix.com>
---
All this ad hoc parsing of DWARF data seems very fragile.  This is an
improvement over the current logic, but I would still prefer if we could find a
more reliable way to obtain the struct sizes we need.
---
 livepatch-build | 7 +++++++
 1 file changed, 7 insertions(+)
diff mbox series

Patch

diff --git a/livepatch-build b/livepatch-build
index f3ca9399d149..aad9849f2ba9 100755
--- a/livepatch-build
+++ b/livepatch-build
@@ -427,9 +427,16 @@  if [ "${SKIP}" != "build" ]; then
     SPECIAL_VARS=$(readelf -wi "$OUTPUT/xen-syms" |
                awk '
                BEGIN { a = b = e = 0 }
+               # Ensure no fall through to the next tag without getting the size
+               (a == 1 || b == 1 || e == 1) && /DW_AT_name/ \
+                   {print "can not get special structure size" > "/dev/stderr"; exit 1}
                a == 0 && /DW_AT_name.* alt_instr/ {a = 1; next}
                b == 0 && /DW_AT_name.* bug_frame/ {b = 1; next}
                e == 0 && /DW_AT_name.* exception_table_entry/ {e = 1; next}
+               # Seek the line that contains the size
+               a == 1 && !/DW_AT_byte_size/ {next}
+               b == 1 && !/DW_AT_byte_size/ {next}
+               e == 1 && !/DW_AT_byte_size/ {next}
                # Use shell printf to (possibly) convert from hex to decimal
                a == 1 {printf("export ALT_STRUCT_SIZE=`printf \"%%d\" \"%s\"`\n", $4); a = 2}
                b == 1 {printf("export BUG_STRUCT_SIZE=`printf \"%%d\" \"%s\"`\n", $4); b = 2}