From patchwork Wed May 4 08:59:13 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Martin_Li=C5=A1ka?= X-Patchwork-Id: 53448 Return-Path: X-Original-To: patchwork@sourceware.org Delivered-To: patchwork@sourceware.org Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id 8C2343856DE5 for ; Wed, 4 May 2022 08:59:39 +0000 (GMT) X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from smtp-out2.suse.de (smtp-out2.suse.de [195.135.220.29]) by sourceware.org (Postfix) with ESMTPS id 176E23858C56 for ; Wed, 4 May 2022 08:59:15 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.1 sourceware.org 176E23858C56 Authentication-Results: sourceware.org; dmarc=none (p=none dis=none) header.from=suse.cz Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=suse.cz Received: from imap2.suse-dmz.suse.de (imap2.suse-dmz.suse.de [192.168.254.74]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-521) server-digest SHA512) (No client certificate requested) by smtp-out2.suse.de (Postfix) with ESMTPS id D42411F749 for ; Wed, 4 May 2022 08:59:13 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=suse.cz; s=susede2_rsa; t=1651654753; h=from:from:reply-to:date:date:message-id:message-id:to:to:cc: mime-version:mime-version:content-type:content-type; bh=qk5d36k+IR3sDp3NaSAQ5M7FuWwkXnYN13289jk55Ac=; b=lnTMtYJdwsoW3pru6/KFrKJ6NdDAbtUGvGc65Ee/QA8/D0gudQmvhyclnFdldVPperqnWT STLm/b6hJnyFNz1sOOmVcS8s0l7ZgpoOaJGqamqYRvHkaNO9Ng949aqqv6GbOY+o0YroB+ mzdmXlFM6S1AaDyiYlZapDTNu0ykSmE= DKIM-Signature: v=1; a=ed25519-sha256; c=relaxed/relaxed; d=suse.cz; s=susede2_ed25519; t=1651654753; h=from:from:reply-to:date:date:message-id:message-id:to:to:cc: mime-version:mime-version:content-type:content-type; bh=qk5d36k+IR3sDp3NaSAQ5M7FuWwkXnYN13289jk55Ac=; b=UXVnntFDJIejKgdp6BD1A2P2NmG4p7gEtFkXdmlBBZX5SrSx+AwIJSo+I6HJvF1/zjqSoH QY8DfsVvyHBKZrCA== Received: from imap2.suse-dmz.suse.de (imap2.suse-dmz.suse.de [192.168.254.74]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (P-521) server-digest SHA512) (No client certificate requested) by imap2.suse-dmz.suse.de (Postfix) with ESMTPS id B6889132C4 for ; Wed, 4 May 2022 08:59:13 +0000 (UTC) Received: from dovecot-director2.suse.de ([192.168.254.65]) by imap2.suse-dmz.suse.de with ESMTPSA id UZVmK2FAcmI3egAAMHmgww (envelope-from ) for ; Wed, 04 May 2022 08:59:13 +0000 Message-ID: Date: Wed, 4 May 2022 10:59:13 +0200 MIME-Version: 1.0 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:91.0) Gecko/20100101 Thunderbird/91.8.1 Content-Language: en-US To: GCC Patches From: =?utf-8?q?Martin_Li=C5=A1ka?= Subject: libsanitizer: merge from upstream X-Spam-Status: No, score=-11.8 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, SPF_HELO_NONE, SPF_PASS, TXREP, T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.4 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: gcc-patches-bounces+patchwork=sourceware.org@gcc.gnu.org Sender: "Gcc-patches" Hello. I'm going to do merge from upstream. Patch can bootstrap on x86_64-linux-gnu and survives regression tests. I've also tested on ppc64le-linux-gnu and verified the ABI. The only real change is a small change in gcc/testsuite/c-c++-common/asan/alloca_loop_unpoisoning.c where we need --param=asan-use-after-return=0. I'm going to push the patches. Thanks, Martin From 1c0069ab7ad0d76072adf3dc006b515a670a3ccb Mon Sep 17 00:00:00 2001 From: "H.J. Lu" Date: Tue, 20 Jul 2021 10:46:51 -0700 Subject: [PATCH 2/4] libsanitizer: Apply local patches --- libsanitizer/asan/asan_globals.cpp | 19 ------------------ libsanitizer/asan/asan_interceptors.h | 7 ++++++- libsanitizer/asan/asan_mapping.h | 2 +- .../sanitizer_linux_libcdep.cpp | 4 ++++ .../sanitizer_common/sanitizer_mac.cpp | 12 +++++++++-- libsanitizer/sanitizer_common/sanitizer_mac.h | 20 +++++++++++++++++++ .../sanitizer_platform_limits_linux.cpp | 5 ++++- .../sanitizer_platform_limits_posix.h | 2 +- .../sanitizer_common/sanitizer_stacktrace.cpp | 17 +++++++++++----- libsanitizer/tsan/tsan_rtl_ppc64.S | 1 + libsanitizer/ubsan/ubsan_flags.cpp | 1 + libsanitizer/ubsan/ubsan_handlers.cpp | 15 ++++++++++++++ libsanitizer/ubsan/ubsan_handlers.h | 8 ++++++++ libsanitizer/ubsan/ubsan_platform.h | 2 ++ 14 files changed, 85 insertions(+), 30 deletions(-) diff --git a/libsanitizer/asan/asan_globals.cpp b/libsanitizer/asan/asan_globals.cpp index ecc2600f039..326a49798f0 100644 --- a/libsanitizer/asan/asan_globals.cpp +++ b/libsanitizer/asan/asan_globals.cpp @@ -153,23 +153,6 @@ static void CheckODRViolationViaIndicator(const Global *g) { } } -// Check ODR violation for given global G by checking if it's already poisoned. -// We use this method in case compiler doesn't use private aliases for global -// variables. -static void CheckODRViolationViaPoisoning(const Global *g) { - if (__asan_region_is_poisoned(g->beg, g->size_with_redzone)) { - // This check may not be enough: if the first global is much larger - // the entire redzone of the second global may be within the first global. - for (ListOfGlobals *l = list_of_all_globals; l; l = l->next) { - if (g->beg == l->g->beg && - (flags()->detect_odr_violation >= 2 || g->size != l->g->size) && - !IsODRViolationSuppressed(g->name)) - ReportODRViolation(g, FindRegistrationSite(g), - l->g, FindRegistrationSite(l->g)); - } - } -} - // Clang provides two different ways for global variables protection: // it can poison the global itself or its private alias. In former // case we may poison same symbol multiple times, that can help us to @@ -215,8 +198,6 @@ static void RegisterGlobal(const Global *g) { // where two globals with the same name are defined in different modules. if (UseODRIndicator(g)) CheckODRViolationViaIndicator(g); - else - CheckODRViolationViaPoisoning(g); } if (CanPoisonMemory()) PoisonRedZones(*g); diff --git a/libsanitizer/asan/asan_interceptors.h b/libsanitizer/asan/asan_interceptors.h index 047b044c8bf..105c672cc24 100644 --- a/libsanitizer/asan/asan_interceptors.h +++ b/libsanitizer/asan/asan_interceptors.h @@ -81,7 +81,12 @@ void InitializePlatformInterceptors(); #if ASAN_HAS_EXCEPTIONS && !SANITIZER_WINDOWS && !SANITIZER_SOLARIS && \ !SANITIZER_NETBSD # define ASAN_INTERCEPT___CXA_THROW 1 -# define ASAN_INTERCEPT___CXA_RETHROW_PRIMARY_EXCEPTION 1 +# if ! defined(ASAN_HAS_CXA_RETHROW_PRIMARY_EXCEPTION) \ + || ASAN_HAS_CXA_RETHROW_PRIMARY_EXCEPTION +# define ASAN_INTERCEPT___CXA_RETHROW_PRIMARY_EXCEPTION 1 +# else +# define ASAN_INTERCEPT___CXA_RETHROW_PRIMARY_EXCEPTION 0 +# endif # if defined(_GLIBCXX_SJLJ_EXCEPTIONS) || (SANITIZER_IOS && defined(__arm__)) # define ASAN_INTERCEPT__UNWIND_SJLJ_RAISEEXCEPTION 1 # else diff --git a/libsanitizer/asan/asan_mapping.h b/libsanitizer/asan/asan_mapping.h index 4ff09b103d5..1b6669e1270 100644 --- a/libsanitizer/asan/asan_mapping.h +++ b/libsanitizer/asan/asan_mapping.h @@ -181,7 +181,7 @@ # elif defined(__aarch64__) # define ASAN_SHADOW_OFFSET_CONST 0x0000001000000000 # elif defined(__powerpc64__) -# define ASAN_SHADOW_OFFSET_CONST 0x0000100000000000 +# define ASAN_SHADOW_OFFSET_CONST 0x0000020000000000 # elif defined(__s390x__) # define ASAN_SHADOW_OFFSET_CONST 0x0010000000000000 # elif SANITIZER_FREEBSD diff --git a/libsanitizer/sanitizer_common/sanitizer_linux_libcdep.cpp b/libsanitizer/sanitizer_common/sanitizer_linux_libcdep.cpp index 25ad825f568..d966d857a76 100644 --- a/libsanitizer/sanitizer_common/sanitizer_linux_libcdep.cpp +++ b/libsanitizer/sanitizer_common/sanitizer_linux_libcdep.cpp @@ -792,9 +792,13 @@ u32 GetNumberOfCPUs() { #elif SANITIZER_SOLARIS return sysconf(_SC_NPROCESSORS_ONLN); #else +#if defined(CPU_COUNT) cpu_set_t CPUs; CHECK_EQ(sched_getaffinity(0, sizeof(cpu_set_t), &CPUs), 0); return CPU_COUNT(&CPUs); +#else + return 1; +#endif #endif } diff --git a/libsanitizer/sanitizer_common/sanitizer_mac.cpp b/libsanitizer/sanitizer_common/sanitizer_mac.cpp index 05512a576ad..7ce8d670ecc 100644 --- a/libsanitizer/sanitizer_common/sanitizer_mac.cpp +++ b/libsanitizer/sanitizer_common/sanitizer_mac.cpp @@ -38,7 +38,7 @@ extern char **environ; #endif -#if defined(__has_include) && __has_include() +#if defined(__has_include) && __has_include() && defined(__BLOCKS__) #define SANITIZER_OS_TRACE 1 #include #else @@ -71,7 +71,15 @@ extern "C" { #include #include #include -#include +#if defined(__has_builtin) && __has_builtin(__builtin_os_log_format) +# include +#else + /* Without support for __builtin_os_log_format, fall back to the older + method. */ +# define OS_LOG_DEFAULT 0 +# define os_log_error(A,B,C) \ + asl_log(nullptr, nullptr, ASL_LEVEL_ERR, "%s", (C)); +#endif #include #include #include diff --git a/libsanitizer/sanitizer_common/sanitizer_mac.h b/libsanitizer/sanitizer_common/sanitizer_mac.h index 0b6af5a3c0e..96a5986a47a 100644 --- a/libsanitizer/sanitizer_common/sanitizer_mac.h +++ b/libsanitizer/sanitizer_common/sanitizer_mac.h @@ -14,6 +14,26 @@ #include "sanitizer_common.h" #include "sanitizer_platform.h" + +/* TARGET_OS_OSX is not present in SDKs before Darwin16 (macOS 10.12) use + TARGET_OS_MAC (we have no support for iOS in any form for these versions, + so there's no ambiguity). */ +#if !defined(TARGET_OS_OSX) && TARGET_OS_MAC +# define TARGET_OS_OSX 1 +#endif + +/* Other TARGET_OS_xxx are not present on earlier versions, define them to + 0 (we have no support for them; they are not valid targets anyway). */ +#ifndef TARGET_OS_IOS +#define TARGET_OS_IOS 0 +#endif +#ifndef TARGET_OS_TV +#define TARGET_OS_TV 0 +#endif +#ifndef TARGET_OS_WATCH +#define TARGET_OS_WATCH 0 +#endif + #if SANITIZER_MAC #include "sanitizer_posix.h" diff --git a/libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cpp b/libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cpp index 9d577570ea1..2b1a2f7932c 100644 --- a/libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cpp +++ b/libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cpp @@ -26,7 +26,10 @@ // With old kernels (and even new kernels on powerpc) asm/stat.h uses types that // are not defined anywhere in userspace headers. Fake them. This seems to work -// fine with newer headers, too. +// fine with newer headers, too. Beware that with , struct stat +// takes the form of struct stat64 on 32-bit platforms if _FILE_OFFSET_BITS=64. +// Also, for some platforms (e.g. mips) there are additional members in the +// struct stat:s. #include # if defined(__x86_64__) || defined(__mips__) || defined(__hexagon__) # include diff --git a/libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h b/libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h index 62a99035db3..89772a7e5c0 100644 --- a/libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h +++ b/libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h @@ -83,7 +83,7 @@ const unsigned struct_kernel_stat64_sz = 104; #elif defined(__mips__) const unsigned struct_kernel_stat_sz = SANITIZER_ANDROID ? FIRST_32_SECOND_64(104, 128) - : FIRST_32_SECOND_64(160, 216); + : FIRST_32_SECOND_64(144, 216); const unsigned struct_kernel_stat64_sz = 104; #elif defined(__s390__) && !defined(__s390x__) const unsigned struct_kernel_stat_sz = 64; diff --git a/libsanitizer/sanitizer_common/sanitizer_stacktrace.cpp b/libsanitizer/sanitizer_common/sanitizer_stacktrace.cpp index 3013a0c4abd..7386285f34b 100644 --- a/libsanitizer/sanitizer_common/sanitizer_stacktrace.cpp +++ b/libsanitizer/sanitizer_common/sanitizer_stacktrace.cpp @@ -87,8 +87,8 @@ static inline uhwptr *GetCanonicFrame(uptr bp, // Nope, this does not look right either. This means the frame after next does // not have a valid frame pointer, but we can still extract the caller PC. // Unfortunately, there is no way to decide between GCC and LLVM frame - // layouts. Assume LLVM. - return bp_prev; + // layouts. Assume GCC. + return bp_prev - 1; #else return (uhwptr*)bp; #endif @@ -111,14 +111,21 @@ void BufferedStackTrace::UnwindFast(uptr pc, uptr bp, uptr stack_top, IsAligned((uptr)frame, sizeof(*frame)) && size < max_depth) { #ifdef __powerpc__ - // PowerPC ABIs specify that the return address is saved at offset - // 16 of the *caller's* stack frame. Thus we must dereference the - // back chain to find the caller frame before extracting it. + // PowerPC ABIs specify that the return address is saved on the + // *caller's* stack frame. Thus we must dereference the back chain + // to find the caller frame before extracting it. uhwptr *caller_frame = (uhwptr*)frame[0]; if (!IsValidFrame((uptr)caller_frame, stack_top, bottom) || !IsAligned((uptr)caller_frame, sizeof(uhwptr))) break; + // For most ABIs the offset where the return address is saved is two + // register sizes. The exception is the SVR4 ABI, which uses an + // offset of only one register size. +#ifdef _CALL_SYSV + uhwptr pc1 = caller_frame[1]; +#else uhwptr pc1 = caller_frame[2]; +#endif #elif defined(__s390__) uhwptr pc1 = frame[14]; #elif defined(__riscv) diff --git a/libsanitizer/tsan/tsan_rtl_ppc64.S b/libsanitizer/tsan/tsan_rtl_ppc64.S index 8285e21aa1e..9e533a71a9c 100644 --- a/libsanitizer/tsan/tsan_rtl_ppc64.S +++ b/libsanitizer/tsan/tsan_rtl_ppc64.S @@ -1,5 +1,6 @@ #include "tsan_ppc_regs.h" + .machine altivec .section .text .hidden __tsan_setjmp .globl _setjmp diff --git a/libsanitizer/ubsan/ubsan_flags.cpp b/libsanitizer/ubsan/ubsan_flags.cpp index 25cefd46ce2..9a66bd37518 100644 --- a/libsanitizer/ubsan/ubsan_flags.cpp +++ b/libsanitizer/ubsan/ubsan_flags.cpp @@ -50,6 +50,7 @@ void InitializeFlags() { { CommonFlags cf; cf.CopyFrom(*common_flags()); + cf.print_summary = false; cf.external_symbolizer_path = GetFlag("UBSAN_SYMBOLIZER_PATH"); OverrideCommonFlags(cf); } diff --git a/libsanitizer/ubsan/ubsan_handlers.cpp b/libsanitizer/ubsan/ubsan_handlers.cpp index e201e6bba22..2184625aa6e 100644 --- a/libsanitizer/ubsan/ubsan_handlers.cpp +++ b/libsanitizer/ubsan/ubsan_handlers.cpp @@ -894,6 +894,21 @@ void __ubsan_handle_cfi_bad_type(CFICheckFailData *Data, ValueHandle Vtable, } // namespace __ubsan +void __ubsan::__ubsan_handle_cfi_bad_icall(CFIBadIcallData *CallData, + ValueHandle Function) { + GET_REPORT_OPTIONS(false); + CFICheckFailData Data = {CFITCK_ICall, CallData->Loc, CallData->Type}; + handleCFIBadIcall(&Data, Function, Opts); +} + +void __ubsan::__ubsan_handle_cfi_bad_icall_abort(CFIBadIcallData *CallData, + ValueHandle Function) { + GET_REPORT_OPTIONS(true); + CFICheckFailData Data = {CFITCK_ICall, CallData->Loc, CallData->Type}; + handleCFIBadIcall(&Data, Function, Opts); + Die(); +} + void __ubsan::__ubsan_handle_cfi_check_fail(CFICheckFailData *Data, ValueHandle Value, uptr ValidVtable) { diff --git a/libsanitizer/ubsan/ubsan_handlers.h b/libsanitizer/ubsan/ubsan_handlers.h index 219fb15de55..9f412353fc0 100644 --- a/libsanitizer/ubsan/ubsan_handlers.h +++ b/libsanitizer/ubsan/ubsan_handlers.h @@ -215,12 +215,20 @@ enum CFITypeCheckKind : unsigned char { CFITCK_VMFCall, }; +struct CFIBadIcallData { + SourceLocation Loc; + const TypeDescriptor &Type; +}; + struct CFICheckFailData { CFITypeCheckKind CheckKind; SourceLocation Loc; const TypeDescriptor &Type; }; +/// \brief Handle control flow integrity failure for indirect function calls. +RECOVERABLE(cfi_bad_icall, CFIBadIcallData *Data, ValueHandle Function) + /// \brief Handle control flow integrity failures. RECOVERABLE(cfi_check_fail, CFICheckFailData *Data, ValueHandle Function, uptr VtableIsValid) diff --git a/libsanitizer/ubsan/ubsan_platform.h b/libsanitizer/ubsan/ubsan_platform.h index d2cc2e10bd2..ad3e883f0f3 100644 --- a/libsanitizer/ubsan/ubsan_platform.h +++ b/libsanitizer/ubsan/ubsan_platform.h @@ -12,6 +12,7 @@ #ifndef UBSAN_PLATFORM_H #define UBSAN_PLATFORM_H +#ifndef CAN_SANITIZE_UB // Other platforms should be easy to add, and probably work as-is. #if defined(__linux__) || defined(__FreeBSD__) || defined(__APPLE__) || \ defined(__NetBSD__) || defined(__DragonFly__) || \ @@ -21,5 +22,6 @@ #else # define CAN_SANITIZE_UB 0 #endif +#endif //CAN_SANITIZE_UB #endif -- 2.36.0