diff mbox

Fix sanitizer build on sparc (PR sanitizer/59758)

Message ID 87ha7w2tlk.fsf@oracle.com
State New
Headers show

Commit Message

Jose E. Marchesi Feb. 18, 2014, 5:55 p.m. UTC
Hi.

This patch fixes builds with --enable-sanitizer, which seems to be the
default for sparc now.

Build tested in a sparc64-*-linux-gnu system with linux 3.8.13 headers.

2014-02-18  Jose E. Marchesi  <jose.marchesi@oracle.com>

	PR sanitizer/59758
	* sanitizer_common/sanitizer_platform_limits_posix.h (__sanitizer):
	Define struct__old_kernel_stat_sz, struct_kernel_stat_sz and
	struct_kernel_stat64_sz for sparc targets (both 32 and 64 bits).
	(__sanitizer_ipc_perm): Adjust for sparc targets.
	(__sanitizer_shmid_ds): Likewise.
	(__sanitizer_sigaction): Likewise.
	(IOC_SIZE): Likewise.

	* sanitizer_common/sanitizer_platform_limits_linux.cc (time_t):
	defined as __kernel_time_t, which is needed for sparc.
	(struct___old_kernel_stat_sz): Don't check if __sparc__ is defined.

Comments

Jakub Jelinek Feb. 18, 2014, 6 p.m. UTC | #1
On Tue, Feb 18, 2014 at 06:55:51PM +0100, Jose E. Marchesi wrote:
> This patch fixes builds with --enable-sanitizer, which seems to be the
> default for sparc now.
> 
> Build tested in a sparc64-*-linux-gnu system with linux 3.8.13 headers.
> 
> 2014-02-18  Jose E. Marchesi  <jose.marchesi@oracle.com>
> 
> 	PR sanitizer/59758
> 	* sanitizer_common/sanitizer_platform_limits_posix.h (__sanitizer):
> 	Define struct__old_kernel_stat_sz, struct_kernel_stat_sz and
> 	struct_kernel_stat64_sz for sparc targets (both 32 and 64 bits).
> 	(__sanitizer_ipc_perm): Adjust for sparc targets.
> 	(__sanitizer_shmid_ds): Likewise.
> 	(__sanitizer_sigaction): Likewise.
> 	(IOC_SIZE): Likewise.
> 
> 	* sanitizer_common/sanitizer_platform_limits_linux.cc (time_t):
> 	defined as __kernel_time_t, which is needed for sparc.
> 	(struct___old_kernel_stat_sz): Don't check if __sparc__ is defined.

Please talk to Konstantin about getting this into the upstream compiler-rt
repository, we don't need to wait for a merge from there, so once it
is accepted there, the same patch can be applied to gcc too.

> Index: libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h
> ===================================================================
> --- libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h	(revision 207826)
> +++ libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h	(working copy)
> @@ -67,6 +67,14 @@
>    const unsigned struct___old_kernel_stat_sz = 0;
>    const unsigned struct_kernel_stat_sz = 144;
>    const unsigned struct_kernel_stat64_sz = 104;
> +#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 = 120;
> +  const unsigned struct_kernel_stat64_sz = 104;
>  #endif
>    struct __sanitizer_perf_event_attr {
>      unsigned type;
> @@ -145,6 +153,18 @@
>      unsigned __seq;
>      u64 __unused1;
>      u64 __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;
> @@ -162,6 +182,26 @@
>  
>    struct __sanitizer_shmid_ds {
>      __sanitizer_ipc_perm shm_perm;
> +  #if defined(__sparc__)
> +  # if !defined(__arch64__)
> +    u32 __pad1;
> +  # endif
> +    s64 shm_atime;
> +  # if !defined(__arch64__)
> +    u32 __pad2;
> +  # endif
> +    s64 shm_dtime;
> +  # if !defined(__arch64__)
> +    u32 __pad3;
> +  # endif
> +    s64 shm_ctime;
> +    uptr shm_segsz;
> +    int shm_cpid;
> +    int shm_lpid;
> +    u64 shm_nattch;
> +    u64 __glibc_reserved1;
> +    u64 __glibc_reserved2;
> +  #else    
>    #ifndef __powerpc__
>      uptr shm_segsz;
>    #elif !defined(__powerpc64__)
> @@ -199,6 +239,7 @@
>      uptr __unused4;
>      uptr __unused5;
>    #endif
> +#endif
>    };
>    #endif  // SANITIZER_LINUX && !SANITIZER_ANDROID
>  
> @@ -365,7 +406,11 @@
>        void (*sa_sigaction)(int sig, void *siginfo, void *uctx);
>      };
>      __sanitizer_sigset_t sa_mask;
> +#if defined(__sparc__)
> +    unsigned long sa_flags;
> +#else
>      int sa_flags;
> +#endif
>  #if SANITIZER_LINUX
>      void (*sa_restorer)();
>  #endif
> @@ -511,7 +556,16 @@
>    };
>  #endif
>  
> -#define IOC_SIZE(nr) (((nr) >> 16) & 0x3fff)
> +#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) >> 16) & 0x3fff)
> +#endif
>  
>    extern unsigned struct_arpreq_sz;
>    extern unsigned struct_ifreq_sz;
> Index: libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc
> ===================================================================
> --- libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc	(revision 207826)
> +++ libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc	(working copy)
> @@ -36,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
> @@ -62,7 +63,7 @@
>    unsigned struct_statfs64_sz = sizeof(struct statfs64);
>  }  // namespace __sanitizer
>  
> -#if !defined(__powerpc64__) && !defined(__x86_64__)
> +#if !defined(__powerpc64__) && !defined(__x86_64__) && !defined(__sparc__)
>  COMPILER_CHECK(struct___old_kernel_stat_sz == sizeof(struct __old_kernel_stat));
>  #endif

	Jakub
Konstantin Serebryany Feb. 18, 2014, 7:12 p.m. UTC | #2
On Tue, Feb 18, 2014 at 10:00 PM, Jakub Jelinek <jakub@redhat.com> wrote:
>
> On Tue, Feb 18, 2014 at 06:55:51PM +0100, Jose E. Marchesi wrote:
> > This patch fixes builds with --enable-sanitizer, which seems to be the
> > default for sparc now.
> >
> > Build tested in a sparc64-*-linux-gnu system with linux 3.8.13 headers.
> >
> > 2014-02-18  Jose E. Marchesi  <jose.marchesi@oracle.com>
> >
> >       PR sanitizer/59758
> >       * sanitizer_common/sanitizer_platform_limits_posix.h (__sanitizer):
> >       Define struct__old_kernel_stat_sz, struct_kernel_stat_sz and
> >       struct_kernel_stat64_sz for sparc targets (both 32 and 64 bits).
> >       (__sanitizer_ipc_perm): Adjust for sparc targets.
> >       (__sanitizer_shmid_ds): Likewise.
> >       (__sanitizer_sigaction): Likewise.
> >       (IOC_SIZE): Likewise.
> >
> >       * sanitizer_common/sanitizer_platform_limits_linux.cc (time_t):
> >       defined as __kernel_time_t, which is needed for sparc.
> >       (struct___old_kernel_stat_sz): Don't check if __sparc__ is defined.
>
> Please talk to Konstantin about getting this into the upstream compiler-rt
> repository, we don't need to wait for a merge from there, so once it
> is accepted there, the same patch can be applied to gcc too.

Right. Please read
https://code.google.com/p/address-sanitizer/wiki/HowToContribute

--kcc

>
> > Index: libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h
> > ===================================================================
> > --- libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h   (revision 207826)
> > +++ libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h   (working copy)
> > @@ -67,6 +67,14 @@
> >    const unsigned struct___old_kernel_stat_sz = 0;
> >    const unsigned struct_kernel_stat_sz = 144;
> >    const unsigned struct_kernel_stat64_sz = 104;
> > +#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 = 120;
> > +  const unsigned struct_kernel_stat64_sz = 104;
> >  #endif
> >    struct __sanitizer_perf_event_attr {
> >      unsigned type;
> > @@ -145,6 +153,18 @@
> >      unsigned __seq;
> >      u64 __unused1;
> >      u64 __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;
> > @@ -162,6 +182,26 @@
> >
> >    struct __sanitizer_shmid_ds {
> >      __sanitizer_ipc_perm shm_perm;
> > +  #if defined(__sparc__)
> > +  # if !defined(__arch64__)
> > +    u32 __pad1;
> > +  # endif
> > +    s64 shm_atime;
> > +  # if !defined(__arch64__)
> > +    u32 __pad2;
> > +  # endif
> > +    s64 shm_dtime;
> > +  # if !defined(__arch64__)
> > +    u32 __pad3;
> > +  # endif
> > +    s64 shm_ctime;
> > +    uptr shm_segsz;
> > +    int shm_cpid;
> > +    int shm_lpid;
> > +    u64 shm_nattch;
> > +    u64 __glibc_reserved1;
> > +    u64 __glibc_reserved2;
> > +  #else
> >    #ifndef __powerpc__
> >      uptr shm_segsz;
> >    #elif !defined(__powerpc64__)
> > @@ -199,6 +239,7 @@
> >      uptr __unused4;
> >      uptr __unused5;
> >    #endif
> > +#endif
> >    };
> >    #endif  // SANITIZER_LINUX && !SANITIZER_ANDROID
> >
> > @@ -365,7 +406,11 @@
> >        void (*sa_sigaction)(int sig, void *siginfo, void *uctx);
> >      };
> >      __sanitizer_sigset_t sa_mask;
> > +#if defined(__sparc__)
> > +    unsigned long sa_flags;
> > +#else
> >      int sa_flags;
> > +#endif
> >  #if SANITIZER_LINUX
> >      void (*sa_restorer)();
> >  #endif
> > @@ -511,7 +556,16 @@
> >    };
> >  #endif
> >
> > -#define IOC_SIZE(nr) (((nr) >> 16) & 0x3fff)
> > +#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) >> 16) & 0x3fff)
> > +#endif
> >
> >    extern unsigned struct_arpreq_sz;
> >    extern unsigned struct_ifreq_sz;
> > Index: libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc
> > ===================================================================
> > --- libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc  (revision 207826)
> > +++ libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc  (working copy)
> > @@ -36,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
> > @@ -62,7 +63,7 @@
> >    unsigned struct_statfs64_sz = sizeof(struct statfs64);
> >  }  // namespace __sanitizer
> >
> > -#if !defined(__powerpc64__) && !defined(__x86_64__)
> > +#if !defined(__powerpc64__) && !defined(__x86_64__) && !defined(__sparc__)
> >  COMPILER_CHECK(struct___old_kernel_stat_sz == sizeof(struct __old_kernel_stat));
> >  #endif
>
>         Jakub
Jose E. Marchesi Feb. 19, 2014, 12:45 p.m. UTC | #3
> On Tue, Feb 18, 2014 at 06:55:51PM +0100, Jose E. Marchesi wrote:
    > > This patch fixes builds with --enable-sanitizer, which seems to be the
    > > default for sparc now.
    > >
    > > Build tested in a sparc64-*-linux-gnu system with linux 3.8.13 headers.
    > >
    > > 2014-02-18  Jose E. Marchesi  <jose.marchesi@oracle.com>
    > >
    > >       PR sanitizer/59758
    > >       * sanitizer_common/sanitizer_platform_limits_posix.h (__sanitizer):
    > >       Define struct__old_kernel_stat_sz, struct_kernel_stat_sz and
    > >       struct_kernel_stat64_sz for sparc targets (both 32 and 64 bits).
    > >       (__sanitizer_ipc_perm): Adjust for sparc targets.
    > >       (__sanitizer_shmid_ds): Likewise.
    > >       (__sanitizer_sigaction): Likewise.
    > >       (IOC_SIZE): Likewise.
    > >
    > >       * sanitizer_common/sanitizer_platform_limits_linux.cc (time_t):
    > >       defined as __kernel_time_t, which is needed for sparc.
    > >       (struct___old_kernel_stat_sz): Don't check if __sparc__ is defined.
    >
    > Please talk to Konstantin about getting this into the upstream compiler-rt
    > repository, we don't need to wait for a merge from there, so once it
    > is accepted there, the same patch can be applied to gcc too.
    
    Right. Please read
    https://code.google.com/p/address-sanitizer/wiki/HowToContribute

Ok, I follow up on llvm-commits@cs.uiuc.edu then..
Jose E. Marchesi Feb. 20, 2014, 12:15 p.m. UTC | #4
> On Tue, Feb 18, 2014 at 06:55:51PM +0100, Jose E. Marchesi wrote:
    > > This patch fixes builds with --enable-sanitizer, which seems to be the
    > > default for sparc now.
    > >
    > > Build tested in a sparc64-*-linux-gnu system with linux 3.8.13 headers.
    > >
    > > 2014-02-18  Jose E. Marchesi  <jose.marchesi@oracle.com>
    > >
    > >       PR sanitizer/59758
    > >       * sanitizer_common/sanitizer_platform_limits_posix.h (__sanitizer):
    > >       Define struct__old_kernel_stat_sz, struct_kernel_stat_sz and
    > >       struct_kernel_stat64_sz for sparc targets (both 32 and 64 bits).
    > >       (__sanitizer_ipc_perm): Adjust for sparc targets.
    > >       (__sanitizer_shmid_ds): Likewise.
    > >       (__sanitizer_sigaction): Likewise.
    > >       (IOC_SIZE): Likewise.
    > >
    > >       * sanitizer_common/sanitizer_platform_limits_linux.cc (time_t):
    > >       defined as __kernel_time_t, which is needed for sparc.
    > >       (struct___old_kernel_stat_sz): Don't check if __sparc__ is defined.
    >
    > Please talk to Konstantin about getting this into the upstream compiler-rt
    > repository, we don't need to wait for a merge from there, so once it
    > is accepted there, the same patch can be applied to gcc too.
    
    Right. Please read
    https://code.google.com/p/address-sanitizer/wiki/HowToContribute
    
Yesterday I fetched and built the latest llvm/compiler-rt in sparc64.  I
could not manage (in a reasonable time) to get the stuff in
compiler-rt/lib/sanitizer_common and compiler-rt/lib/asan built: these
directories seems to be skipped when compiling on this platform.  No, I
am not familiar at all with the llvm/compiler-rt build system.  Also I
noticed that there are a lot of changes upstream since last gcc merge
that may or may not compile on sparc: basically constants and data
structures duplicating stuff from kernel headers.

Well, I really dont have time to hack the llvm build system and also
keep the upstream sanitizer compiling on sparc until next merge, sorry.

At this point I would suggest to either apply my patch to gcc's
libsanitizer to fix the sparc build until next merge[1] or disable
building libsanitizer on sparc targets.

[1] I offer my help to make sure that whatever comes in the next merge
    builds on sparc64 in the gcc source tree.
Konstantin Serebryany Feb. 20, 2014, 12:34 p.m. UTC | #5
>
> At this point I would suggest to either apply my patch to gcc's
> libsanitizer to fix the sparc build
Please don't.
The "merge" is actually not a merge, it is a simple copy of LLVM
sources over the GCC sources,
no *merging* is ever expected to happen.

> until next merge[1] or disable
> building libsanitizer on sparc targets.

Works for me.
If anyone really wants to support asan on sparc (s)he should work with
us on the upstream (LLVM) repo.
We welcome such work but will request a public build bot.

--kcc


>
> [1] I offer my help to make sure that whatever comes in the next merge
>     builds on sparc64 in the gcc source tree.
Jakub Jelinek Feb. 20, 2014, 12:34 p.m. UTC | #6
On Thu, Feb 20, 2014 at 01:15:37PM +0100, Jose E. Marchesi wrote:
> Yesterday I fetched and built the latest llvm/compiler-rt in sparc64.  I
> could not manage (in a reasonable time) to get the stuff in
> compiler-rt/lib/sanitizer_common and compiler-rt/lib/asan built: these
> directories seems to be skipped when compiling on this platform.  No, I
> am not familiar at all with the llvm/compiler-rt build system.  Also I
> noticed that there are a lot of changes upstream since last gcc merge
> that may or may not compile on sparc: basically constants and data
> structures duplicating stuff from kernel headers.

Most likely llvm asan isn't supported on sparc, or perhaps even llvm, I
think it is not your responsibility to fix it up.  So, if the patch is
clearly for sparc and doesn't affect anything else, it shouldn't break
anything on the llvm side, so I'd hope it should be ok as is to compiler-rt.

	Jakub
Konstantin Serebryany Feb. 20, 2014, 12:44 p.m. UTC | #7
On Thu, Feb 20, 2014 at 4:34 PM, Jakub Jelinek <jakub@redhat.com> wrote:
> On Thu, Feb 20, 2014 at 01:15:37PM +0100, Jose E. Marchesi wrote:
>> Yesterday I fetched and built the latest llvm/compiler-rt in sparc64.  I
>> could not manage (in a reasonable time) to get the stuff in
>> compiler-rt/lib/sanitizer_common and compiler-rt/lib/asan built: these
>> directories seems to be skipped when compiling on this platform.  No, I
>> am not familiar at all with the llvm/compiler-rt build system.  Also I
>> noticed that there are a lot of changes upstream since last gcc merge
>> that may or may not compile on sparc: basically constants and data
>> structures duplicating stuff from kernel headers.
>
> Most likely llvm asan isn't supported on sparc, or perhaps even llvm, I
> think it is not your responsibility to fix it up.  So, if the patch is
> clearly for sparc and doesn't affect anything else, it shouldn't break
> anything on the llvm side, so I'd hope it should be ok as is to compiler-rt.

We can accept any patch that looks reasonable and does not break our testing.
We can not promise to keep sparc in usable state as we apply other
changes (unless you set a public build bot),
but of course we'll not to break sparc intentionally.

--kcc

>
>         Jakub
Jakub Jelinek Feb. 20, 2014, 12:56 p.m. UTC | #8
On Thu, Feb 20, 2014 at 04:44:48PM +0400, Konstantin Serebryany wrote:
> On Thu, Feb 20, 2014 at 4:34 PM, Jakub Jelinek <jakub@redhat.com> wrote:
> > On Thu, Feb 20, 2014 at 01:15:37PM +0100, Jose E. Marchesi wrote:
> >> Yesterday I fetched and built the latest llvm/compiler-rt in sparc64.  I
> >> could not manage (in a reasonable time) to get the stuff in
> >> compiler-rt/lib/sanitizer_common and compiler-rt/lib/asan built: these
> >> directories seems to be skipped when compiling on this platform.  No, I
> >> am not familiar at all with the llvm/compiler-rt build system.  Also I
> >> noticed that there are a lot of changes upstream since last gcc merge
> >> that may or may not compile on sparc: basically constants and data
> >> structures duplicating stuff from kernel headers.
> >
> > Most likely llvm asan isn't supported on sparc, or perhaps even llvm, I
> > think it is not your responsibility to fix it up.  So, if the patch is
> > clearly for sparc and doesn't affect anything else, it shouldn't break
> > anything on the llvm side, so I'd hope it should be ok as is to compiler-rt.
> 
> We can accept any patch that looks reasonable and does not break our testing.
> We can not promise to keep sparc in usable state as we apply other
> changes (unless you set a public build bot),
> but of course we'll not to break sparc intentionally.

So I think that it is this case.  Of course it is possible next merge
from compiler-rt will break sparc again, so I think we should CC affected
target maintainers at that point and let them test/fix it up when that
happens, but that will be post 4.9.

	Jakub
diff mbox

Patch

Index: libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h
===================================================================
--- libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h	(revision 207826)
+++ libsanitizer/sanitizer_common/sanitizer_platform_limits_posix.h	(working copy)
@@ -67,6 +67,14 @@ 
   const unsigned struct___old_kernel_stat_sz = 0;
   const unsigned struct_kernel_stat_sz = 144;
   const unsigned struct_kernel_stat64_sz = 104;
+#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 = 120;
+  const unsigned struct_kernel_stat64_sz = 104;
 #endif
   struct __sanitizer_perf_event_attr {
     unsigned type;
@@ -145,6 +153,18 @@ 
     unsigned __seq;
     u64 __unused1;
     u64 __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;
@@ -162,6 +182,26 @@ 
 
   struct __sanitizer_shmid_ds {
     __sanitizer_ipc_perm shm_perm;
+  #if defined(__sparc__)
+  # if !defined(__arch64__)
+    u32 __pad1;
+  # endif
+    s64 shm_atime;
+  # if !defined(__arch64__)
+    u32 __pad2;
+  # endif
+    s64 shm_dtime;
+  # if !defined(__arch64__)
+    u32 __pad3;
+  # endif
+    s64 shm_ctime;
+    uptr shm_segsz;
+    int shm_cpid;
+    int shm_lpid;
+    u64 shm_nattch;
+    u64 __glibc_reserved1;
+    u64 __glibc_reserved2;
+  #else    
   #ifndef __powerpc__
     uptr shm_segsz;
   #elif !defined(__powerpc64__)
@@ -199,6 +239,7 @@ 
     uptr __unused4;
     uptr __unused5;
   #endif
+#endif
   };
   #endif  // SANITIZER_LINUX && !SANITIZER_ANDROID
 
@@ -365,7 +406,11 @@ 
       void (*sa_sigaction)(int sig, void *siginfo, void *uctx);
     };
     __sanitizer_sigset_t sa_mask;
+#if defined(__sparc__)
+    unsigned long sa_flags;
+#else
     int sa_flags;
+#endif
 #if SANITIZER_LINUX
     void (*sa_restorer)();
 #endif
@@ -511,7 +556,16 @@ 
   };
 #endif
 
-#define IOC_SIZE(nr) (((nr) >> 16) & 0x3fff)
+#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) >> 16) & 0x3fff)
+#endif
 
   extern unsigned struct_arpreq_sz;
   extern unsigned struct_ifreq_sz;
Index: libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc
===================================================================
--- libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc	(revision 207826)
+++ libsanitizer/sanitizer_common/sanitizer_platform_limits_linux.cc	(working copy)
@@ -36,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
@@ -62,7 +63,7 @@ 
   unsigned struct_statfs64_sz = sizeof(struct statfs64);
 }  // namespace __sanitizer
 
-#if !defined(__powerpc64__) && !defined(__x86_64__)
+#if !defined(__powerpc64__) && !defined(__x86_64__) && !defined(__sparc__)
 COMPILER_CHECK(struct___old_kernel_stat_sz == sizeof(struct __old_kernel_stat));
 #endif