#include <stdio.h>
+#include <stdint.h>
#include <string.h>
#include <stdlib.h>
+#include <errno.h>
#include <sys/stat.h>
static void writes(const char *p)
write(2, p, strlen(p));
}
-static long parse_number(const char *p, int base)
-{
- char *end;
- unsigned long result;
-
- errno = 0;
- result = strtoul(p, &end, base);
- if (errno || *end)
- return -1;
- return result;
-}
-
-int do_mknod(char *path, char *modes, char *devs)
+int main(int argc, char *argv[])
{
- int mode;
- int dev;
-
- mode = parse_number(modes, 8);
- if (mode < 0) {
- writes("mknod: bad mode\n");
- return 1;
- }
-
- if (!S_ISFIFO(mode) && !S_ISDEV(mode)) {
- writes("mknod: mode is not device/fifo\n");
- return 1;
+ uint16_t mode;
+ uint16_t dev;
+
+ if (argc !=3 && argc != 5)
+ goto usage;
+
+ if (argv[2][1])
+ goto badtype;
+ switch (*argv[2]) {
+ case 'b':
+ mode = S_IFBLK|0777;
+ break;
+ case 'c':
+ mode = S_IFCHR|0777;
+ break;
+ case 'p':
+ mode = S_IFIFO|0777;
+ break;
+ default:
+ goto badtype;
}
- dev = parse_number(devs, 10);
- if (dev < 0) {
- writes("mknod: bad device\n");
- return 1;
- }
-
- if (mknod(path, mode, dev) != 0) {
- perror("mknod");
- return 1;
- }
- return (0);
-}
-
-int main(int argc, char *argv[])
-{
- if (argc != 4) {
- writes("usage: mknod path modes devs\n");
+ if (*argv[2] != 'p') {
+ if (argc != 5)
+ goto usage;
+ errno = 0;
+ dev = atoi(argv[3]) << 8;
+ dev |= atoi(argv[4]);
+ if (errno)
+ goto usage;
+ } else if (argc != 3)
+ goto usage;
+
+ if (mknod(argv[1], mode, dev) != 0) {
+ perror(argv[1]);
return 1;
}
- return do_mknod(argv[1], argv[2], argv[3]);
+ return 0;
+
+badtype:
+ writes("mknod: invalid type (must be b c or p)\n");
+ return 1;
+usage:
+ writes("usage: mknod path type {major minor}\n");
+ return 1;
}