The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/contrib/openzfs/tests/zfs-tests/cmd/mkbusy.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /*
    2  * This file and its contents are supplied under the terms of the
    3  * Common Development and Distribution License ("CDDL"), version 1.0.
    4  * You may only use this file in accordance with the terms of version
    5  * 1.0 of the CDDL.
    6  *
    7  * A full copy of the text of the CDDL should have accompanied this
    8  * source.  A copy of the CDDL is also available via the Internet at
    9  * http://www.illumos.org/license/CDDL.
   10  */
   11 
   12 /*
   13  * Copyright (c) 2012 by Delphix. All rights reserved.
   14  */
   15 
   16 /*
   17  * Make a directory busy. If the argument is an existing file or directory,
   18  * simply open it directly and pause. If not, verify that the parent directory
   19  * exists, and create a new file in that directory.
   20  */
   21 
   22 #include <stdio.h>
   23 #include <sys/types.h>
   24 #include <sys/stat.h>
   25 #include <fcntl.h>
   26 #include <dirent.h>
   27 #include <string.h>
   28 #include <stdlib.h>
   29 #include <unistd.h>
   30 #include <errno.h>
   31 #include <string.h>
   32 
   33 
   34 static __attribute__((noreturn)) void
   35 usage(const char *progname)
   36 {
   37         (void) fprintf(stderr, "Usage: %s <dirname|filename>\n", progname);
   38         exit(1);
   39 }
   40 
   41 static __attribute__((noreturn)) void
   42 fail(const char *err)
   43 {
   44         perror(err);
   45         exit(1);
   46 }
   47 
   48 static void
   49 daemonize(void)
   50 {
   51         pid_t   pid;
   52 
   53         if ((pid = fork()) < 0) {
   54                 fail("fork");
   55         } else if (pid != 0) {
   56                 (void) fprintf(stdout, "%ld\n", (long)pid);
   57                 exit(0);
   58         }
   59 
   60         (void) setsid();
   61         (void) close(0);
   62         (void) close(1);
   63         (void) close(2);
   64 }
   65 
   66 
   67 static const char *
   68 get_basename(const char *path)
   69 {
   70         const char *bn = strrchr(path, '/');
   71         return (bn ? bn + 1 : path);
   72 }
   73 
   74 static ssize_t
   75 get_dirnamelen(const char *path)
   76 {
   77         const char *end = strrchr(path, '/');
   78         return (end ? end - path : -1);
   79 }
   80 
   81 int
   82 main(int argc, char *argv[])
   83 {
   84         int             c;
   85         boolean_t       isdir = B_FALSE;
   86         struct stat     sbuf;
   87         char            *fpath = NULL;
   88         char            *prog = argv[0];
   89 
   90         while ((c = getopt(argc, argv, "")) != -1) {
   91                 switch (c) {
   92                 default:
   93                         usage(prog);
   94                 }
   95         }
   96 
   97         argc -= optind;
   98         argv += optind;
   99 
  100         if (argc != 1)
  101                 usage(prog);
  102 
  103         if (stat(argv[0], &sbuf) != 0) {
  104                 char    *arg;
  105                 const char      *dname, *fname;
  106                 size_t  arglen;
  107                 ssize_t dnamelen;
  108 
  109                 /*
  110                  * The argument supplied doesn't exist. Copy the path, and
  111                  * remove the trailing slash if present.
  112                  */
  113                 if ((arg = strdup(argv[0])) == NULL)
  114                         fail("strdup");
  115                 arglen = strlen(arg);
  116                 if (arg[arglen - 1] == '/')
  117                         arg[arglen - 1] = '\0';
  118 
  119                 /* Get the directory and file names. */
  120                 fname = get_basename(arg);
  121                 dname = arg;
  122                 if ((dnamelen = get_dirnamelen(arg)) != -1)
  123                         arg[dnamelen] = '\0';
  124                 else
  125                         dname = ".";
  126 
  127                 /* The directory portion of the path must exist */
  128                 if (stat(dname, &sbuf) != 0 || !(sbuf.st_mode & S_IFDIR))
  129                         usage(prog);
  130 
  131                 if (asprintf(&fpath, "%s/%s", dname, fname) == -1)
  132                         fail("asprintf");
  133 
  134                 free(arg);
  135         } else
  136                 switch (sbuf.st_mode & S_IFMT) {
  137                         case S_IFDIR:
  138                                 isdir = B_TRUE;
  139                                 zfs_fallthrough;
  140                         case S_IFLNK:
  141                         case S_IFCHR:
  142                         case S_IFBLK:
  143                                 if ((fpath = strdup(argv[0])) == NULL)
  144                                         fail("strdup");
  145                                 break;
  146                         default:
  147                                 usage(prog);
  148                 }
  149 
  150         if (!isdir) {
  151                 if (open(fpath, O_CREAT | O_RDWR, 0600) < 0)
  152                         fail("open");
  153         } else {
  154                 if (opendir(fpath) == NULL)
  155                         fail("opendir");
  156         }
  157         free(fpath);
  158 
  159         daemonize();
  160         (void) pause();
  161 
  162         return (0);
  163 }

Cache object: 620f957b542810ba9e5287ba608e4d45


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.