nolibc: fix fd_set type
authorSven Schnelle <svens@linux.ibm.com>
Mon, 9 Jan 2023 07:54:37 +0000 (08:54 +0100)
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>
Wed, 1 Feb 2023 07:34:30 +0000 (08:34 +0100)
[ Upstream commit feaf75658783a919410f8c2039dbc24b6a29603d ]

The kernel uses unsigned long for the fd_set bitmap,
but nolibc use u32. This works fine on little endian
machines, but fails on big endian. Convert to unsigned
long to fix this.

Signed-off-by: Sven Schnelle <svens@linux.ibm.com>
Signed-off-by: Willy Tarreau <w@1wt.eu>
Signed-off-by: Paul E. McKenney <paulmck@kernel.org>
Signed-off-by: Sasha Levin <sashal@kernel.org>
tools/include/nolibc/types.h

index 9599970..300e0ff 100644 (file)
 #define EXIT_SUCCESS 0
 #define EXIT_FAILURE 1
 
+#define FD_SETIDXMASK (8 * sizeof(unsigned long))
+#define FD_SETBITMASK (8 * sizeof(unsigned long)-1)
+
 /* for select() */
 typedef struct {
-       uint32_t fd32[(FD_SETSIZE + 31) / 32];
+       unsigned long fds[(FD_SETSIZE + FD_SETBITMASK) / FD_SETIDXMASK];
 } fd_set;
 
-#define FD_CLR(fd, set) do {                                            \
-               fd_set *__set = (set);                                  \
-               int __fd = (fd);                                        \
-               if (__fd >= 0)                                          \
-                       __set->fd32[__fd / 32] &= ~(1U << (__fd & 31)); \
+#define FD_CLR(fd, set) do {                                           \
+               fd_set *__set = (set);                                  \
+               int __fd = (fd);                                        \
+               if (__fd >= 0)                                          \
+                       __set->fds[__fd / FD_SETIDXMASK] &=             \
+                               ~(1U << (__fd & FX_SETBITMASK));        \
        } while (0)
 
-#define FD_SET(fd, set) do {                                            \
-               fd_set *__set = (set);                                  \
-               int __fd = (fd);                                        \
-               if (__fd >= 0)                                          \
-                       __set->fd32[__fd / 32] |= 1U << (__fd & 31);    \
+#define FD_SET(fd, set) do {                                           \
+               fd_set *__set = (set);                                  \
+               int __fd = (fd);                                        \
+               if (__fd >= 0)                                          \
+                       __set->fds[__fd / FD_SETIDXMASK] |=             \
+                               1 << (__fd & FD_SETBITMASK);            \
        } while (0)
 
-#define FD_ISSET(fd, set) ({                                                  \
-               fd_set *__set = (set);                                        \
-               int __fd = (fd);                                              \
-               int __r = 0;                                                  \
-               if (__fd >= 0)                                                \
-                       __r = !!(__set->fd32[__fd / 32] & 1U << (__fd & 31)); \
-               __r;                                                          \
+#define FD_ISSET(fd, set) ({                                           \
+                       fd_set *__set = (set);                          \
+                       int __fd = (fd);                                \
+               int __r = 0;                                            \
+               if (__fd >= 0)                                          \
+                       __r = !!(__set->fds[__fd / FD_SETIDXMASK] &     \
+1U << (__fd & FD_SET_BITMASK));                                                \
+               __r;                                                    \
        })
 
-#define FD_ZERO(set) do {                                               \
-               fd_set *__set = (set);                                  \
-               int __idx;                                              \
-               for (__idx = 0; __idx < (FD_SETSIZE+31) / 32; __idx ++) \
-                       __set->fd32[__idx] = 0;                         \
+#define FD_ZERO(set) do {                                              \
+               fd_set *__set = (set);                                  \
+               int __idx;                                              \
+               int __size = (FD_SETSIZE+FD_SETBITMASK) / FD_SETIDXMASK;\
+               for (__idx = 0; __idx < __size; __idx++)                \
+                       __set->fds[__idx] = 0;                          \
        } while (0)
 
 /* for poll() */