1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27#define FOR_mktemp
28#include "toys.h"
29
30GLOBALS(
31 char *p, *tmpdir;
32)
33
34void mktemp_main(void)
35{
36 char *template = *toys.optargs, *dir, *te = getenv("TMPDIR");
37 int len;
38
39
40 if (!TT.p && FLAG(tmpdir)) {
41 TT.p = TT.tmpdir ? TT.tmpdir : "";
42 toys.optflags |= FLAG_p;
43 }
44 dir = TT.p;
45
46 if (!dir || !*dir || (FLAG(t) && te && *te)) dir = te;
47 if (!dir || !*dir) dir = "/tmp";
48 if (!template) template = "tmp.XXXXXXXXXX";
49 else {
50 if (*template == '/' && TT.p && *TT.p) perror_exit("-p + /template");
51 if (!FLAG(p)&&!FLAG(t)) dir = 0;
52 }
53
54
55 template = dir ? xmprintf("%s/%s", dir, template) : xstrdup(template);
56 len = strlen(template);
57 if (len<3 || strcmp(template+len-3, "XXX")) perror_exit("need XXX");
58
59
60
61 if (FLAG(u)) {
62 long long rr;
63 char *s = template+len;
64
65
66 if (!xgetrandom(&rr, sizeof(rr), WARN_ONLY)) {
67 struct timespec ts;
68
69 clock_gettime(CLOCK_REALTIME, &ts);
70 rr = ts.tv_nsec*65537+(long)template+getpid()+(long)&template;
71 }
72
73 while (--s>template) {
74 if (*s != 'X') break;
75 *s = '-'+(rr&63);
76 if (*s>'.') ++*s;
77 if (*s>'9') (*s) += 7;
78 if (*s>'Z') (*s) += 6;
79 rr>>=6;
80 }
81 } else if (FLAG(d) ? !mkdtemp(template) : mkstemp(template) == -1) {
82 if (FLAG(q)) {
83 toys.exitval = 1;
84 return;
85 } else perror_exit("Failed to create %s %s",
86 FLAG(d) ? "directory" : "file", template);
87 }
88
89 xputs(template);
90 if (CFG_TOYBOX_FREE) free(template);
91}
92