public inbox for gcc-cvs@sourceware.org help / color / mirror / Atom feed
From: Matthew Malcomson <matmal01@gcc.gnu.org> To: gcc-cvs@gcc.gnu.org Subject: [gcc(refs/vendors/ARM/heads/morello)] Fix up some cheri warnings in libgcc Date: Mon, 14 Mar 2022 10:35:47 +0000 (GMT) [thread overview] Message-ID: <20220314103547.C7C66385E445@sourceware.org> (raw) https://gcc.gnu.org/g:9b82fa20f04768be50824a2e4ce8762a1a3db7ef commit 9b82fa20f04768be50824a2e4ce8762a1a3db7ef Author: Matthew Malcomson <matthew.malcomson@arm.com> Date: Mon Mar 7 18:04:39 2022 +0000 Fix up some cheri warnings in libgcc In emutls.c we introduce a new type to represent an address, to ensure we have the same distinction between pointer and address here as everywhere else. This allows us to remove a provenance warning on a binary operation between two capabilities. One point of note is that we use __attribute__((mode(address))) rather than ptraddr_t. This is because ptraddr_t is not necessarily defined for all targets, while __attribute__((mode(address))) is. We care about this more inside libgcc than in other software since this software is supposed to be as portable as GCC is. In the GCC C-language personality function we avoid some provenance warnings by using _Unwind_Address in some binary operations, and we cast an _Unwind_Ptr to a void * before passing it to __builtin_code_address_from_pointer. In unwind-dw2 and unwind-dw2-fde we just need to make the difference between an address and a pointer clear for the compiler. We record addresses in many structures since they are smaller and we only need the address. Our functions for reading in encoded values need to be able to return capabilities because we can have capabilities stored (indirectly) in the debug information. Hence we now need to cast from the "read" value type to the "for use" value type. Avoid unaligned warnings in `read_encoded_value_with_base`. We know the union we define is not aligned for capabilities, but we handle it manually ourselves (there is never a capability directly in the debug information, but there can be `void *`'s for other backends). Mark the __EH_FRAME_BEGIN__ symbol as being used in the inline assembly that the purecap implementation of get_eh_frame_begin is implemented with. This avoids a warning, and avoids the possibility of the variable being optimised away. Add the EH_FRAME_SECTION_CONST macro (which expands to `const` or the empty string depending on configuration settings) to the declaration of `get_eh_frame_begin` so the function does not discard the `const` attribute. We adjust our `asm` directive so that it indicates we are using the __EH_FRAME_BEGIN__ symbol as this avoids an unused variable warning. Diff: --- libgcc/crtstuff.c | 12 ++++++------ libgcc/emutls.c | 3 ++- libgcc/unwind-c.c | 4 ++-- libgcc/unwind-dw2-fde.c | 9 +++++---- libgcc/unwind-dw2.c | 2 +- libgcc/unwind-dw2.h | 9 ++++++--- libgcc/unwind-pe.h | 7 +++++++ 7 files changed, 29 insertions(+), 17 deletions(-) diff --git a/libgcc/crtstuff.c b/libgcc/crtstuff.c index 225af9db8a0..74470f1c923 100644 --- a/libgcc/crtstuff.c +++ b/libgcc/crtstuff.c @@ -263,7 +263,7 @@ STATIC func_ptr __DTOR_LIST__[1] STATIC EH_FRAME_SECTION_CONST char __EH_FRAME_BEGIN__[] __attribute__((section(__LIBGCC_EH_FRAME_SECTION_NAME__), aligned(4))) = { }; -# ifdef __CHERI_PURE_CAPABILITY__ && defined (__aarch64__) +# if defined (__CHERI_PURE_CAPABILITY__) && defined (__aarch64__) /* MORELLO __EH_FRAME_BEGIN__ marks the start of the .eh_frame section. The __register_frame_info* functions below pass this to the unwinder so that it knows where to access the dwarf unwinding information from. @@ -273,19 +273,19 @@ STATIC EH_FRAME_SECTION_CONST char __EH_FRAME_BEGIN__[] N.b. this is pretty useful in development since PCC gives us executable permissions, which means we can use the landing-pad offset info rather than having to implement both at the same time. */ -static inline void * +static inline EH_FRAME_SECTION_CONST void * get_eh_frame_begin (void) { void *ret; - asm ("adrp %0, __EH_FRAME_BEGIN__\n\t" - "add %0, %0, :lo12:__EH_FRAME_BEGIN__" - : "=r" (ret) : ); + asm ("adrp %0, %1\n\t" + "add %0, %0, :lo12:%1" + : "=r" (ret) : "S" (__EH_FRAME_BEGIN__)); return ret; } # elif defined (__CHERI_PURE_CAPABILITY__) # error libgcc crtstuff not updated for non-Morello capability target. # else -static inline void * +static inline EH_FRAME_SECTION_CONST void * get_eh_frame_begin (void) { return __EH_FRAME_BEGIN__; diff --git a/libgcc/emutls.c b/libgcc/emutls.c index 5f23e626b94..9bc514cf3d7 100644 --- a/libgcc/emutls.c +++ b/libgcc/emutls.c @@ -32,6 +32,7 @@ see the files COPYING3 and COPYING.RUNTIME respectively. If not, see typedef unsigned int word __attribute__((mode(word))); typedef __UINTPTR_TYPE__ pointer; +typedef unsigned address_t __attribute__((mode(address))); struct __emutls_object { @@ -111,7 +112,7 @@ emutls_alloc (struct __emutls_object *obj) if (ptr == NULL) abort (); ret = (void *) (((pointer) (ptr + sizeof (void *) + obj->align - 1)) - & ~(pointer)(obj->align - 1)); + & ~(address_t)(obj->align - 1)); ((void **) ret)[-1] = ptr; } diff --git a/libgcc/unwind-c.c b/libgcc/unwind-c.c index 24a464fa670..be553ae970b 100644 --- a/libgcc/unwind-c.c +++ b/libgcc/unwind-c.c @@ -169,7 +169,7 @@ PERSONALITY_FUNCTION (int version, #ifdef __USING_SJLJ_EXCEPTIONS__ ip = (_Unwind_Address) ip_ptr; #else - ip = __builtin_code_address_from_pointer (ip_ptr); + ip = __builtin_code_address_from_pointer ((void*)ip_ptr); #endif if (! ip_before_insn) @@ -226,7 +226,7 @@ PERSONALITY_FUNCTION (int version, /* The table is sorted, so if we've passed the ip, stop. */ if (ip < info.Start + cs_start) p = info.action_table; - else if (ip < info.Start + cs_start + cs_len) + else if (ip < info.Start + (_Unwind_Address)cs_start + (_Unwind_Address)cs_len) { if (cs_lp) { diff --git a/libgcc/unwind-dw2-fde.c b/libgcc/unwind-dw2-fde.c index 609507db638..26be05d4aca 100644 --- a/libgcc/unwind-dw2-fde.c +++ b/libgcc/unwind-dw2-fde.c @@ -668,6 +668,7 @@ classify_object_over_fdes (struct object *ob, const fde *this_fde) read_encoded_value_with_base (encoding, base, this_fde->pc_begin, &pc_begin); + _Unwind_Address pc_begin_addr = (_Unwind_Address)pc_begin; /* Take care to ignore link-once functions that were removed. In these cases, the function address will be NULL, but if @@ -679,12 +680,12 @@ classify_object_over_fdes (struct object *ob, const fde *this_fde) else mask = -1; - if ((pc_begin & mask) == 0) + if ((pc_begin_addr & mask) == 0) continue; count += 1; - if (pc_begin < ob->pc_begin) - ob->pc_begin = pc_begin; + if (pc_begin_addr < (_Unwind_Address)ob->pc_begin) + ob->pc_begin = (void *) pc_begin; } return count; @@ -911,7 +912,7 @@ binary_search_unencoded_fdes (struct object *ob, _Unwind_Address pc) memcpy (&pc_begin, (const void * const *) f->pc_begin, sizeof (void *)); memcpy (&pc_range, (const uaddr *) f->pc_begin + 1, sizeof (uaddr)); - if (pc < pc_begin) + if ((_Unwind_Address)pc < pc_begin) hi = i; else if (pc >= pc_begin + pc_range) lo = i + 1; diff --git a/libgcc/unwind-dw2.c b/libgcc/unwind-dw2.c index 2b964a0e495..096476e041c 100644 --- a/libgcc/unwind-dw2.c +++ b/libgcc/unwind-dw2.c @@ -1316,7 +1316,7 @@ uw_frame_state_for (struct _Unwind_Context *context, _Unwind_FrameState *fs) #endif } - fs->pc = context->bases.func; + fs->pc = (_Unwind_Address)context->bases.func; cie = get_cie (fde); insn = extract_cie_info (cie, context, fs); diff --git a/libgcc/unwind-dw2.h b/libgcc/unwind-dw2.h index 1c4977d97e2..615fe590feb 100644 --- a/libgcc/unwind-dw2.h +++ b/libgcc/unwind-dw2.h @@ -64,9 +64,12 @@ typedef struct } regs; /* The PC described by the current frame state. - This is read from the CFA data or FDE pc range. Hence on capability - architectures it is an address rather than a pointer. For non-capability - architectures _Unwind_Address is the same as a pointer. */ + This is read from the CFA data or FDE pc range. On capability + architectures it can be a pointer, but will never be an executable pointer + (since reading from the DWARF information can only have the permissions of + the capability we use for a base, and we never use an executable + capability for such a base). For non-capability architectures + _Unwind_Address is the same as a pointer. */ _Unwind_Address pc; /* The information we care about from the CIE/FDE. */ diff --git a/libgcc/unwind-pe.h b/libgcc/unwind-pe.h index 1b0496527b8..f96a0d95c73 100644 --- a/libgcc/unwind-pe.h +++ b/libgcc/unwind-pe.h @@ -184,6 +184,12 @@ static const unsigned char * read_encoded_value_with_base (unsigned char encoding, _Unwind_Ptr base, const unsigned char *p, _Unwind_Ptr *val) { + /* This structure can not hold capabilities since it is not aligned. + That is just fine, since (in the ABI's supported currently) capabilities + are never directly embedded in DWARF information so that the eh_frame + section can be read-only. */ +#pragma GCC diagnostic push +#pragma GCC diagnostic ignored "-Wif-not-aligned" union unaligned { void *ptr; @@ -194,6 +200,7 @@ read_encoded_value_with_base (unsigned char encoding, _Unwind_Ptr base, signed s4 __attribute__ ((mode (SI))); signed s8 __attribute__ ((mode (DI))); } __attribute__((__packed__)); +#pragma GCC diagnostic pop const union unaligned *u = (const union unaligned *) p; _Unwind_Internal_Ptr result;
reply other threads:[~2022-03-14 10:35 UTC|newest] Thread overview: [no followups] expand[flat|nested] mbox.gz Atom feed
Reply instructions: You may reply publicly to this message via plain-text email using any one of the following methods: * Save the following mbox file, import it into your mail client, and reply-to-all from there: mbox Avoid top-posting and favor interleaved quoting: https://en.wikipedia.org/wiki/Posting_style#Interleaved_style * Reply using the --to, --cc, and --in-reply-to switches of git-send-email(1): git send-email \ --in-reply-to=20220314103547.C7C66385E445@sourceware.org \ --to=matmal01@gcc.gnu.org \ --cc=gcc-cvs@gcc.gnu.org \ /path/to/YOUR_REPLY https://kernel.org/pub/software/scm/git/docs/git-send-email.html * If your mail client supports setting the In-Reply-To header via mailto: links, try the mailto: linkBe sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).