]> git.ipfire.org Git - thirdparty/binutils-gdb.git/commitdiff
include: sframe: doc: define new flag SFRAME_F_FDE_FUNC_START_ADDR_PCREL
authorIndu Bhagat <indu.bhagat@oracle.com>
Thu, 24 Apr 2025 21:59:56 +0000 (14:59 -0700)
committerIndu Bhagat <indu.bhagat@oracle.com>
Wed, 25 Jun 2025 19:56:19 +0000 (12:56 -0700)
Add a new flag SFRAME_F_FDE_FUNC_START_ADDR_PCREL to SFrame stack trace
format.  If set, this flag indicates that the function start address
field (sfde_func_start_address) is the offset to the function start
address from the SFrame FDE function start address field itself.

Such an encoding is friendlier to the exisitng PC-REL relocations
available in the ABIs supported in SFrame: AMD64 (R_X86_64_PC32) and
AArch64 (R_AARCH64_PREL32).  In subsequent patches, we will make the
implementation in gas and ld to both:
  - emit the values in the same (above-mentioned) encoding uniformly.
  - set the flag SFRAME_F_FDE_FUNC_START_ADDR_PCREL in the SFrame header
    for consumers to be able to distinguish.

Define SFRAME_F_ALL_FLAGS in sframe-api.h to help keep the
implementation less error-prone by keeping a set of all defined flags at
a central place.  Adjust the check in sframe_header_sanity_check_p () to
use the SFRAME_F_ALL_FLAGS instead.

Add documentation for SFRAME_F_FDE_FUNC_START_ADDR_PCREL.  Update the
documentation about the encoding of the sfde_func_start_address field.

Also, update the section "Changes from Version 1 to Version 2" to
include the specification of the new flag
SFRAME_F_FDE_FUNC_START_ADDR_PCREL as an errata release to the SFrame
Version 2 specification.

include/
        * sframe-api.h (SFRAME_F_ALL_FLAGS): New definition.
        * sframe.h (SFRAME_F_FDE_FUNC_START_ADDR_PCREL): Likewise.
libsframe/
* sframe-dump.c (dump_sframe_header_flags): Update to include
the new flag.
* sframe.c (sframe_header_sanity_check_p): Use uint8_t.
libsframe/doc/
* sframe-spec.texi: Add details about the new flag.  Also update
the defails about the sfde_func_start_address encoding.

---
[Changes in V4]
 - Define new SFRAME_F_ALL_FLAGS in sframe-api.h.  Use it in
   sframe_header_sanity_check_p ().  Mention SFRAME_F_ALL_FLAGS in the
   commit log.
 - Add one liner in the SFrame spec "Bits corresponding to the currently
   undefined flags must be set to zero."
[End of changes in V4]

[No changes in V3]

[Changes in V2]
  - Switch back to the old style of flag values.
  - Merge three patches from V1 into a single patch
    include: libsframe: add APIs for offsetof FDE func start addr field
    doc: sframe: add documentation for SFRAME_F_FDE_FUNC_START_ADDR_PCREL
    doc: sframe: update documentation for sfde_func_start_address
[End of changes in V2]

include/sframe-api.h
include/sframe.h
libsframe/doc/sframe-spec.texi
libsframe/sframe-dump.c
libsframe/sframe.c

index 3dc18b6ad394977f97f595c38390210ba2974941..0dfdd289b82f1680f74f704dd2800bc782a5ae05 100644 (file)
@@ -36,6 +36,14 @@ typedef struct sframe_encoder_ctx sframe_encoder_ctx;
 #define MAX_OFFSET_BYTES  \
   ((SFRAME_FRE_OFFSET_4B * 2 * MAX_NUM_STACK_OFFSETS))
 
+/* Set of all defined flags known to this implementation.  Any flag other than
+   these, if set, is deemed invalid.  This is used for sanity checking to
+   ensure that the implementation only admits sections with flags defined in
+   the specific version.  */
+#define SFRAME_F_ALL_FLAGS \
+  (SFRAME_F_FDE_SORTED | SFRAME_F_FRAME_POINTER \
+   | SFRAME_F_FDE_FUNC_START_ADDR_PCREL)
+
 /* User interfacing SFrame Row Entry.
    An abstraction provided by libsframe so the consumer is decoupled from
    the binary format representation of the same.
index a965e23bdd1817e4eef513bd126de0f6f542de18..11cbc9b5b0f15ccf2f6fb4decf16a649377a2661 100644 (file)
@@ -82,9 +82,15 @@ extern "C"
 /* Various flags for SFrame.  */
 
 /* Function Descriptor Entries are sorted on PC.  */
-#define SFRAME_F_FDE_SORTED    0x1
+#define SFRAME_F_FDE_SORTED                0x1
 /* Functions preserve frame pointer.  */
-#define SFRAME_F_FRAME_POINTER 0x2
+#define SFRAME_F_FRAME_POINTER             0x2
+/* Function start address in SFrame FDE is encoded as the distance from the
+   location of the sfde_func_start_address to the start PC of the function.
+   If absent, the function start address in SFrame FDE is encoded as the
+   distance from the start of the SFrame FDE section to the start PC of the
+   function.  */
+#define SFRAME_F_FDE_FUNC_START_ADDR_PCREL  0x4
 
 #define SFRAME_CFA_FIXED_FP_INVALID 0
 #define SFRAME_CFA_FIXED_RA_INVALID 0
index 6b8dfa8065005f5888a28d5fed5bd595edd33ea1..0574ac57d5dd514ada282ea12ad512b9103a6b69 100644 (file)
@@ -128,6 +128,17 @@ the data structure.
 @item
 The above two imply that each SFrame function descriptor entry has a fixed size
 of 20 bytes instead of its size of 17 bytes in SFrame format version 1.
+@item
+A new flag SFRAME_F_FDE_FUNC_START_ADDR_PCREL, released as an errata to SFrame
+Version 2, to indicate the encoding of the SFrame FDE function start address
+field:
+ @itemize @minus
+  @item if set, @code{sfde_func_start_address} field contains the offset in
+bytes to the start PC of the associated function from the field itself.
+  @item if unset, @code{sfde_func_start_address} field contains the offset in
+bytes to the start PC of the associated function from the start of the SFrame
+section.
+ @end itemize
 @end itemize
 
 SFrame version 1 is now obsolete and should not be used.
@@ -234,21 +245,28 @@ describe various section-wide properties.
 
 The following flags are currently defined.
 
-@multitable {@code{SFRAME_F_FRAME_POINTER}} {Versions} {Value} {Function Descriptor Entries}
-@headitem Flag @tab Versions @tab Value @tab Meaning
+@multitable {@code{SFRAME_F_FRAME_POINTER}} {Version} {Value} {Function Descriptor Entries are sorted}
+@headitem Flag @tab Version @tab Value @tab Meaning
 @tindex SFRAME_F_FDE_SORTED
 @item @code{SFRAME_F_FDE_SORTED} @tab All @tab 0x1 @tab Function Descriptor
 Entries are sorted on PC.
 @tindex SFRAME_F_FRAME_POINTER
 @item @code{SFRAME_F_FRAME_POINTER} @tab All @tab 0x2
 @tab All functions in the object file preserve frame pointer.
+@tindex SFRAME_F_FDE_FUNC_START_ADDR_PCREL
+@item @code{SFRAME_F_FDE_FUNC_START_ADDR_PCREL} @tab 2 @tab 0x4
+@tab The @code{sfde_func_start_address} field in the SFrame FDE is an offset in
+bytes to the function's start address, from the field itself.  If unset, the
+@code{sfde_func_start_address} field in the SFrame FDE is an offset in bytes to
+the function's start address, from the start of the SFrame section.
 @end multitable
 
 The purpose of SFRAME_F_FRAME_POINTER flag is to facilitate stack tracers to
 reliably fallback on the frame pointer based stack tracing method, if SFrame
 information is not present for some function in the SFrame section.
 
-Further flags may be added in future.
+Further flags may be added in future.  Bits corresponding to the currently
+undefined flags must be set to zero.
 
 @node SFrame Header
 @section SFrame Header
@@ -461,9 +479,11 @@ Following table describes each component of the SFrame FDE structure:
 @tab @code{int32_t}
 @tab @code{sfde_func_start_address}
 @tab Signed 32-bit integral field denoting the virtual memory address of the
-described function, for which the SFrame FDE applies.  The value encoded in
-the @code{sfde_func_start_address} field is the offset in bytes of the
-function's start address, from the SFrame section.
+described function, for which the SFrame FDE applies.  If the flag
+@code{SFRAME_F_FDE_FUNC_START_ADDR_PCREL}, @xref{SFrame Flags}, in the SFrame
+header is set, the value encoded in the @code{sfde_func_start_address} field is
+the offset in bytes to the function's start address, from the SFrame
+@code{sfde_func_start_address} field.
 
 @item 0x04
 @tab @code{uint32_t}
index c1b0fb166a891cd46ad165d7cf96b3b684557836..bc0d5e46b039e6ff622575dcca5adcd6de5ac9e3 100644 (file)
@@ -60,6 +60,7 @@ dump_sframe_header_flags (sframe_decoder_ctx *sfd_ctx)
 
   PRINT_FLAG (SFRAME_F_FDE_SORTED);
   PRINT_FLAG (SFRAME_F_FRAME_POINTER);
+  PRINT_FLAG (SFRAME_F_FDE_FUNC_START_ADDR_PCREL);
 #undef PRINT_FLAG
 
   /* Print any residual flags, should this implementation be out of sync when
index d212b4f88c964caf5b6a88efb11eb040092d65f9..8be7bec8917170caecbbbbee66779f11a1299eec 100644 (file)
@@ -205,12 +205,11 @@ flip_fde (sframe_func_desc_entry *fdep)
 static bool
 sframe_header_sanity_check_p (sframe_header *hp)
 {
-  unsigned char all_flags = SFRAME_F_FDE_SORTED | SFRAME_F_FRAME_POINTER;
   /* Check preamble is valid.  */
   if (hp->sfh_preamble.sfp_magic != SFRAME_MAGIC
       || (hp->sfh_preamble.sfp_version != SFRAME_VERSION_1
          && hp->sfh_preamble.sfp_version != SFRAME_VERSION_2)
-      || (hp->sfh_preamble.sfp_flags | all_flags) != all_flags)
+      || hp->sfh_preamble.sfp_flags & ~SFRAME_F_ALL_FLAGS)
     return false;
 
   /* Check offsets are valid.  */