From 1c50ffe83f41a6859e7595fd60851cd2b9b8e39b Mon Sep 17 00:00:00 2001 From: Cedric Bail Date: Sun, 31 Mar 2013 00:09:37 +0900 Subject: [PATCH] Evil: add mkdtemp --- ChangeLog | 4 ++ NEWS | 2 + src/lib/evil/evil_stdlib.c | 114 +++++++++++++++++++++++++++---------- src/lib/evil/evil_stdlib.h | 7 +++ 4 files changed, 97 insertions(+), 30 deletions(-) diff --git a/ChangeLog b/ChangeLog index 585c3061a5..d71b13c342 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,7 @@ +2013-03-30 Cedric Bail + + * Evil: Add mkdtemp. + 2013-03-29 Carsten Haitzler (The Rasterman) * Fix edje entry to resepct filter callbacks and not clear diff --git a/NEWS b/NEWS index e9589a3a06..67e6c2a742 100644 --- a/NEWS +++ b/NEWS @@ -86,6 +86,8 @@ Additions: - automatically support Watchdog. * ecore_imf: Add ecore_imf_context_input_panel_layout_variation_set/get API * Add edje_object_part_text_input_panel_layout_variation_set/get API + * Evil: + - Add mkdtemp. Deprecations: * ecore_x: diff --git a/src/lib/evil/evil_stdlib.c b/src/lib/evil/evil_stdlib.c index ffd9acde9a..b7c814ec44 100644 --- a/src/lib/evil/evil_stdlib.c +++ b/src/lib/evil/evil_stdlib.c @@ -7,6 +7,7 @@ #include #include #include +#include #include @@ -269,11 +270,90 @@ unsetenv(const char *name) * Files related functions * */ +static int +_mkstemp_init(char *__template, char **suffix, size_t *length, DWORD *val) +{ + *length = strlen(__template); + if ((*length < 6) || + (strncmp (__template + *length - 6, "XXXXXX", 6))) + { + errno = EINVAL; + return 0; + } + + *suffix = __template + *length - 6; + + *val = GetTickCount(); + *val += GetCurrentProcessId(); + + return 1; +} + +static int +_mkstemp(char *suffix, int val) +{ + const char lookup[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"; + DWORD v = val; + + suffix[0] = lookup[v % 62]; + v /= 62; + suffix[1] = lookup[v % 62]; + v /= 62; + suffix[2] = lookup[v % 62]; + v /= 62; + suffix[3] = lookup[v % 62]; + v /= 62; + suffix[4] = lookup[v % 62]; + v /= 62; + suffix[5] = lookup[v % 62]; + v /= 62; + + val += 7777; + + return v; +} + +EAPI char * +mkdtemp(char *__template) +{ + char *suffix; + DWORD val; + size_t length; + int i; + + if (!__template) + { + errno = EINVAL; + return NULL; + } + + if (!_mkstemp_init(__template, &suffix, &length, &val)) + return NULL; + + for (i = 0; i < 32768; i++) + { + val = _mkstemp(suffix, val); + + if (mkdir(__template)) + return __template; + + if (errno == EFAULT || + errno == ENOSPC || + errno == ENOMEM || + errno == ENOENT || + errno == ENOTDIR || + errno == EPERM || + errno == EROFS) + return NULL; + } + + errno = EEXIST; + return NULL; +} int mkstemp(char *__template) { - const char lookup[] = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"; char *suffix; DWORD val; size_t length; @@ -282,38 +362,14 @@ mkstemp(char *__template) if (!__template) return 0; - length = strlen(__template); - if ((length < 6) || - (strncmp (__template + length - 6, "XXXXXX", 6))) - { - errno = EINVAL; - return -1; - } - - suffix = __template + length - 6; - - val = GetTickCount(); - val += GetCurrentProcessId(); + if (!_mkstemp_init(__template, &suffix, &length, &val)) + return -1; for (i = 0; i < 32768; i++) { - DWORD v; int fd; - v = val; - - suffix[0] = lookup[v % 62]; - v /= 62; - suffix[1] = lookup[v % 62]; - v /= 62; - suffix[2] = lookup[v % 62]; - v /= 62; - suffix[3] = lookup[v % 62]; - v /= 62; - suffix[4] = lookup[v % 62]; - v /= 62; - suffix[5] = lookup[v % 62]; - v /= 62; + val = _mkstemp(suffix, val); #ifndef __MINGW32CE__ fd = _open(__template, _O_RDWR | _O_BINARY | _O_CREAT | _O_EXCL, _S_IREAD | _S_IWRITE); @@ -337,8 +393,6 @@ mkstemp(char *__template) #endif /* __MINGW32CE__ */ if (fd >= 0) return fd; - - val += 7777; } errno = EEXIST; diff --git a/src/lib/evil/evil_stdlib.h b/src/lib/evil/evil_stdlib.h index b102b66f8e..52318dc964 100644 --- a/src/lib/evil/evil_stdlib.h +++ b/src/lib/evil/evil_stdlib.h @@ -159,6 +159,13 @@ EAPI int unsetenv(const char *name); */ EAPI int mkstemp(char *__template); +/** + * @brief create an unique temporary directory + * + * @since 1.8.0 + */ +EAPI char *mkdtemp(char *__template); + /** * @brief Return an absolute or full path name for a specified relative path name. *