#define SIOCSPGRP      _IOW('s', 8, pid_t)
 #define SIOCGPGRP      _IOR('s', 9, pid_t)
 
-#define SIOCGSTAMP     0x8906          /* Get stamp (timeval) */
-#define SIOCGSTAMPNS   0x8907          /* Get stamp (timespec) */
+#define SIOCGSTAMP_OLD 0x8906          /* Get stamp (timeval) */
+#define SIOCGSTAMPNS_OLD 0x8907                /* Get stamp (timespec) */
 
 #endif /* _ASM_ALPHA_SOCKIOS_H */
 
 #define SIOCSPGRP      _IOW('s', 8, pid_t)
 #define SIOCGPGRP      _IOR('s', 9, pid_t)
 
-#define SIOCGSTAMP     0x8906          /* Get stamp (timeval) */
-#define SIOCGSTAMPNS   0x8907          /* Get stamp (timespec) */
+#define SIOCGSTAMP_OLD 0x8906          /* Get stamp (timeval) */
+#define SIOCGSTAMPNS_OLD 0x8907                /* Get stamp (timespec) */
 
 #endif /* _ASM_SOCKIOS_H */
 
 #define SIOCSPGRP      _IOW('s', 8, pid_t)
 #define SIOCGPGRP      _IOR('s', 9, pid_t)
 
-#define SIOCGSTAMP     _IOR('s', 100, struct timeval) /* Get stamp (timeval) */
-#define SIOCGSTAMPNS   _IOR('s', 101, struct timespec) /* Get stamp (timespec) */
+#define SIOCGSTAMP_OLD _IOR('s', 100, struct timeval) /* Get stamp (timeval) */
+#define SIOCGSTAMPNS_OLD _IOR('s', 101, struct timespec) /* Get stamp (timespec) */
+
 #endif /* __ASM_SH_SOCKIOS_H */
 
 #define SIOCSPGRP      _IOW('s', 8, pid_t)
 #define SIOCGPGRP      _IOR('s', 9, pid_t)
 
-#define SIOCGSTAMP     0x8906          /* Get stamp (timeval) */
-#define SIOCGSTAMPNS   0x8907          /* Get stamp (timespec) */
+#define SIOCGSTAMP_OLD 0x8906          /* Get stamp (timeval) */
+#define SIOCGSTAMPNS_OLD 0x8907                /* Get stamp (timespec) */
 
 #endif /* _XTENSA_SOCKIOS_H */
 
 #define FIOGETOWN      0x8903
 #define SIOCGPGRP      0x8904
 #define SIOCATMARK     0x8905
-#define SIOCGSTAMP     0x8906          /* Get stamp (timeval) */
-#define SIOCGSTAMPNS   0x8907          /* Get stamp (timespec) */
+#define SIOCGSTAMP_OLD 0x8906          /* Get stamp (timeval) */
+#define SIOCGSTAMPNS_OLD 0x8907                /* Get stamp (timespec) */
 
 #endif /* __ASM_GENERIC_SOCKIOS_H */
 
 #ifndef _LINUX_SOCKIOS_H
 #define _LINUX_SOCKIOS_H
 
+#include <asm/bitsperlong.h>
 #include <asm/sockios.h>
 
 /* Linux-specific socket ioctls */
 
 #define SOCK_IOC_TYPE  0x89
 
+/*
+ * the timeval/timespec data structure layout is defined by libc,
+ * so we need to cover both possible versions on 32-bit.
+ */
+/* Get stamp (timeval) */
+#define SIOCGSTAMP_NEW  _IOR(SOCK_IOC_TYPE, 0x06, long long[2])
+/* Get stamp (timespec) */
+#define SIOCGSTAMPNS_NEW _IOR(SOCK_IOC_TYPE, 0x07, long long[2])
+
+#if __BITS_PER_LONG == 64 || (defined(__x86_64__) && defined(__ILP32__))
+/* on 64-bit and x32, avoid the ?: operator */
+#define SIOCGSTAMP     SIOCGSTAMP_OLD
+#define SIOCGSTAMPNS   SIOCGSTAMPNS_OLD
+#else
+#define SIOCGSTAMP     ((sizeof(struct timeval))  == 8 ? \
+                        SIOCGSTAMP_OLD   : SIOCGSTAMP_NEW)
+#define SIOCGSTAMPNS   ((sizeof(struct timespec)) == 8 ? \
+                        SIOCGSTAMPNS_OLD : SIOCGSTAMPNS_NEW)
+#endif
+
 /* Routing table calls. */
 #define SIOCADDRT      0x890B          /* add routing table entry      */
 #define SIOCDELRT      0x890C          /* delete routing table entry   */
 
 
                        err = open_related_ns(&net->ns, get_net_ns);
                        break;
-               case SIOCGSTAMP:
-               case SIOCGSTAMPNS:
+               case SIOCGSTAMP_OLD:
+               case SIOCGSTAMPNS_OLD:
                        if (!sock->ops->gettstamp) {
                                err = -ENOIOCTLCMD;
                                break;
                        }
                        err = sock->ops->gettstamp(sock, argp,
-                                                  cmd == SIOCGSTAMP, false);
+                                                  cmd == SIOCGSTAMP_OLD,
+                                                  !IS_ENABLED(CONFIG_64BIT));
+               case SIOCGSTAMP_NEW:
+               case SIOCGSTAMPNS_NEW:
+                       if (!sock->ops->gettstamp) {
+                               err = -ENOIOCTLCMD;
+                               break;
+                       }
+                       err = sock->ops->gettstamp(sock, argp,
+                                                  cmd == SIOCGSTAMP_NEW,
+                                                  false);
                        break;
                default:
                        err = sock_do_ioctl(net, sock, cmd, arg);
        case SIOCADDRT:
        case SIOCDELRT:
                return routing_ioctl(net, sock, cmd, argp);
-       case SIOCGSTAMP:
-       case SIOCGSTAMPNS:
+       case SIOCGSTAMP_OLD:
+       case SIOCGSTAMPNS_OLD:
                if (!sock->ops->gettstamp)
                        return -ENOIOCTLCMD;
-               return sock->ops->gettstamp(sock, argp, cmd == SIOCGSTAMP,
+               return sock->ops->gettstamp(sock, argp, cmd == SIOCGSTAMP_OLD,
                                            !COMPAT_USE_64BIT_TIME);
 
        case SIOCBONDSLAVEINFOQUERY:
        case SIOCADDDLCI:
        case SIOCDELDLCI:
        case SIOCGSKNS:
+       case SIOCGSTAMP_NEW:
+       case SIOCGSTAMPNS_NEW:
                return sock_ioctl(file, cmd, arg);
 
        case SIOCGIFFLAGS: