Whamcloud - gitweb
libe2p: avoid potential integer overflow in interate_on_dir()
authorTheodore Ts'o <tytso@mit.edu>
Mon, 26 May 2025 14:09:59 +0000 (10:09 -0400)
committerTheodore Ts'o <tytso@mit.edu>
Mon, 26 May 2025 14:09:59 +0000 (10:09 -0400)
Overflows won't happen if the OS's implementation of pathconf()
returns reasonable values, but we can make it a bit more hardened
against maliciou implementations.

Addresses-Coverity-Bug: 1633758
Signed-off-by: Theodore Ts'o <tytso@mit.edu>
lib/e2p/iod.c

index 6a030dd..5e07654 100644 (file)
 #include <stdlib.h>
 #include <string.h>
 
+#define max_long(a,b) ((((long) (a)) > ((long) (b))) ? (a) : (b))
+
 int iterate_on_dir (const char * dir_name,
                    int (*func) (const char *, struct dirent *, void *),
                    void * private)
 {
        DIR * dir;
        struct dirent *de, *dep;
-       int     max_len = -1, len, ret = 0;
+       long    name_max = -1;
+       int     max_len, len, ret = 0;
 
 #if HAVE_PATHCONF && defined(_PC_NAME_MAX)
-       max_len = pathconf(dir_name, _PC_NAME_MAX);
+       name_max = pathconf(dir_name, _PC_NAME_MAX);
 #endif
-       if (max_len == -1) {
 #ifdef _POSIX_NAME_MAX
-               max_len = _POSIX_NAME_MAX;
-#else
+       name_max = max_long(name_max, _POSIX_NAME_MAX);
+#endif
 #ifdef NAME_MAX
-               max_len = NAME_MAX;
-#else
-               max_len = 256;
-#endif /* NAME_MAX */
-#endif /* _POSIX_NAME_MAX */
-       }
-       max_len += sizeof(struct dirent);
+       name_max = max_long(name_max, NAME_MAX);
+#endif
+       name_max = max_long(name_max, 256);
+       /* clamp name_max in case the OS returns something crazy */
+       if (name_max > 65536)
+               name_max = 65536;
 
+       max_len = name_max + sizeof(struct dirent);
        de = malloc(max_len+1);
        if (!de)
                return -1;