1/* See LICENSE file for copyright and license details. */
2#include <sys/stat.h>
3#include <sys/types.h>
4
5#include <stdio.h>
6#include <stdlib.h>
7#include <string.h>
8#include <unistd.h>
9
10#include "util.h"
11
12#ifndef makedev
13#include <sys/sysmacros.h>
14#endif
15
16static void
17usage(void)
18{
19 eprintf(
20 "usage: %s [-m mode] name b|c|u major minor\n"
21 " %s [-m mode] name p\n",
22 argv0,
23 argv0
24 );
25}
26
27// ?man mknod: create special files
28// ?man arguments: name type [major minor]
29// ?man create a block special, character special, or fifo file
30int
31main(int argc, char *argv[])
32{
33 mode_t mode = 0666;
34 dev_t dev;
35
36 ARGBEGIN
37 {
38 case 'm':
39 // ?man -m:mode: set the file mode bits of the created node
40 mode = parsemode(EARGF(usage()), mode, umask(0));
41 break;
42 default:
43 usage();
44 }
45 ARGEND
46
47 if (argc < 2)
48 usage();
49
50 if (strlen(argv[1]) != 1)
51 goto invalid;
52 switch (argv[1][0]) {
53 case 'b':
54 mode |= S_IFBLK;
55 break;
56 case 'u':
57 case 'c':
58 mode |= S_IFCHR;
59 break;
60 case 'p':
61 mode |= S_IFIFO;
62 break;
63 default:
64 invalid:
65 eprintf("invalid type '%s'\n", argv[1]);
66 }
67
68 if (S_ISFIFO(mode)) {
69 if (argc != 2)
70 usage();
71 dev = 0;
72 } else {
73 if (argc != 4)
74 usage();
75 dev = makedev(estrtonum(argv[2], 0, LLONG_MAX), estrtonum(argv[3], 0, LLONG_MAX));
76 }
77
78 if (mknod(argv[0], mode, dev) == -1)
79 eprintf("mknod %s:", argv[0]);
80 return 0;
81}