Add xdg_app_mkstempat

This is like g_mkstemp except it uses openat
tingping/wmclass
Alexander Larsson 2015-09-03 22:14:37 +02:00
parent 4a298aeec3
commit c0e480df94
2 changed files with 70 additions and 0 deletions

View File

@ -677,3 +677,68 @@ ostree_repo_load_summary (const char *repository_url,
out:
return ret;
}
/* Based on g_mkstemp from glib */
gint
xdg_app_mkstempat (int dir_fd,
gchar *tmpl,
int flags,
int mode)
{
char *XXXXXX;
int count, fd;
static const char letters[] =
"ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
static const int NLETTERS = sizeof (letters) - 1;
glong value;
GTimeVal tv;
static int counter = 0;
g_return_val_if_fail (tmpl != NULL, -1);
/* find the last occurrence of "XXXXXX" */
XXXXXX = g_strrstr (tmpl, "XXXXXX");
if (!XXXXXX || strncmp (XXXXXX, "XXXXXX", 6))
{
errno = EINVAL;
return -1;
}
/* Get some more or less random data. */
g_get_current_time (&tv);
value = (tv.tv_usec ^ tv.tv_sec) + counter++;
for (count = 0; count < 100; value += 7777, ++count)
{
glong v = value;
/* Fill in the random bits. */
XXXXXX[0] = letters[v % NLETTERS];
v /= NLETTERS;
XXXXXX[1] = letters[v % NLETTERS];
v /= NLETTERS;
XXXXXX[2] = letters[v % NLETTERS];
v /= NLETTERS;
XXXXXX[3] = letters[v % NLETTERS];
v /= NLETTERS;
XXXXXX[4] = letters[v % NLETTERS];
v /= NLETTERS;
XXXXXX[5] = letters[v % NLETTERS];
fd = openat (dir_fd, tmpl, flags | O_CREAT | O_EXCL, mode);
if (fd >= 0)
return fd;
else if (errno != EEXIST)
/* Any other error will apply also to other names we might
* try, and there are 2^32 or so of them, so give up now.
*/
return -1;
}
/* We got out of the loop because we ran out of combinations to try. */
errno = EEXIST;
return -1;
}

View File

@ -124,6 +124,11 @@ static inline GMutex *xdg_app_auto_lock_helper (GMutex *mutex)
return mutex;
}
gint xdg_app_mkstempat (int dir_fd,
gchar *tmpl,
int flags,
int mode);
#define AUTOLOCK(name) G_GNUC_UNUSED __attribute__((cleanup(xdg_app_auto_unlock_helper))) GMutex * G_PASTE(auto_unlock, __LINE__) = xdg_app_auto_lock_helper (&G_LOCK_NAME (name))