summaryrefslogtreecommitdiff
path: root/src/temp
diff options
context:
space:
mode:
authorVladimir Azarov <avm@intermediate-node.net>2024-10-01 15:47:05 +0200
committerVladimir Azarov <avm@intermediate-node.net>2024-10-01 15:47:05 +0200
commit4abab5ad6c8465a7528ccdd5f49367da05f78bbd (patch)
treeebf009bf1376a5a223a915bc27cbbd791a1316bc /src/temp
Initial version
Diffstat (limited to 'src/temp')
-rw-r--r--src/temp/__randname.c19
-rw-r--r--src/temp/mkdtemp.c23
-rw-r--r--src/temp/mkostemp.c7
-rw-r--r--src/temp/mkostemps.c28
-rw-r--r--src/temp/mkstemp.c6
-rw-r--r--src/temp/mkstemps.c7
-rw-r--r--src/temp/mktemp.c30
7 files changed, 120 insertions, 0 deletions
diff --git a/src/temp/__randname.c b/src/temp/__randname.c
new file mode 100644
index 0000000..e9b970f
--- /dev/null
+++ b/src/temp/__randname.c
@@ -0,0 +1,19 @@
+#include <time.h>
+#include <stdint.h>
+#include "pthread_impl.h"
+
+/* This assumes that a check for the
+ template size has already been made */
+char *__randname(char *template)
+{
+ int i;
+ struct timespec ts;
+ unsigned long r;
+
+ __clock_gettime(CLOCK_REALTIME, &ts);
+ r = ts.tv_sec + ts.tv_nsec + __pthread_self()->tid * 65537UL;
+ for (i=0; i<6; i++, r>>=5)
+ template[i] = 'A'+(r&15)+(r&16)*2;
+
+ return template;
+}
diff --git a/src/temp/mkdtemp.c b/src/temp/mkdtemp.c
new file mode 100644
index 0000000..5708257
--- /dev/null
+++ b/src/temp/mkdtemp.c
@@ -0,0 +1,23 @@
+#include <string.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <sys/stat.h>
+
+char *mkdtemp(char *template)
+{
+ size_t l = strlen(template);
+ int retries = 100;
+
+ if (l<6 || memcmp(template+l-6, "XXXXXX", 6)) {
+ errno = EINVAL;
+ return 0;
+ }
+
+ do {
+ __randname(template+l-6);
+ if (!mkdir(template, 0700)) return template;
+ } while (--retries && errno == EEXIST);
+
+ memcpy(template+l-6, "XXXXXX", 6);
+ return 0;
+}
diff --git a/src/temp/mkostemp.c b/src/temp/mkostemp.c
new file mode 100644
index 0000000..e3dfdd9
--- /dev/null
+++ b/src/temp/mkostemp.c
@@ -0,0 +1,7 @@
+#define _BSD_SOURCE
+#include <stdlib.h>
+
+int mkostemp(char *template, int flags)
+{
+ return __mkostemps(template, 0, flags);
+}
diff --git a/src/temp/mkostemps.c b/src/temp/mkostemps.c
new file mode 100644
index 0000000..093d238
--- /dev/null
+++ b/src/temp/mkostemps.c
@@ -0,0 +1,28 @@
+#define _BSD_SOURCE
+#include <stdlib.h>
+#include <string.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <errno.h>
+
+int __mkostemps(char *template, int len, int flags)
+{
+ size_t l = strlen(template);
+ if (l<6 || len>l-6 || memcmp(template+l-len-6, "XXXXXX", 6)) {
+ errno = EINVAL;
+ return -1;
+ }
+
+ flags -= flags & O_ACCMODE;
+ int fd, retries = 100;
+ do {
+ __randname(template+l-len-6);
+ if ((fd = open(template, flags | O_RDWR | O_CREAT | O_EXCL, 0600))>=0)
+ return fd;
+ } while (--retries && errno == EEXIST);
+
+ memcpy(template+l-len-6, "XXXXXX", 6);
+ return -1;
+}
+
+weak_alias(__mkostemps, mkostemps);
diff --git a/src/temp/mkstemp.c b/src/temp/mkstemp.c
new file mode 100644
index 0000000..76c835b
--- /dev/null
+++ b/src/temp/mkstemp.c
@@ -0,0 +1,6 @@
+#include <stdlib.h>
+
+int mkstemp(char *template)
+{
+ return __mkostemps(template, 0, 0);
+}
diff --git a/src/temp/mkstemps.c b/src/temp/mkstemps.c
new file mode 100644
index 0000000..f8eabfe
--- /dev/null
+++ b/src/temp/mkstemps.c
@@ -0,0 +1,7 @@
+#define _BSD_SOURCE
+#include <stdlib.h>
+
+int mkstemps(char *template, int len)
+{
+ return __mkostemps(template, len, 0);
+}
diff --git a/src/temp/mktemp.c b/src/temp/mktemp.c
new file mode 100644
index 0000000..7b3d264
--- /dev/null
+++ b/src/temp/mktemp.c
@@ -0,0 +1,30 @@
+#define _GNU_SOURCE
+#include <string.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <sys/stat.h>
+
+char *mktemp(char *template)
+{
+ size_t l = strlen(template);
+ int retries = 100;
+ struct stat st;
+
+ if (l < 6 || memcmp(template+l-6, "XXXXXX", 6)) {
+ errno = EINVAL;
+ *template = 0;
+ return template;
+ }
+
+ do {
+ __randname(template+l-6);
+ if (stat(template, &st)) {
+ if (errno != ENOENT) *template = 0;
+ return template;
+ }
+ } while (--retries);
+
+ *template = 0;
+ errno = EEXIST;
+ return template;
+}