On Thu, Oct 19, 2017 at 02:07:24PM +0300, Maxim Ostapenko wrote:
> > Is the patch (the merge + this incremental) ok for trunk?
> 
> I think the patch is OK, just wondering about two things:

Richi just approved the patch on IRC, so I'll commit, then we can deal with
follow-ups.

> 1) We have a bunch of GCC local patches, did you include them into a
> cumulative patch (I guess yes)?

I have done some verification today, diff from upstream r285547 to unpatched
GCC (with the LLVM Compiler infrastructure two liners removed), attached P1,
and diff from upstream r315899 to patched GCC (again, two liners removed),
attached P2 and went through the changes in P1 and verified that except for
the ubsan backwards compatibility we had that can't work anymore everything
else was upstreamed, or remained in P2.  So P2 is the current diff from
upstream, with the sanitizer_common/sanitizer_symbolizer_libbacktrace.cc
changes now filed upstream.

> 2) Upstream has enabled LSan for x86 and ARM, is it worth to enable them in
> GCC too?

Maybe, feel free to post patches.  For LSan we need to split off lsan_preinit
out of liblsan and link it into executables, will handle it next (there is a
PR about it, just wanted to wait until the merge is in).

        Jakub
--- /usr/src/llvm/projects/compiler-rt.285547/lib/asan/asan_globals.cc  
2017-10-19 10:29:52.916249242 +0200
+++ asan/asan_globals.cc        2017-10-19 09:17:31.163837518 +0200
@@ -149,23 +147,6 @@ static void CheckODRViolationViaIndicato
   }
 }
 
-// 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
@@ -213,8 +194,6 @@ static void RegisterGlobal(const Global
     // where two globals with the same name are defined in different modules.
     if (UseODRIndicator(g))
       CheckODRViolationViaIndicator(g);
-    else
-      CheckODRViolationViaPoisoning(g);
   }
   if (CanPoisonMemory())
     PoisonRedZones(*g);
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_common_interceptors.inc
    2017-10-19 10:29:53.330243835 +0200
+++ sanitizer_common/sanitizer_common_interceptors.inc  2017-10-19 
09:17:31.139837810 +0200
@@ -3352,7 +3350,8 @@ INTERCEPTOR(int, getgroups, int size, u3
   // its metadata. See
   // https://github.com/google/sanitizers/issues/321.
   int res = REAL(getgroups)(size, lst);
-  if (res && lst) COMMON_INTERCEPTOR_WRITE_RANGE(ctx, lst, res * sizeof(*lst));
+  if (res >= 0 && lst && size > 0)
+    COMMON_INTERCEPTOR_WRITE_RANGE(ctx, lst, res * sizeof(*lst));
   return res;
 }
 #define INIT_GETGROUPS COMMON_INTERCEPT_FUNCTION(getgroups);
@@ -4552,11 +4551,15 @@ void *__tls_get_addr_opt(void *arg);
 //   descriptor offset as an argument instead of a pointer.  GOT address
 //   is passed in r12, so it's necessary to write it in assembly.  This is
 //   the function used by the compiler.
-#define INIT_TLS_GET_ADDR COMMON_INTERCEPT_FUNCTION(__tls_get_addr_internal)
+extern "C" uptr __tls_get_offset_wrapper(void *arg, uptr (*fn)(void *arg));
+#define INIT_TLS_GET_ADDR COMMON_INTERCEPT_FUNCTION(__tls_get_offset)
+DEFINE_REAL(uptr, __tls_get_offset, void *arg)
+extern "C" uptr __tls_get_offset(void *arg);
+extern "C" uptr __interceptor___tls_get_offset(void *arg);
 INTERCEPTOR(uptr, __tls_get_addr_internal, void *arg) {
   void *ctx;
   COMMON_INTERCEPTOR_ENTER(ctx, __tls_get_addr_internal, arg);
-  uptr res = REAL(__tls_get_addr_internal)(arg);
+  uptr res = __tls_get_offset_wrapper(arg, REAL(__tls_get_offset));
   uptr tp = reinterpret_cast<uptr>(__builtin_thread_pointer());
   void *ptr = reinterpret_cast<void *>(res + tp);
   uptr tls_begin, tls_end;
@@ -4568,32 +4571,43 @@ INTERCEPTOR(uptr, __tls_get_addr_interna
   }
   return res;
 }
-// We need a protected symbol aliasing the above, so that we can jump
+// We need a hidden symbol aliasing the above, so that we can jump
 // directly to it from the assembly below.
 extern "C" __attribute__((alias("__interceptor___tls_get_addr_internal"),
-                          visibility("protected")))
-uptr __interceptor___tls_get_addr_internal_protected(void *arg);
+                          visibility("hidden")))
+uptr __tls_get_addr_hidden(void *arg);
 // Now carefully intercept __tls_get_offset.
 asm(
   ".text\n"
-  ".global __tls_get_offset\n"
-  "__tls_get_offset:\n"
 // The __intercept_ version has to exist, so that gen_dynamic_list.py
 // exports our symbol.
+  ".weak __tls_get_offset\n"
+  ".type __tls_get_offset, @function\n"
+  "__tls_get_offset:\n"
   ".global __interceptor___tls_get_offset\n"
+  ".type __interceptor___tls_get_offset, @function\n"
   "__interceptor___tls_get_offset:\n"
 #ifdef __s390x__
   "la %r2, 0(%r2,%r12)\n"
-  "jg __interceptor___tls_get_addr_internal_protected\n"
+  "jg __tls_get_addr_hidden\n"
 #else
   "basr %r3,0\n"
   "0: la %r2,0(%r2,%r12)\n"
   "l %r4,1f-0b(%r3)\n"
   "b 0(%r4,%r3)\n"
-  "1: .long __interceptor___tls_get_addr_internal_protected - 0b\n"
+  "1: .long __tls_get_addr_hidden - 0b\n"
 #endif
-  ".type __tls_get_offset, @function\n"
-  ".size __tls_get_offset, .-__tls_get_offset\n"
+  ".size __interceptor___tls_get_offset, .-__interceptor___tls_get_offset\n"
+// Assembly wrapper to call REAL(__tls_get_offset)(arg)
+  ".type __tls_get_offset_wrapper, @function\n"
+  "__tls_get_offset_wrapper:\n"
+#ifdef __s390x__
+  "sgr %r2,%r12\n"
+#else
+  "sr %r2,%r12\n"
+#endif
+  "br %r3\n"
+  ".size __tls_get_offset_wrapper, .-__tls_get_offset_wrapper\n"
 );
 #endif // SANITIZER_S390
 #else
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_internal_defs.h
    2017-10-19 10:29:52.818250522 +0200
+++ sanitizer_common/sanitizer_internal_defs.h  2017-10-19 09:17:31.154837627 
+0200
@@ -289,7 +287,12 @@ void NORETURN CheckFailed(const char *fi
 enum LinkerInitialized { LINKER_INITIALIZED = 0 };
 
 #if !defined(_MSC_VER) || defined(__clang__)
-# define GET_CALLER_PC() (uptr)__builtin_return_address(0)
+# if SANITIZER_S390_31
+#  define GET_CALLER_PC() \
+  (uptr)__builtin_extract_return_addr(__builtin_return_address(0))
+# else
+#  define GET_CALLER_PC() (uptr)__builtin_return_address(0)
+# endif
 # define GET_CURRENT_FRAME() (uptr)__builtin_frame_address(0)
 inline void Trap() {
   __builtin_trap();
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_linux.cc
   2017-10-19 10:29:53.305244161 +0200
+++ sanitizer_common/sanitizer_linux.cc 2017-10-19 09:17:31.151837664 +0200
@@ -607,8 +605,7 @@ uptr internal_prctl(int option, uptr arg
 }
 #endif
 
-uptr internal_sigaltstack(const struct sigaltstack *ss,
-                         struct sigaltstack *oss) {
+uptr internal_sigaltstack(const void *ss, void *oss) {
   return internal_syscall(SYSCALL(sigaltstack), (uptr)ss, (uptr)oss);
 }
 
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_linux.h
    2017-10-19 10:29:52.816250548 +0200
+++ sanitizer_common/sanitizer_linux.h  2017-10-19 09:17:31.152837652 +0200
@@ -21,7 +19,6 @@
 #include "sanitizer_platform_limits_posix.h"
 
 struct link_map;  // Opaque type returned by dlopen().
-struct sigaltstack;
 
 namespace __sanitizer {
 // Dirent structure for getdents(). Note that this structure is different from
@@ -30,8 +27,7 @@ struct linux_dirent;
 
 // Syscall wrappers.
 uptr internal_getdents(fd_t fd, struct linux_dirent *dirp, unsigned int count);
-uptr internal_sigaltstack(const struct sigaltstack* ss,
-                          struct sigaltstack* oss);
+uptr internal_sigaltstack(const void* ss, void* oss);
 uptr internal_sigprocmask(int how, __sanitizer_sigset_t *set,
     __sanitizer_sigset_t *oldset);
 
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_linux_s390.cc
      2017-10-19 10:29:52.566253813 +0200
+++ sanitizer_common/sanitizer_linux_s390.cc    2017-10-19 09:17:31.139837810 
+0200
@@ -136,6 +134,18 @@ static bool FixedCVE_2016_2143() {
   if (ptr[0] == '.')
     patch = internal_simple_strtoll(ptr+1, &ptr, 10);
   if (major < 3) {
+    if (major == 2 && minor == 6 && patch == 32 && ptr[0] == '-' &&
+        internal_strstr(ptr, ".el6")) {
+      // Check RHEL6
+      int r1 = internal_simple_strtoll(ptr+1, &ptr, 10);
+      if (r1 >= 657) // 2.6.32-657.el6 or later
+        return true;
+      if (r1 == 642 && ptr[0] == '.') {
+        int r2 = internal_simple_strtoll(ptr+1, &ptr, 10);
+        if (r2 >= 9) // 2.6.32-642.9.1.el6 or later
+          return true;
+      }
+    }
     // <3.0 is bad.
     return false;
   } else if (major == 3) {
@@ -145,6 +155,18 @@ static bool FixedCVE_2016_2143() {
     // 3.12.58+ is OK.
     if (minor == 12 && patch >= 58)
       return true;
+    if (minor == 10 && patch == 0 && ptr[0] == '-' &&
+        internal_strstr(ptr, ".el7")) {
+      // Check RHEL7
+      int r1 = internal_simple_strtoll(ptr+1, &ptr, 10);
+      if (r1 >= 426) // 3.10.0-426.el7 or later
+        return true;
+      if (r1 == 327 && ptr[0] == '.') {
+        int r2 = internal_simple_strtoll(ptr+1, &ptr, 10);
+        if (r2 >= 27) // 3.10.0-327.27.1.el7 or later
+          return true;
+      }
+    }
     // Otherwise, bad.
     return false;
   } else if (major == 4) {
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_mac.cc 
    2017-10-19 10:29:53.306244148 +0200
+++ sanitizer_common/sanitizer_mac.cc   2017-10-19 09:17:31.143837761 +0200
@@ -36,7 +34,7 @@
 extern char **environ;
 #endif
 
-#if defined(__has_include) && __has_include(<os/trace.h>)
+#if defined(__has_include) && __has_include(<os/trace.h>) && 
defined(__BLOCKS__)
 #define SANITIZER_OS_TRACE 1
 #include <os/trace.h>
 #else
@@ -93,20 +91,22 @@ namespace __sanitizer {
 
 #include "sanitizer_syscall_generic.inc"
 
-// Direct syscalls, don't call libmalloc hooks.
+// Direct syscalls, don't call libmalloc hooks (but not available on 10.6).
 extern "C" void *__mmap(void *addr, size_t len, int prot, int flags, int 
fildes,
-                        off_t off);
-extern "C" int __munmap(void *, size_t);
+                        off_t off) SANITIZER_WEAK_ATTRIBUTE;
+extern "C" int __munmap(void *, size_t) SANITIZER_WEAK_ATTRIBUTE;
 
 // ---------------------- sanitizer_libc.h
 uptr internal_mmap(void *addr, size_t length, int prot, int flags,
                    int fd, u64 offset) {
   if (fd == -1) fd = VM_MAKE_TAG(VM_MEMORY_ANALYSIS_TOOL);
-  return (uptr)__mmap(addr, length, prot, flags, fd, offset);
+  if (__mmap) return (uptr)__mmap(addr, length, prot, flags, fd, offset);
+  return (uptr)mmap(addr, length, prot, flags, fd, offset);
 }
 
 uptr internal_munmap(void *addr, uptr length) {
-  return __munmap(addr, length);
+  if (__munmap) return __munmap(addr, length);
+  return munmap(addr, length);
 }
 
 int internal_mprotect(void *addr, uptr length, int prot) {
@@ -192,17 +192,19 @@ uptr internal_sigprocmask(int how, __san
   return sigprocmask(how, set, oldset);
 }
 
-// Doesn't call pthread_atfork() handlers.
-extern "C" pid_t __fork(void);
+// Doesn't call pthread_atfork() handlers (but not available on 10.6).
+extern "C" pid_t __fork(void) SANITIZER_WEAK_ATTRIBUTE;
 
 int internal_fork() {
-  return __fork();
+  if (__fork)
+    return __fork();
+  return fork();
 }
 
 int internal_forkpty(int *amaster) {
   int master, slave;
   if (openpty(&master, &slave, nullptr, nullptr, nullptr) == -1) return -1;
-  int pid = __fork();
+  int pid = internal_fork();
   if (pid == -1) {
     close(master);
     close(slave);
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_platform_interceptors.h
    2017-10-19 10:29:52.826250417 +0200
+++ sanitizer_common/sanitizer_platform_interceptors.h  2017-10-19 
09:17:31.141837786 +0200
@@ -83,8 +81,16 @@
 #define SANITIZER_INTERCEPT_MEMMOVE 1
 #define SANITIZER_INTERCEPT_MEMCPY 1
 #define SANITIZER_INTERCEPT_MEMCMP 1
+#if defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && \
+    __ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ < 1070
+# define SI_MAC_DEPLOYMENT_BELOW_10_7 1
+#else
+# define SI_MAC_DEPLOYMENT_BELOW_10_7 0
+#endif
+// memmem on Darwin doesn't exist on 10.6
 // FIXME: enable memmem on Windows.
-#define SANITIZER_INTERCEPT_MEMMEM SI_NOT_WINDOWS
+#define SANITIZER_INTERCEPT_MEMMEM \
+  SI_NOT_WINDOWS && !SI_MAC_DEPLOYMENT_BELOW_10_7
 #define SANITIZER_INTERCEPT_MEMCHR 1
 #define SANITIZER_INTERCEPT_MEMRCHR SI_FREEBSD || SI_LINUX
 
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_platform_limits_linux.cc
   2017-10-19 10:29:52.573253722 +0200
+++ sanitizer_common/sanitizer_platform_limits_linux.cc 2017-10-16 
13:26:27.582029950 +0200
@@ -38,6 +36,7 @@
 #define uid_t __kernel_uid_t
 #define gid_t __kernel_gid_t
 #define off_t __kernel_off_t
+#define time_t __kernel_time_t
 // This header seems to contain the definitions of _kernel_ stat* structs.
 #include <asm/stat.h>
 #undef ino_t
@@ -64,7 +63,8 @@ namespace __sanitizer {
 }  // namespace __sanitizer
 
 #if !defined(__powerpc64__) && !defined(__x86_64__) && !defined(__aarch64__)\
-                            && !defined(__mips__) && !defined(__s390__)
+                            && !defined(__mips__) && !defined(__s390__)\
+                            && !defined(__sparc__)
 COMPILER_CHECK(struct___old_kernel_stat_sz == sizeof(struct 
__old_kernel_stat));
 #endif
 
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_platform_limits_posix.cc
   2017-10-19 10:29:52.821250483 +0200
+++ sanitizer_common/sanitizer_platform_limits_posix.cc 2017-10-19 
09:17:31.141837786 +0200
@@ -23,11 +21,6 @@
 #ifdef _FILE_OFFSET_BITS
 #undef _FILE_OFFSET_BITS
 #endif
-#if SANITIZER_FREEBSD
-#define _WANT_RTENTRY
-#include <sys/param.h>
-#include <sys/socketvar.h>
-#endif
 #include <arpa/inet.h>
 #include <dirent.h>
 #include <errno.h>
@@ -422,6 +415,7 @@ unsigned struct_ElfW_Phdr_sz = sizeof(El
   unsigned struct_input_absinfo_sz = sizeof(struct input_absinfo);
   unsigned struct_input_id_sz = sizeof(struct input_id);
   unsigned struct_mtpos_sz = sizeof(struct mtpos);
+  unsigned struct_rtentry_sz = sizeof(struct rtentry);
   unsigned struct_termio_sz = sizeof(struct termio);
   unsigned struct_vt_consize_sz = sizeof(struct vt_consize);
   unsigned struct_vt_sizes_sz = sizeof(struct vt_sizes);
@@ -441,7 +435,6 @@ unsigned struct_ElfW_Phdr_sz = sizeof(El
   unsigned struct_midi_info_sz = sizeof(struct midi_info);
   unsigned struct_mtget_sz = sizeof(struct mtget);
   unsigned struct_mtop_sz = sizeof(struct mtop);
-  unsigned struct_rtentry_sz = sizeof(struct rtentry);
   unsigned struct_sbi_instrument_sz = sizeof(struct sbi_instrument);
   unsigned struct_seq_event_rec_sz = sizeof(struct seq_event_rec);
   unsigned struct_synth_info_sz = sizeof(struct synth_info);
diff -upr 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_platform_limits_posix.h
 sanitizer_common/sanitizer_platform_limits_posix.h
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_platform_limits_posix.h
    2017-10-19 10:29:52.827250404 +0200
+++ sanitizer_common/sanitizer_platform_limits_posix.h  2017-10-19 
09:17:31.142837773 +0200
@@ -27,6 +25,10 @@
 # define GET_LINK_MAP_BY_DLOPEN_HANDLE(handle) ((link_map*)(handle))
 #endif  // !SANITIZER_FREEBSD
 
+#ifndef __GLIBC_PREREQ
+#define __GLIBC_PREREQ(x, y) 0
+#endif
+
 namespace __sanitizer {
   extern unsigned struct_utsname_sz;
   extern unsigned struct_stat_sz;
@@ -87,6 +89,14 @@ namespace __sanitizer {
 #elif defined(__s390x__)
   const unsigned struct_kernel_stat_sz = 144;
   const unsigned struct_kernel_stat64_sz = 0;
+#elif defined(__sparc__) && defined(__arch64__)
+  const unsigned struct___old_kernel_stat_sz = 0;
+  const unsigned struct_kernel_stat_sz = 104;
+  const unsigned struct_kernel_stat64_sz = 144;
+#elif defined(__sparc__) && !defined(__arch64__)
+  const unsigned struct___old_kernel_stat_sz = 0;
+  const unsigned struct_kernel_stat_sz = 64;
+  const unsigned struct_kernel_stat64_sz = 104;
 #endif
   struct __sanitizer_perf_event_attr {
     unsigned type;
@@ -109,7 +119,7 @@ namespace __sanitizer {
 
 #if defined(__powerpc64__) || defined(__s390__)
   const unsigned struct___old_kernel_stat_sz = 0;
-#else
+#elif !defined(__sparc__)
   const unsigned struct___old_kernel_stat_sz = 32;
 #endif
 
@@ -200,6 +210,18 @@ namespace __sanitizer {
     unsigned short __pad1;
     unsigned long __unused1;
     unsigned long __unused2;
+#elif defined(__sparc__)
+# if defined(__arch64__)
+    unsigned mode;
+    unsigned short __pad1;
+# else
+    unsigned short __pad1;
+    unsigned short mode;
+    unsigned short __pad2;
+# endif
+    unsigned short __seq;
+    unsigned long long __unused1;
+    unsigned long long __unused2;
 #else
     unsigned short mode;
     unsigned short __pad1;
@@ -217,6 +239,26 @@ namespace __sanitizer {
 
   struct __sanitizer_shmid_ds {
     __sanitizer_ipc_perm shm_perm;
+  #if defined(__sparc__)
+  # if !defined(__arch64__)
+    u32 __pad1;
+  # endif
+    long shm_atime;
+  # if !defined(__arch64__)
+    u32 __pad2;
+  # endif
+    long shm_dtime;
+  # if !defined(__arch64__)
+    u32 __pad3;
+  # endif
+    long shm_ctime;
+    uptr shm_segsz;
+    int shm_cpid;
+    int shm_lpid;
+    unsigned long shm_nattch;
+    unsigned long __glibc_reserved1;
+    unsigned long __glibc_reserved2;
+  #else
   #ifndef __powerpc__
     uptr shm_segsz;
   #elif !defined(__powerpc64__)
@@ -254,6 +296,7 @@ namespace __sanitizer {
     uptr __unused4;
     uptr __unused5;
   #endif
+#endif
   };
 #elif SANITIZER_FREEBSD
   struct __sanitizer_ipc_perm {
@@ -588,7 +631,21 @@ namespace __sanitizer {
     __sanitizer_sigset_t sa_mask;
 #endif
 #ifndef __mips__
+#if defined(__sparc__)
+#if __GLIBC_PREREQ (2, 20)
+    // On sparc glibc 2.19 and earlier sa_flags was unsigned long.
+#if defined(__arch64__)
+    // To maintain ABI compatibility on sparc64 when switching to an int,
+    // __glibc_reserved0 was added.
+    int __glibc_reserved0;
+#endif
     int sa_flags;
+#else
+    unsigned long sa_flags;
+#endif
+#else
+    int sa_flags;
+#endif
 #endif
 #endif
 #if SANITIZER_LINUX
@@ -851,7 +908,7 @@ struct __sanitizer_cookie_io_functions_t
 
 #define IOC_NRBITS 8
 #define IOC_TYPEBITS 8
-#if defined(__powerpc__) || defined(__powerpc64__) || defined(__mips__)
+#if defined(__powerpc__) || defined(__powerpc64__) || defined(__mips__) || 
defined(__sparc__)
 #define IOC_SIZEBITS 13
 #define IOC_DIRBITS 3
 #define IOC_NONE 1U
@@ -881,7 +938,17 @@ struct __sanitizer_cookie_io_functions_t
 #define IOC_DIR(nr) (((nr) >> IOC_DIRSHIFT) & IOC_DIRMASK)
 #define IOC_TYPE(nr) (((nr) >> IOC_TYPESHIFT) & IOC_TYPEMASK)
 #define IOC_NR(nr) (((nr) >> IOC_NRSHIFT) & IOC_NRMASK)
+
+#if defined(__sparc__)
+// In sparc the 14 bits SIZE field overlaps with the
+// least significant bit of DIR, so either IOC_READ or
+// IOC_WRITE shall be 1 in order to get a non-zero SIZE.
+# define IOC_SIZE(nr)                       \
+  ((((((nr) >> 29) & 0x7) & (4U|2U)) == 0)? \
+   0 : (((nr) >> 16) & 0x3fff))
+#else
 #define IOC_SIZE(nr) (((nr) >> IOC_SIZESHIFT) & IOC_SIZEMASK)
+#endif
 
   extern unsigned struct_ifreq_sz;
   extern unsigned struct_termios_sz;
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_stacktrace.cc
      2017-10-19 10:29:52.833250326 +0200
+++ sanitizer_common/sanitizer_stacktrace.cc    2017-10-19 09:17:31.155837615 
+0200
@@ -57,8 +55,8 @@ static inline uhwptr *GetCanonicFrame(up
   // 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
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/sanitizer_common/sanitizer_stoptheworld_linux_libcdep.cc
      2017-10-19 10:29:52.835250300 +0200
+++ sanitizer_common/sanitizer_stoptheworld_linux_libcdep.cc    2017-10-19 
09:17:31.137837834 +0200
@@ -275,7 +273,7 @@ static int TracerThread(void* argument)
 
   // Alternate stack for signal handling.
   InternalScopedBuffer<char> handler_stack_memory(kHandlerStackSize);
-  struct sigaltstack handler_stack;
+  stack_t handler_stack;
   internal_memset(&handler_stack, 0, sizeof(handler_stack));
   handler_stack.ss_sp = handler_stack_memory.data();
   handler_stack.ss_size = kHandlerStackSize;
--- /usr/src/llvm/projects/compiler-rt.285547/lib/ubsan/ubsan_checks.inc        
2017-10-19 10:30:18.061920811 +0200
+++ ubsan/ubsan_checks.inc      2017-10-19 09:17:31.133837883 +0200
@@ -19,6 +17,7 @@
 
 UBSAN_CHECK(GenericUB, "undefined-behavior", "undefined")
 UBSAN_CHECK(NullPointerUse, "null-pointer-use", "null")
+UBSAN_CHECK(PointerOverflow, "pointer-overflow", "pointer-overflow")
 UBSAN_CHECK(MisalignedPointerUse, "misaligned-pointer-use", "alignment")
 UBSAN_CHECK(InsufficientObjectSize, "insufficient-object-size", "object-size")
 UBSAN_CHECK(SignedIntegerOverflow, "signed-integer-overflow",
--- /usr/src/llvm/projects/compiler-rt.285547/lib/ubsan/ubsan_handlers.cc       
2017-10-19 10:30:18.062920798 +0200
+++ ubsan/ubsan_handlers.cc     2017-10-19 09:17:31.134837871 +0200
@@ -523,6 +521,37 @@ void __ubsan::__ubsan_handle_nonnull_arg
   Die();
 }
 
+static void handlePointerOverflowImpl(PointerOverflowData *Data,
+                                      ValueHandle Base,
+                                      ValueHandle Result,
+                                      ReportOptions Opts) {
+  SourceLocation Loc = Data->Loc.acquire();
+  ErrorType ET = ErrorType::PointerOverflow;
+
+  if (ignoreReport(Loc, Opts, ET))
+    return;
+
+  ScopedReport R(Opts, Loc, ET);
+
+  Diag(Loc, DL_Error, "pointer index expression with base %0 overflowed to %1")
+    << (void *)Base << (void*)Result;
+}
+
+void __ubsan::__ubsan_handle_pointer_overflow(PointerOverflowData *Data,
+                                              ValueHandle Base,
+                                              ValueHandle Result) {
+  GET_REPORT_OPTIONS(false);
+  handlePointerOverflowImpl(Data, Base, Result, Opts);
+}
+
+void __ubsan::__ubsan_handle_pointer_overflow_abort(PointerOverflowData *Data,
+                                                    ValueHandle Base,
+                                                    ValueHandle Result) {
+  GET_REPORT_OPTIONS(true);
+  handlePointerOverflowImpl(Data, Base, Result, Opts);
+  Die();
+}
+
 static void handleCFIBadIcall(CFICheckFailData *Data, ValueHandle Function,
                               ReportOptions Opts) {
   if (Data->CheckKind != CFITCK_ICall)
@@ -560,6 +589,21 @@ static void HandleCFIBadType(CFICheckFai
 #endif
 }  // 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 -upr 
/usr/src/llvm/projects/compiler-rt.285547/lib/ubsan/ubsan_handlers_cxx.cc 
ubsan/ubsan_handlers_cxx.cc
--- /usr/src/llvm/projects/compiler-rt.285547/lib/ubsan/ubsan_handlers_cxx.cc   
2017-10-19 10:30:18.060920824 +0200
+++ ubsan/ubsan_handlers_cxx.cc 2017-10-19 09:17:31.132837895 +0200
@@ -144,4 +142,22 @@ void HandleCFIBadType(CFICheckFailData *
 }
 }  // namespace __ubsan
 
+void __ubsan::__ubsan_handle_cfi_bad_type(CFIBadTypeData *TypeData,
+                                          ValueHandle Vtable) {
+  GET_REPORT_OPTIONS(false);
+  CFITypeCheckKind TypeCheckKind
+    = static_cast<CFITypeCheckKind> (TypeData->TypeCheckKind);
+  CFICheckFailData Data = {TypeCheckKind, TypeData->Loc, TypeData->Type};
+  HandleCFIBadType(&Data, Vtable, false, Opts);
+}
+
+void __ubsan::__ubsan_handle_cfi_bad_type_abort(CFIBadTypeData *TypeData,
+                                                ValueHandle Vtable) {
+  GET_REPORT_OPTIONS(true);
+  CFITypeCheckKind TypeCheckKind
+    = static_cast<CFITypeCheckKind> (TypeData->TypeCheckKind);
+  CFICheckFailData Data = {TypeCheckKind, TypeData->Loc, TypeData->Type};
+  HandleCFIBadType(&Data, Vtable, false, Opts);
+}
+
 #endif // CAN_SANITIZE_UB
--- /usr/src/llvm/projects/compiler-rt.285547/lib/ubsan/ubsan_handlers_cxx.h    
2016-05-17 10:47:06.700073119 +0200
+++ ubsan/ubsan_handlers_cxx.h  2017-10-19 09:17:31.133837883 +0200
@@ -25,6 +23,12 @@ struct DynamicTypeCacheMissData {
   unsigned char TypeCheckKind;
 };
 
+struct CFIBadTypeData {
+  SourceLocation Loc;
+  const TypeDescriptor &Type;
+  unsigned char TypeCheckKind;
+};
+
 /// \brief Handle a runtime type check failure, caused by an incorrect vptr.
 /// When this handler is called, all we know is that the type was not in the
 /// cache; this does not necessarily imply the existence of a bug.
@@ -34,6 +38,13 @@ void __ubsan_handle_dynamic_type_cache_m
 extern "C" SANITIZER_INTERFACE_ATTRIBUTE
 void __ubsan_handle_dynamic_type_cache_miss_abort(
   DynamicTypeCacheMissData *Data, ValueHandle Pointer, ValueHandle Hash);
+
+/// \brief Handle a control flow integrity check failure by printing a
+/// diagnostic.
+extern "C" SANITIZER_INTERFACE_ATTRIBUTE void
+__ubsan_handle_cfi_bad_type(CFIBadTypeData *Data, ValueHandle Vtable);
+extern "C" SANITIZER_INTERFACE_ATTRIBUTE void
+__ubsan_handle_cfi_bad_type_abort(CFIBadTypeData *Data, ValueHandle Vtable);
 }
 
 #endif // UBSAN_HANDLERS_H
diff -upr /usr/src/llvm/projects/compiler-rt.285547/lib/ubsan/ubsan_handlers.h 
ubsan/ubsan_handlers.h
--- /usr/src/llvm/projects/compiler-rt.285547/lib/ubsan/ubsan_handlers.h        
2017-10-19 10:30:18.064920772 +0200
+++ ubsan/ubsan_handlers.h      2017-10-19 09:17:31.134837871 +0200
@@ -148,6 +146,13 @@ struct NonNullArgData {
 /// \brief Handle passing null pointer to function with nonnull attribute.
 RECOVERABLE(nonnull_arg, NonNullArgData *Data)
 
+struct PointerOverflowData {
+  SourceLocation Loc;
+};
+
+RECOVERABLE(pointer_overflow, PointerOverflowData *Data, ValueHandle Base,
+            ValueHandle Result)
+
 /// \brief Known CFI check kinds.
 /// Keep in sync with the enum of the same name in CodeGenFunction.h
 enum CFITypeCheckKind : unsigned char {
@@ -158,12 +163,20 @@ enum CFITypeCheckKind : unsigned char {
   CFITCK_ICall,
 };
 
+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)
--- /usr/src/llvm/projects/compiler-rt.285547/lib/ubsan/ubsan_platform.h        
2017-10-19 10:29:52.427255629 +0200
+++ ubsan/ubsan_platform.h      2017-10-19 09:17:31.133837883 +0200
@@ -13,6 +11,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(__x86_64__) || defined(__i386__) || defined(__arm__) || \
@@ -24,5 +23,6 @@
 #else
 # define CAN_SANITIZE_UB 0
 #endif
+#endif //CAN_SANITIZE_UB
 
 #endif
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/tsan/rtl/tsan_interface_atomic.cc 
    2017-10-19 10:29:53.124246525 +0200
+++ tsan/tsan_interface_atomic.cc       2017-10-19 09:17:31.128837944 +0200
@@ -450,10 +448,27 @@ static void AtomicFence(ThreadState *thr
 
 // C/C++
 
+static morder covert_morder(morder mo) {
+  if (flags()->force_seq_cst_atomics)
+    return (morder)mo_seq_cst;
+
+  // Filter out additional memory order flags:
+  // MEMMODEL_SYNC        = 1 << 15
+  // __ATOMIC_HLE_ACQUIRE = 1 << 16
+  // __ATOMIC_HLE_RELEASE = 1 << 17
+  //
+  // HLE is an optimization, and we pretend that elision always fails.
+  // MEMMODEL_SYNC is used when lowering __sync_ atomics,
+  // since we use __sync_ atomics for actual atomic operations,
+  // we can safely ignore it as well. It also subtly affects semantics,
+  // but we don't model the difference.
+  return (morder)(mo & 0x7fff);
+}
+
 #define SCOPED_ATOMIC(func, ...) \
     const uptr callpc = (uptr)__builtin_return_address(0); \
     uptr pc = StackTrace::GetCurrentPc(); \
-    mo = flags()->force_seq_cst_atomics ? (morder)mo_seq_cst : mo; \
+    mo = covert_morder(mo); \
     ThreadState *const thr = cur_thread(); \
     if (thr->ignore_interceptors) \
       return NoTsanAtomic##func(__VA_ARGS__); \
--- 
/usr/src/llvm/projects/compiler-rt.285547/lib/tsan/rtl/tsan_platform_linux.cc   
    2017-10-19 10:29:52.992248249 +0200
+++ tsan/tsan_platform_linux.cc 2017-10-19 09:17:31.129837932 +0200
@@ -289,7 +287,7 @@ void InitializePlatform() {
 int ExtractResolvFDs(void *state, int *fds, int nfd) {
 #if SANITIZER_LINUX && !SANITIZER_ANDROID
   int cnt = 0;
-  __res_state *statp = (__res_state*)state;
+  struct __res_state *statp = (struct __res_state*)state;
   for (int i = 0; i < MAXNS && cnt < nfd; i++) {
     if (statp->_u._ext.nsaddrs[i] && statp->_u._ext.nssocks[i] != -1)
       fds[cnt++] = statp->_u._ext.nssocks[i];
--- /usr/src/llvm/projects/compiler-rt.285547/lib/tsan/rtl/tsan_rtl.cc  
2017-10-19 10:29:53.167245964 +0200
+++ tsan/tsan_rtl.cc    2017-10-19 09:17:31.121838029 +0200
@@ -45,6 +43,7 @@ extern "C" void __tsan_resume() {
 namespace __tsan {
 
 #if !SANITIZER_GO && !SANITIZER_MAC
+  __attribute__((tls_model("initial-exec")))
 THREADLOCAL char cur_thread_placeholder[sizeof(ThreadState)] ALIGNED(64);
 #endif
 static char ctx_placeholder[sizeof(Context)] ALIGNED(64);
--- /usr/src/llvm/projects/compiler-rt.315899/lib/asan/asan_globals.cc  
2017-10-16 13:15:29.231304156 +0200
+++ asan/asan_globals.cc        2017-10-19 11:17:30.063515687 +0200
@@ -149,23 +147,6 @@ static void CheckODRViolationViaIndicato
   }
 }
 
-// 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
@@ -213,8 +194,6 @@ static void RegisterGlobal(const Global
     // where two globals with the same name are defined in different modules.
     if (UseODRIndicator(g))
       CheckODRViolationViaIndicator(g);
-    else
-      CheckODRViolationViaPoisoning(g);
   }
   if (CanPoisonMemory())
     PoisonRedZones(*g);
--- 
/usr/src/llvm/projects/compiler-rt.315899/lib/sanitizer_common/sanitizer_mac.cc 
    2017-10-16 13:15:28.767309991 +0200
+++ sanitizer_common/sanitizer_mac.cc   2017-10-19 11:17:30.098515256 +0200
@@ -37,7 +35,7 @@
 extern char **environ;
 #endif
 
-#if defined(__has_include) && __has_include(<os/trace.h>)
+#if defined(__has_include) && __has_include(<os/trace.h>) && 
defined(__BLOCKS__)
 #define SANITIZER_OS_TRACE 1
 #include <os/trace.h>
 #else
--- 
/usr/src/llvm/projects/compiler-rt.315899/lib/sanitizer_common/sanitizer_stacktrace.cc
      2017-06-06 12:33:41.951512038 +0200
+++ sanitizer_common/sanitizer_stacktrace.cc    2017-10-19 11:17:30.105515170 
+0200
@@ -57,8 +55,8 @@ static inline uhwptr *GetCanonicFrame(up
   // 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
--- 
/usr/src/llvm/projects/compiler-rt.315899/lib/sanitizer_common/sanitizer_symbolizer_libbacktrace.cc
 2017-10-19 10:30:45.124567343 +0200
+++ sanitizer_common/sanitizer_symbolizer_libbacktrace.cc       2017-10-19 
11:17:30.108515133 +0200
@@ -95,7 +93,8 @@ struct SymbolizeCodeCallbackArg {
     if (frames_symbolized > 0) {
       SymbolizedStack *cur = SymbolizedStack::New(addr);
       AddressInfo *info = &cur->info;
-      info->FillModuleInfo(first->info.module, first->info.module_offset);
+      info->FillModuleInfo(first->info.module, first->info.module_offset,
+                           first->info.module_arch);
       last->next = cur;
       last = cur;
     }
--- /usr/src/llvm/projects/compiler-rt.315899/lib/ubsan/ubsan_handlers_cxx.cc   
2017-10-19 10:30:45.122567369 +0200
+++ ubsan/ubsan_handlers_cxx.cc 2017-10-19 11:17:30.125514924 +0200
@@ -123,6 +121,7 @@ void __ubsan_handle_cfi_bad_type(CFIChec
     CheckKindStr = "cast to unrelated type";
     break;
   case CFITCK_ICall:
+  default:
     Die();
   }
 
--- /usr/src/llvm/projects/compiler-rt.315899/lib/ubsan/ubsan_platform.h        
2017-09-05 16:22:49.032429239 +0200
+++ ubsan/ubsan_platform.h      2017-10-19 11:17:30.126514912 +0200
@@ -13,6 +11,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__)) &&                                                   
\
@@ -25,5 +24,6 @@
 #else
 # define CAN_SANITIZE_UB 0
 #endif
+#endif //CAN_SANITIZE_UB
 
 #endif

Reply via email to