1 1.15 maya /* $NetBSD: mount_udf.c,v 1.15 2019/10/16 21:52:22 maya Exp $ */ 2 1.1 reinoud 3 1.1 reinoud /* 4 1.1 reinoud * Copyright (c) 2006 Reinoud Zandijk 5 1.1 reinoud * All rights reserved. 6 1.1 reinoud * 7 1.1 reinoud * Redistribution and use in source and binary forms, with or without 8 1.1 reinoud * modification, are permitted provided that the following conditions 9 1.1 reinoud * are met: 10 1.1 reinoud * 1. Redistributions of source code must retain the above copyright 11 1.1 reinoud * notice, this list of conditions and the following disclaimer. 12 1.1 reinoud * 2. Redistributions in binary form must reproduce the above copyright 13 1.1 reinoud * notice, this list of conditions and the following disclaimer in the 14 1.1 reinoud * documentation and/or other materials provided with the distribution. 15 1.1 reinoud * 16 1.1 reinoud * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 17 1.1 reinoud * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 18 1.1 reinoud * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 19 1.1 reinoud * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 20 1.1 reinoud * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 21 1.1 reinoud * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22 1.1 reinoud * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23 1.1 reinoud * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24 1.1 reinoud * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 25 1.1 reinoud * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 1.1 reinoud * 27 1.1 reinoud */ 28 1.1 reinoud 29 1.1 reinoud 30 1.1 reinoud #include <sys/cdefs.h> 31 1.1 reinoud #ifndef lint 32 1.15 maya __RCSID("$NetBSD: mount_udf.c,v 1.15 2019/10/16 21:52:22 maya Exp $"); 33 1.1 reinoud #endif /* not lint */ 34 1.1 reinoud 35 1.1 reinoud 36 1.1 reinoud #include <sys/param.h> 37 1.1 reinoud #include <sys/mount.h> 38 1.1 reinoud #include <sys/stat.h> 39 1.8 hubertf 40 1.8 hubertf #include <assert.h> 41 1.1 reinoud #include <err.h> 42 1.8 hubertf #include <errno.h> 43 1.1 reinoud #include <grp.h> 44 1.1 reinoud #include <pwd.h> 45 1.1 reinoud #include <stdio.h> 46 1.1 reinoud #include <stdlib.h> 47 1.1 reinoud #include <string.h> 48 1.1 reinoud #include <time.h> 49 1.1 reinoud #include <unistd.h> 50 1.1 reinoud #include <util.h> 51 1.1 reinoud 52 1.1 reinoud 53 1.1 reinoud /* mount specific options */ 54 1.1 reinoud #include <fs/udf/udf_mount.h> 55 1.1 reinoud #include <mntopts.h> 56 1.1 reinoud 57 1.12 pooka #include "mountprog.h" 58 1.12 pooka #include "mount_udf.h" 59 1.1 reinoud 60 1.1 reinoud /* options to pass on to the `mount' call */ 61 1.1 reinoud static const struct mntopt mopts[] = { 62 1.7 reinoud MOPT_STDOPTS, /* `normal' options */ 63 1.7 reinoud MOPT_ASYNC, /* default */ 64 1.7 reinoud MOPT_NOATIME, /* dont update access times */ 65 1.14 christos MOPT_RELATIME, /* update access times on change*/ 66 1.7 reinoud MOPT_UPDATE, /* not yet supported */ 67 1.7 reinoud MOPT_GETARGS, /* printing */ 68 1.6 christos MOPT_NULL, 69 1.1 reinoud }; 70 1.1 reinoud 71 1.1 reinoud 72 1.1 reinoud /* prototypes */ 73 1.11 perry static void usage(void) __dead; 74 1.1 reinoud 75 1.1 reinoud 76 1.1 reinoud /* code */ 77 1.1 reinoud 78 1.1 reinoud static void 79 1.4 christos usage(void) 80 1.1 reinoud { 81 1.4 christos (void)fprintf(stderr, "Usage: %s [-g gid] [-o options] [-s session] " 82 1.4 christos "[-t gmtoff] [-u uid] special node\n", getprogname()); 83 1.1 reinoud exit(EXIT_FAILURE); 84 1.1 reinoud } 85 1.1 reinoud 86 1.1 reinoud 87 1.1 reinoud #ifndef MOUNT_NOMAIN 88 1.1 reinoud int 89 1.1 reinoud main(int argc, char **argv) 90 1.1 reinoud { 91 1.12 pooka 92 1.12 pooka setprogname(argv[0]); 93 1.1 reinoud return mount_udf(argc, argv); 94 1.1 reinoud } 95 1.1 reinoud #endif 96 1.1 reinoud 97 1.1 reinoud 98 1.1 reinoud /* main routine */ 99 1.12 pooka void 100 1.12 pooka mount_udf_parseargs(int argc, char **argv, 101 1.12 pooka struct udf_args *args, int *mntflags, 102 1.12 pooka char *canon_dev, char *canon_dir) 103 1.1 reinoud { 104 1.1 reinoud struct tm *tm; 105 1.1 reinoud time_t now; 106 1.1 reinoud uid_t anon_uid, nobody_uid; 107 1.1 reinoud gid_t anon_gid, nobody_gid; 108 1.12 pooka int ch, set_gmtoff; 109 1.1 reinoud uint32_t sector_size; 110 1.5 christos mntoptparse_t mp; 111 1.1 reinoud 112 1.1 reinoud /* initialise */ 113 1.12 pooka (void)memset(args, 0, sizeof(*args)); 114 1.1 reinoud 115 1.12 pooka set_gmtoff = *mntflags = 0; 116 1.1 reinoud sector_size = 0; 117 1.1 reinoud 118 1.1 reinoud /* get nobody */ 119 1.4 christos nobody_uid = anon_uid = a_uid("nobody"); 120 1.4 christos nobody_gid = anon_gid = a_gid("nobody"); 121 1.1 reinoud 122 1.1 reinoud /* NEVER EVER allow nobody_uid:nobody_gid to be 0:0 */ 123 1.1 reinoud assert(nobody_uid != 0); 124 1.1 reinoud assert(nobody_gid != 0); 125 1.1 reinoud 126 1.1 reinoud while ((ch = getopt(argc, argv, "cg:o:s:t:u:")) != -1) { 127 1.1 reinoud switch (ch) { 128 1.1 reinoud case 'c' : 129 1.12 pooka args->udfmflags |= UDFMNT_CLOSESESSION; 130 1.1 reinoud break; 131 1.1 reinoud case 'g' : 132 1.1 reinoud /* convert groupname or numeric equiv. */ 133 1.4 christos anon_gid = a_gid(optarg); 134 1.1 reinoud break; 135 1.1 reinoud case 'u' : 136 1.1 reinoud /* convert username or numeric equiv. */ 137 1.4 christos anon_uid = a_uid(optarg); 138 1.1 reinoud break; 139 1.1 reinoud case 'o' : 140 1.1 reinoud /* process generic mount options */ 141 1.12 pooka mp = getmntopts(optarg, mopts, mntflags, 0); 142 1.5 christos if (mp == NULL) 143 1.5 christos err(EXIT_FAILURE, "getmntopts"); 144 1.5 christos freemntopts(mp); 145 1.1 reinoud break; 146 1.1 reinoud case 's' : 147 1.12 pooka args->sessionnr = a_num(optarg, "session number"); 148 1.1 reinoud break; 149 1.1 reinoud case 't' : 150 1.12 pooka args->gmtoff = a_num(optarg, "gmtoff"); 151 1.1 reinoud set_gmtoff = 1; 152 1.1 reinoud break; 153 1.1 reinoud default : 154 1.1 reinoud usage(); 155 1.3 xtraeme /* NOTREACHED */ 156 1.3 xtraeme } 157 1.3 xtraeme } 158 1.1 reinoud 159 1.1 reinoud if (optind + 2 != argc) 160 1.1 reinoud usage(); 161 1.1 reinoud 162 1.1 reinoud if (!set_gmtoff) { 163 1.1 reinoud /* use user's time zone as default */ 164 1.4 christos (void)time(&now); 165 1.1 reinoud tm = localtime(&now); 166 1.12 pooka args->gmtoff = tm->tm_gmtoff; 167 1.1 reinoud } 168 1.1 reinoud 169 1.1 reinoud /* get device and directory specifier */ 170 1.12 pooka pathadj(argv[optind], canon_dev); 171 1.12 pooka pathadj(argv[optind+1], canon_dir); 172 1.12 pooka 173 1.12 pooka args->version = UDFMNT_VERSION; 174 1.12 pooka args->fspec = canon_dev; 175 1.12 pooka args->anon_uid = anon_uid; 176 1.12 pooka args->anon_gid = anon_gid; 177 1.12 pooka args->nobody_uid = nobody_uid; 178 1.12 pooka args->nobody_gid = nobody_gid; 179 1.12 pooka args->sector_size = sector_size; /* invalid */ 180 1.12 pooka } 181 1.12 pooka 182 1.12 pooka int 183 1.12 pooka mount_udf(int argc, char *argv[]) 184 1.12 pooka { 185 1.12 pooka struct udf_args args; 186 1.12 pooka char canon_dev[MAXPATHLEN], canon_dir[MAXPATHLEN]; 187 1.12 pooka int mntflags; 188 1.4 christos 189 1.12 pooka mount_udf_parseargs(argc, argv, &args, &mntflags, canon_dev, canon_dir); 190 1.1 reinoud 191 1.1 reinoud /* mount it! :) */ 192 1.12 pooka if (mount(MOUNT_UDF, canon_dir, mntflags, &args, sizeof args) == -1) 193 1.12 pooka err(EXIT_FAILURE, "Cannot mount %s on %s", canon_dev,canon_dir); 194 1.1 reinoud 195 1.1 reinoud if (mntflags & MNT_GETARGS) { 196 1.1 reinoud char buf[1024]; 197 1.1 reinoud 198 1.4 christos (void)snprintb(buf, sizeof(buf), UDFMNT_BITS, 199 1.4 christos (uint64_t)args.udfmflags); 200 1.4 christos (void)printf("gmtoffset=%d, sessionnr=%d, flags=%s\n", 201 1.4 christos args.gmtoff, args.sessionnr, buf); 202 1.1 reinoud } 203 1.1 reinoud 204 1.4 christos return EXIT_SUCCESS; 205 1.1 reinoud } 206