diff --git a/include/lighttpd/utils.h b/include/lighttpd/utils.h index e947fb8..d0d07b6 100644 --- a/include/lighttpd/utils.h +++ b/include/lighttpd/utils.h @@ -66,4 +66,6 @@ LI_API gboolean l_g_strncase_equal(GString *str, const gchar *s, guint len); LI_API GString *l_g_string_assign_len(GString *string, const gchar *val, gssize len); +LI_API gsize dirent_buf_size(DIR * dirp); + #endif diff --git a/src/utils.c b/src/utils.c index ab81dda..cdc7299 100644 --- a/src/utils.c +++ b/src/utils.c @@ -638,3 +638,33 @@ GString *l_g_string_assign_len(GString *string, const gchar *val, gssize len) { g_string_append_len(string, val, len); return string; } + +/* http://womble.decadentplace.org.uk/readdir_r-advisory.html */ +gsize dirent_buf_size(DIR * dirp) { + glong name_max; + gsize name_end; + +# if !defined(HAVE_DIRFD) + UNUSED(dirp); +# endif + +# if defined(HAVE_FPATHCONF) && defined(HAVE_DIRFD) && defined(_PC_NAME_MAX) + name_max = fpathconf(dirfd(dirp), _PC_NAME_MAX); + if (name_max == -1) +# if defined(NAME_MAX) + name_max = (NAME_MAX > 255) ? NAME_MAX : 255; +# else + return (gsize)(-1); +# endif +# else +# if defined(NAME_MAX) + name_max = (NAME_MAX > 255) ? NAME_MAX : 255; +# else +# error "buffer size for readdir_r cannot be determined" +# endif +# endif + + name_end = (gsize)offsetof(struct dirent, d_name) + name_max + 1; + + return (name_end > sizeof(struct dirent) ? name_end : sizeof(struct dirent)); +}