From d6dbf831f70bcb2e83676d92903b303010253272 Mon Sep 17 00:00:00 2001 From: Sergey Lyubka Date: Sat, 24 Jul 2021 10:35:48 +0100 Subject: [PATCH] Remove mg_stat --- mongoose.c | 27 ++++++++++----------------- mongoose.h | 28 ++++++++++++++++++++-------- src/arch_unix.h | 3 ++- src/arch_win32.h | 18 +++++++++++++++++- src/fs.c | 11 ++--------- src/fs.h | 7 +------ src/http.c | 16 ++++++++-------- test/unit_test.c | 6 +++--- 8 files changed, 63 insertions(+), 53 deletions(-) diff --git a/mongoose.c b/mongoose.c index c042408a..2c13f6da 100644 --- a/mongoose.c +++ b/mongoose.c @@ -411,15 +411,8 @@ void mg_error(struct mg_connection *c, const char *fmt, ...) { #endif -int mg_stat(const char *path, mg_stat_t *st) { -#ifdef _WIN32 - wchar_t tmp[MG_PATH_MAX]; - MultiByteToWideChar(CP_UTF8, 0, path, -1, tmp, sizeof(tmp) / sizeof(tmp[0])); - return _wstati64(tmp, st); -#else - return stat(path, st); -#endif -} +// FILE *fopen_packed(const char *path, const char *mode) { +//} #ifdef MG_ENABLE_LINES #line 1 "src/http.c" @@ -797,7 +790,7 @@ static void restore_http_cb(struct mg_connection *c) { c->pfn = http_cb; } -char *mg_http_etag(char *buf, size_t len, mg_stat_t *st) { +char *mg_http_etag(char *buf, size_t len, struct stat *st) { snprintf(buf, len, "\"%lx." MG_INT64_FMT "\"", (unsigned long) st->st_mtime, (int64_t) st->st_size); return buf; @@ -938,10 +931,10 @@ static int getrange(struct mg_str *s, int64_t *a, int64_t *b) { void mg_http_serve_file(struct mg_connection *c, struct mg_http_message *hm, const char *path, const char *mime, const char *hdrs) { struct mg_str *inm = mg_http_get_header(hm, "If-None-Match"); - mg_stat_t st; + struct stat st; char etag[64]; FILE *fp = fopen(path, "rb"); - if (fp == NULL || mg_stat(path, &st) != 0 || + if (fp == NULL || stat(path, &st) != 0 || mg_http_etag(etag, sizeof(etag), &st) != etag) { LOG(LL_DEBUG, ("404 [%.*s] [%s] %p", (int) hm->uri.len, hm->uri.ptr, path, (void *) fp)); @@ -1015,8 +1008,8 @@ bool mg_is_dir(const char *path) { struct FF_STAT st; return (ff_stat(path, &st) == 0) && (st.st_mode & FF_IFDIR); #else - mg_stat_t st; - return mg_stat(path, &st) == 0 && S_ISDIR(st.st_mode); + struct stat st; + return stat(path, &st) == 0 && S_ISDIR(st.st_mode); #endif } @@ -1132,7 +1125,7 @@ struct dirent *readdir(DIR *d) { #endif static void printdirentry(struct mg_connection *c, const char *name, - mg_stat_t *stp) { + struct stat *stp) { char size[64], mod[64], path[MG_PATH_MAX]; int is_dir = S_ISDIR(stp->st_mode), n = 0; const char *slash = is_dir ? "/" : ""; @@ -1213,14 +1206,14 @@ static void listdir(struct mg_connection *c, struct mg_http_message *hm, (int) hm->uri.len, hm->uri.ptr); while ((dp = readdir(dirp)) != NULL) { - mg_stat_t st; + struct stat st; const char *sep = dp->d_name[0] == MG_DIRSEP ? "/" : ""; // Do not show current dir and hidden files if (!strcmp(dp->d_name, ".") || !strcmp(dp->d_name, "..")) continue; // SPIFFS can report "/foo.txt" in the dp->d_name if (snprintf(path, sizeof(path), "%s%s%s", dir, sep, dp->d_name) < 0) { LOG(LL_ERROR, ("%s truncated", dp->d_name)); - } else if (mg_stat(path, &st) != 0) { + } else if (stat(path, &st) != 0) { LOG(LL_ERROR, ("%lu stat(%s): %d", c->id, path, errno)); } else { printdirentry(c, dp->d_name, &st); diff --git a/mongoose.h b/mongoose.h index 34e2dd55..25b3a450 100644 --- a/mongoose.h +++ b/mongoose.h @@ -314,7 +314,8 @@ struct timeval { #if MG_ARCH == MG_ARCH_UNIX -#define _DARWIN_UNLIMITED_SELECT 1 +#define _DARWIN_UNLIMITED_SELECT 1 // No limit on file descriptors +#define _GNU_SOURCE // For fopencookie() on Linux #include #include @@ -415,6 +416,16 @@ typedef int socklen_t; #endif #define realpath(a, b) _fullpath((b), (a), MG_PATH_MAX) #define fopen(a, b) mg_fopen((a), (b)) + +// Later windows define _stati64 macro, older do not +#ifdef _stati64 +#define stat _stat64 +#define _stat64(a, b) mg_stat((a), (b)) +#else +#define stat _stati64 +#define _stati64(a, b) mg_stat((a), (b)) +#endif + #ifndef va_copy #ifdef __va_copy #define va_copy __va_copy @@ -429,12 +440,18 @@ typedef int socklen_t; #define MG_INT64_FMT "%I64d" static __inline FILE *mg_fopen(const char *path, const char *mode) { - wchar_t b1[PATH_MAX], b2[10]; + wchar_t b1[MAX_PATH], b2[10]; MultiByteToWideChar(CP_UTF8, 0, path, -1, b1, sizeof(b1) / sizeof(b1[0])); MultiByteToWideChar(CP_UTF8, 0, mode, -1, b2, sizeof(b2) / sizeof(b2[0])); return _wfopen(b1, b2); } +static __inline int mg_stat(const char *path, struct stat *st) { + wchar_t tmp[MAX_PATH]; + MultiByteToWideChar(CP_UTF8, 0, path, -1, tmp, sizeof(tmp) / sizeof(tmp[0])); + return _wstati64(tmp, st); +} + // https://lgtm.com/rules/2154840805/ -gmtime, localtime, ctime and asctime static __inline struct tm *gmtime_r(time_t *t, struct tm *tm) { (void) tm; @@ -589,12 +606,7 @@ void mg_usleep(unsigned long usecs); -#ifdef _WIN32 -typedef struct _stati64 mg_stat_t; -#else -typedef struct stat mg_stat_t; -#endif -int mg_stat(const char *path, mg_stat_t *); +FILE *fopen_packed(const char *path, const char *mode); diff --git a/src/arch_unix.h b/src/arch_unix.h index 806ba325..a65892ff 100644 --- a/src/arch_unix.h +++ b/src/arch_unix.h @@ -2,7 +2,8 @@ #if MG_ARCH == MG_ARCH_UNIX -#define _DARWIN_UNLIMITED_SELECT 1 +#define _DARWIN_UNLIMITED_SELECT 1 // No limit on file descriptors +#define _GNU_SOURCE // For fopencookie() on Linux #include #include diff --git a/src/arch_win32.h b/src/arch_win32.h index f7df817a..1926f2ca 100644 --- a/src/arch_win32.h +++ b/src/arch_win32.h @@ -68,6 +68,16 @@ typedef int socklen_t; #endif #define realpath(a, b) _fullpath((b), (a), MG_PATH_MAX) #define fopen(a, b) mg_fopen((a), (b)) + +// Later windows define _stati64 macro, older do not +#ifdef _stati64 +#define stat _stat64 +#define _stat64(a, b) mg_stat((a), (b)) +#else +#define stat _stati64 +#define _stati64(a, b) mg_stat((a), (b)) +#endif + #ifndef va_copy #ifdef __va_copy #define va_copy __va_copy @@ -82,12 +92,18 @@ typedef int socklen_t; #define MG_INT64_FMT "%I64d" static __inline FILE *mg_fopen(const char *path, const char *mode) { - wchar_t b1[PATH_MAX], b2[10]; + wchar_t b1[MAX_PATH], b2[10]; MultiByteToWideChar(CP_UTF8, 0, path, -1, b1, sizeof(b1) / sizeof(b1[0])); MultiByteToWideChar(CP_UTF8, 0, mode, -1, b2, sizeof(b2) / sizeof(b2[0])); return _wfopen(b1, b2); } +static __inline int mg_stat(const char *path, struct stat *st) { + wchar_t tmp[MAX_PATH]; + MultiByteToWideChar(CP_UTF8, 0, path, -1, tmp, sizeof(tmp) / sizeof(tmp[0])); + return _wstati64(tmp, st); +} + // https://lgtm.com/rules/2154840805/ -gmtime, localtime, ctime and asctime static __inline struct tm *gmtime_r(time_t *t, struct tm *tm) { (void) tm; diff --git a/src/fs.c b/src/fs.c index 16b9f26c..fe0122fb 100644 --- a/src/fs.c +++ b/src/fs.c @@ -1,11 +1,4 @@ #include "fs.h" -int mg_stat(const char *path, mg_stat_t *st) { -#ifdef _WIN32 - wchar_t tmp[MG_PATH_MAX]; - MultiByteToWideChar(CP_UTF8, 0, path, -1, tmp, sizeof(tmp) / sizeof(tmp[0])); - return _wstati64(tmp, st); -#else - return stat(path, st); -#endif -} +// FILE *fopen_packed(const char *path, const char *mode) { +//} diff --git a/src/fs.h b/src/fs.h index 98d8c916..71e2a8ab 100644 --- a/src/fs.h +++ b/src/fs.h @@ -2,9 +2,4 @@ #include "arch.h" -#ifdef _WIN32 -typedef struct _stati64 mg_stat_t; -#else -typedef struct stat mg_stat_t; -#endif -int mg_stat(const char *path, mg_stat_t *); +FILE *fopen_packed(const char *path, const char *mode); diff --git a/src/http.c b/src/http.c index ee97ea22..a6d1586e 100644 --- a/src/http.c +++ b/src/http.c @@ -371,7 +371,7 @@ static void restore_http_cb(struct mg_connection *c) { c->pfn = http_cb; } -char *mg_http_etag(char *buf, size_t len, mg_stat_t *st) { +char *mg_http_etag(char *buf, size_t len, struct stat *st) { snprintf(buf, len, "\"%lx." MG_INT64_FMT "\"", (unsigned long) st->st_mtime, (int64_t) st->st_size); return buf; @@ -512,10 +512,10 @@ static int getrange(struct mg_str *s, int64_t *a, int64_t *b) { void mg_http_serve_file(struct mg_connection *c, struct mg_http_message *hm, const char *path, const char *mime, const char *hdrs) { struct mg_str *inm = mg_http_get_header(hm, "If-None-Match"); - mg_stat_t st; + struct stat st; char etag[64]; FILE *fp = fopen(path, "rb"); - if (fp == NULL || mg_stat(path, &st) != 0 || + if (fp == NULL || stat(path, &st) != 0 || mg_http_etag(etag, sizeof(etag), &st) != etag) { LOG(LL_DEBUG, ("404 [%.*s] [%s] %p", (int) hm->uri.len, hm->uri.ptr, path, (void *) fp)); @@ -589,8 +589,8 @@ bool mg_is_dir(const char *path) { struct FF_STAT st; return (ff_stat(path, &st) == 0) && (st.st_mode & FF_IFDIR); #else - mg_stat_t st; - return mg_stat(path, &st) == 0 && S_ISDIR(st.st_mode); + struct stat st; + return stat(path, &st) == 0 && S_ISDIR(st.st_mode); #endif } @@ -706,7 +706,7 @@ struct dirent *readdir(DIR *d) { #endif static void printdirentry(struct mg_connection *c, const char *name, - mg_stat_t *stp) { + struct stat *stp) { char size[64], mod[64], path[MG_PATH_MAX]; int is_dir = S_ISDIR(stp->st_mode), n = 0; const char *slash = is_dir ? "/" : ""; @@ -787,14 +787,14 @@ static void listdir(struct mg_connection *c, struct mg_http_message *hm, (int) hm->uri.len, hm->uri.ptr); while ((dp = readdir(dirp)) != NULL) { - mg_stat_t st; + struct stat st; const char *sep = dp->d_name[0] == MG_DIRSEP ? "/" : ""; // Do not show current dir and hidden files if (!strcmp(dp->d_name, ".") || !strcmp(dp->d_name, "..")) continue; // SPIFFS can report "/foo.txt" in the dp->d_name if (snprintf(path, sizeof(path), "%s%s%s", dir, sep, dp->d_name) < 0) { LOG(LL_ERROR, ("%s truncated", dp->d_name)); - } else if (mg_stat(path, &st) != 0) { + } else if (stat(path, &st) != 0) { LOG(LL_ERROR, ("%lu stat(%s): %d", c->id, path, errno)); } else { printdirentry(c, dp->d_name, &st); diff --git a/test/unit_test.c b/test/unit_test.c index 6f3604b4..efdd5f2f 100644 --- a/test/unit_test.c +++ b/test/unit_test.c @@ -473,7 +473,6 @@ static void test_http_server(void) { struct mg_mgr mgr; const char *url = "http://127.0.0.1:12346"; char buf[FETCH_BUF_SIZE]; - mg_stat_t st; mg_mgr_init(&mgr); mg_http_listen(&mgr, url, eh1, NULL); @@ -493,9 +492,10 @@ static void test_http_server(void) { ASSERT(cmpbody(buf, "є\n") == 0); { - extern char *mg_http_etag(char *, size_t, mg_stat_t *); + extern char *mg_http_etag(char *, size_t, struct stat *); + struct stat st; char etag[100]; - ASSERT(mg_stat("./test/data/a.txt", &st) == 0); + ASSERT(stat("./test/data/a.txt", &st) == 0); ASSERT(mg_http_etag(etag, sizeof(etag), &st) == etag); ASSERT(fetch(&mgr, buf, url, "GET /a.txt HTTP/1.0\nIf-None-Match: %s\n\n", etag) == 304);