diff mbox series

[uclibc-ng-devel] Add time64 support for sparc.

Message ID 20240229163553.2476623-1-dm.chestnykh@gmail.com
State Accepted
Headers show
Series [uclibc-ng-devel] Add time64 support for sparc. | expand

Commit Message

Dmitry Chestnykh Feb. 29, 2024, 4:35 p.m. UTC
By some reason sparc ld.so cannot work properly with
statx() system call, so fallback to regular stat() family in ld.so.

Signed-off-by: Dmitry Chestnykh <dm.chestnykh@gmail.com>
---
 extra/Configs/Config.in                        |  1 +
 ldso/include/dl-syscall.h                      | 10 +++++-----
 libc/sysdeps/linux/sparc/bits/kernel_stat.h    | 16 ++++++++++++++++
 libc/sysdeps/linux/sparc/bits/sem.h            | 18 ++++++++++++++++--
 libc/sysdeps/linux/sparc/bits/typesizes.h      | 12 ++++++++++++
 .../linux/sparc/bits/uClibc_arch_features.h    |  3 ---
 6 files changed, 50 insertions(+), 10 deletions(-)

Comments

Waldemar Brodkorb March 3, 2024, 7:13 p.m. UTC | #1
Hi Dmitry,
Dmitry Chestnykh wrote,

> By some reason sparc ld.so cannot work properly with
> statx() system call, so fallback to regular stat() family in ld.so.
> 
> Signed-off-by: Dmitry Chestnykh <dm.chestnykh@gmail.com>

Okay a little bit ugly that we need an extra condition only for
sparc, but okay. Committed and pushed,
 Thanks
  Waldemar
diff mbox series

Patch

diff --git a/extra/Configs/Config.in b/extra/Configs/Config.in
index ded1f72c9..bae7b4885 100644
--- a/extra/Configs/Config.in
+++ b/extra/Configs/Config.in
@@ -1030,6 +1030,7 @@  config UCLIBC_USE_TIME64
 		   (TARGET_mips && !CONFIG_MIPS_N64_ABI) || \
 		   TARGET_or1k                           || \
 		   TARGET_powerpc                        || \
+		   TARGET_sparc                          || \
 		   TARGET_xtensa
 	# TODO: add support for other architectures
 	default n
diff --git a/ldso/include/dl-syscall.h b/ldso/include/dl-syscall.h
index 666a7c693..b40f58b10 100644
--- a/ldso/include/dl-syscall.h
+++ b/ldso/include/dl-syscall.h
@@ -20,7 +20,7 @@  extern int _dl_errno;
 #define _SYS_MMAN_H 1
 #include <bits/mman.h>
 
-#if defined(__ARCH_HAS_DEPRECATED_SYSCALLS__) && !defined(__UCLIBC_USE_TIME64__)
+#if defined(__ARCH_HAS_DEPRECATED_SYSCALLS__) && (!defined(__UCLIBC_USE_TIME64__) || defined(__sparc__))
 /* Pull in whatever this particular arch's kernel thinks the kernel version of
  * struct stat should look like.  It turns out that each arch has a different
  * opinion on the subject, and different kernel revs use different names... */
@@ -116,7 +116,7 @@  static __always_inline _syscall3(unsigned long, _dl_read, int, fd,
 static __always_inline _syscall3(int, _dl_mprotect, const void *, addr,
                         unsigned long, len, int, prot)
 
-#if defined __NR_fstatat64 && !defined __NR_stat && !defined(__UCLIBC_USE_TIME64__)
+#if defined __NR_fstatat64 && !defined __NR_stat && (!defined(__UCLIBC_USE_TIME64__) || defined(__sparc__))
 # define __NR__dl_fstatat64 __NR_fstatat64
 static __always_inline _syscall4(int, _dl_fstatat64, int, fd, const char *,
 				 fn, struct stat *, stat, int, flags)
@@ -126,7 +126,7 @@  static __always_inline int _dl_stat(const char *file_name,
 {
 	return _dl_fstatat64(AT_FDCWD, file_name, buf, 0);
 }
-#elif defined __NR_newfstatat && !defined __NR_stat && !defined(__UCLIBC_USE_TIME64__)
+#elif defined __NR_newfstatat && !defined __NR_stat && (!defined(__UCLIBC_USE_TIME64__) || defined(__sparc__))
 # define __NR__dl_newfstatat __NR_newfstatat
 static __always_inline _syscall4(int, _dl_newfstatat, int, fd, const char *,
 				 fn, struct stat *, stat, int, flags)
@@ -136,7 +136,7 @@  static __always_inline int _dl_stat(const char *file_name,
 {
 	return _dl_newfstatat(AT_FDCWD, file_name, buf, 0);
 }
-#elif defined __NR_stat && !defined(__UCLIBC_USE_TIME64__)
+#elif defined __NR_stat && (!defined(__UCLIBC_USE_TIME64__) || defined(__sparc__))
 # define __NR__dl_stat __NR_stat
 static __always_inline _syscall2(int, _dl_stat, const char *, file_name,
                         struct stat *, buf)
@@ -160,7 +160,7 @@  static __always_inline int _dl_stat(const char *file_name,
 }
 #endif
 
-#if defined __NR_fstat64 && !defined __NR_fstat && !defined(__UCLIBC_USE_TIME64__)
+#if defined __NR_fstat64 && !defined __NR_fstat && (!defined(__UCLIBC_USE_TIME64__) || defined(__sparc__))
 # define __NR__dl_fstat __NR_fstat64
 static __always_inline _syscall2(int, _dl_fstat, int, fd, struct stat *, buf)
 #elif defined __NR_fstat
diff --git a/libc/sysdeps/linux/sparc/bits/kernel_stat.h b/libc/sysdeps/linux/sparc/bits/kernel_stat.h
index e960857fe..5e214c72f 100644
--- a/libc/sysdeps/linux/sparc/bits/kernel_stat.h
+++ b/libc/sysdeps/linux/sparc/bits/kernel_stat.h
@@ -5,6 +5,10 @@ 
  * struct kernel_stat should look like...  It turns out each arch has a
  * different opinion on the subject... */
 
+#if defined(__UCLIBC_USE_TIME64__)
+#include "internal/time64_helpers.h"
+#endif
+
 struct kernel_stat {
     unsigned short	st_dev;
     unsigned long	st_ino;
@@ -14,9 +18,15 @@  struct kernel_stat {
     unsigned short	st_gid;
     unsigned short	st_rdev;
     long		st_size;
+#if defined(__UCLIBC_USE_TIME64__)
+    struct __ts32_struct __st_atim32;
+    struct __ts32_struct __st_mtim32;
+    struct __ts32_struct __st_ctim32;
+#else
     struct timespec	st_atim;
     struct timespec	st_mtim;
     struct timespec	st_ctim;
+#endif
     long		st_blksize;
     long		st_blocks;
     unsigned long	__unused4[2];
@@ -35,9 +45,15 @@  struct kernel_stat64 {
 	unsigned int	st_blksize;
 	unsigned char	__pad4[8];
 	unsigned int	st_blocks;
+#if defined(__UCLIBC_USE_TIME64__)
+	struct __ts32_struct __st_atim32;
+	struct __ts32_struct __st_mtim32;
+	struct __ts32_struct __st_ctim32;
+#else
 	struct timespec	st_atim;
 	struct timespec	st_mtim;
 	struct timespec	st_ctim;
+#endif
 	unsigned int	__unused4;
 	unsigned int	__unused5;
 };
diff --git a/libc/sysdeps/linux/sparc/bits/sem.h b/libc/sysdeps/linux/sparc/bits/sem.h
index 04c579fc6..23fd7c2eb 100644
--- a/libc/sysdeps/linux/sparc/bits/sem.h
+++ b/libc/sysdeps/linux/sparc/bits/sem.h
@@ -38,10 +38,24 @@  struct semid_ds
 {
   struct ipc_perm sem_perm;		/* operation permission struct */
   unsigned int __pad1;
-  __time_t sem_otime;			/* last semop() time */
+#if defined(__UCLIBC_USE_TIME64__)
+  unsigned long int __sem_otime_internal_1; /* last semop() time */
+  unsigned long int __sem_otime_internal_2;
+#else
+  __time_t sem_otime;                  /* last semop() time */
+#endif
   unsigned int __pad2;
-  __time_t sem_ctime;			/* last time changed by semctl() */
+#if defined(__UCLIBC_USE_TIME64__)
+  unsigned long int __sem_ctime_internal_1; /* last time changed by semctl() */
+  unsigned long int __sem_ctime_internal_2;
+#else
+  __time_t sem_ctime;                  /* last time changed by semctl() */
+#endif
   unsigned long int sem_nsems;		/* number of semaphores in set */
+#if defined(__UCLIBC_USE_TIME64__)
+  __time_t sem_otime;
+  __time_t sem_ctime;
+#endif
   unsigned long int __uclibc_unused1;
   unsigned long int __uclibc_unused2;
 };
diff --git a/libc/sysdeps/linux/sparc/bits/typesizes.h b/libc/sysdeps/linux/sparc/bits/typesizes.h
index 37b7656aa..c7b7f5576 100644
--- a/libc/sysdeps/linux/sparc/bits/typesizes.h
+++ b/libc/sysdeps/linux/sparc/bits/typesizes.h
@@ -46,9 +46,21 @@ 
 #define	__FSFILCNT64_T_TYPE	__UQUAD_TYPE
 #define	__ID_T_TYPE		__U32_TYPE
 #define __CLOCK_T_TYPE		__SLONGWORD_TYPE
+
+#ifdef __UCLIBC_USE_TIME64__
+#define __TIME_T_TYPE		__S64_TYPE
+#else
 #define __TIME_T_TYPE		__SLONGWORD_TYPE
+#endif
+
 #define __USECONDS_T_TYPE	__U32_TYPE
+
+#ifdef __UCLIBC_USE_TIME64__
+#define __SUSECONDS_T_TYPE	__S64_TYPE
+#else
 #define __SUSECONDS_T_TYPE	__S32_TYPE
+#endif
+
 #define __DADDR_T_TYPE		__S32_TYPE
 #define __SWBLK_T_TYPE		__SLONGWORD_TYPE
 #define __KEY_T_TYPE		__S32_TYPE
diff --git a/libc/sysdeps/linux/sparc/bits/uClibc_arch_features.h b/libc/sysdeps/linux/sparc/bits/uClibc_arch_features.h
index 76f5084ff..283a250bb 100644
--- a/libc/sysdeps/linux/sparc/bits/uClibc_arch_features.h
+++ b/libc/sysdeps/linux/sparc/bits/uClibc_arch_features.h
@@ -11,9 +11,6 @@ 
 /* can your target use syscall6() for mmap ? */
 #define __UCLIBC_MMAP_HAS_6_ARGS__
 
-/* does your target use statx */
-#undef __UCLIBC_HAVE_STATX__
-
 /* does your target align 64bit values in register pairs ? (32bit arches only) */
 #undef __UCLIBC_SYSCALL_ALIGN_64BIT__