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 2013 Nexenta Systems, Inc. All rights reserved. 14 */ 15 16 #include <sys/types.h> 17 #include <sys/param.h> 18 #include <sys/t_lock.h> 19 #include <sys/errno.h> 20 #include <sys/cred.h> 21 #include <sys/user.h> 22 #include <sys/uio.h> 23 #include <sys/file.h> 24 #include <sys/pathname.h> 25 #include <sys/vfs.h> 26 #include <sys/vnode.h> 27 #include <sys/stat.h> 28 #include <sys/mode.h> 29 #include <sys/conf.h> 30 #include <sys/sysmacros.h> 31 #include <sys/cmn_err.h> 32 #include <sys/systm.h> 33 #include <sys/kmem.h> 34 #include <sys/debug.h> 35 #include <sys/acl.h> 36 #include <sys/nbmlock.h> 37 #include <sys/fcntl.h> 38 #include <sys/poll.h> 39 40 #include <errno.h> 41 #include <fcntl.h> 42 #include <unistd.h> 43 44 #include "vncache.h" 45 46 #define VFTBITS(feature) ((feature) & 0xFFFFFFFFLL) 47 48 static uint64_t vfs_features = VFSFT_XVATTR; 49 50 vnode_t *rootdir = NULL; /* pointer to root inode vnode. */ 51 52 static struct vfs fake_rootvfs; 53 struct vfs *rootvfs = NULL; 54 55 int 56 fksmbsrv_vfs_init(void) 57 { 58 struct stat st; 59 int err, fd; 60 vnode_t *vp; 61 char *name = "/"; 62 63 if (rootvfs == NULL) { 64 rootvfs = &fake_rootvfs; 65 rootvfs->vfs_mntpt = refstr_alloc(name); 66 rootvfs->vfs_fsid.val[0] = 1; 67 } 68 69 if (rootdir == NULL) { 70 if (lstat(name, &st) == -1) 71 return (errno); 72 fd = open(name, O_RDONLY, 0); 73 if (fd < 0) { 74 return (errno); 75 } 76 if (fstat(fd, &st) == -1) { 77 err = errno; 78 (void) close(fd); 79 return (err); 80 } 81 vp = vncache_enter(&st, NULL, "", fd); 82 /* extra hold for rootvp */ 83 vn_hold(vp); 84 rootdir = vp; 85 86 /* VFS stuff in global zone struct. */ 87 zone0.zone_rootvp = rootdir; 88 zone0.zone_rootpath = "/"; 89 } 90 91 return (0); 92 93 } 94 95 96 /* 97 * Query a vfs for a feature. 98 * Returns 1 if feature is present, 0 if not 99 */ 100 /* ARGSUSED */ 101 int 102 vfs_has_feature(vfs_t *vfsp, vfs_feature_t feature) 103 { 104 int ret = 0; 105 106 if (vfs_features & VFTBITS(feature)) 107 ret = 1; 108 109 return (ret); 110 } 111 112 /* ARGSUSED */ 113 struct vfs * 114 getvfs(fsid_t *fsid) 115 { 116 return (rootvfs); 117 } 118 119 vfsops_t * 120 vfs_getops(vfs_t *vfsp) 121 { 122 return (vfsp->vfs_op); 123 } 124 125 /* ARGSUSED */ 126 struct vfssw * 127 vfs_getvfsswbyvfsops(vfsops_t *vfsops) 128 { 129 return (NULL); 130 } 131 132 /* ARGSUSED */ 133 void 134 vfs_unrefvfssw(struct vfssw *vswp) 135 { 136 } 137 138 /* ARGSUSED */ 139 int 140 fsop_root(vfs_t *vfsp, vnode_t **vpp) 141 { 142 vnode_t *vp; 143 144 if ((vp = rootdir) == NULL) 145 return (ENXIO); 146 147 vn_hold(vp); 148 *vpp = vp; 149 return (0); 150 } 151 152 /* ARGSUSED */ 153 int 154 fsop_statfs(vfs_t *vfsp, statvfs64_t *sp) 155 { 156 vnode_t *vp; 157 int rc; 158 159 if ((vp = rootdir) == NULL) 160 return (ENXIO); 161 162 rc = fstatvfs64(vp->v_fd, sp); 163 if (rc == -1) { 164 rc = errno; 165 } 166 167 return (rc); 168 } 169 170 refstr_t * 171 vfs_getmntpoint(const struct vfs *vfsp) 172 { 173 refstr_t *mntpt; 174 175 mntpt = vfsp->vfs_mntpt; 176 refstr_hold(mntpt); 177 178 return (mntpt); 179 } 180 181 /* ARGSUSED */ 182 void 183 vfs_hold(vfs_t *vfsp) 184 { 185 } 186 187 /* ARGSUSED */ 188 void 189 vfs_rele(vfs_t *vfsp) 190 { 191 } 192 193 /* ARGSUSED */ 194 int 195 vfs_lock(vfs_t *vfsp) 196 { 197 return (0); 198 } 199 200 /* ARGSUSED */ 201 int 202 vfs_rlock(vfs_t *vfsp) 203 { 204 return (0); 205 } 206 207 /* ARGSUSED */ 208 void 209 vfs_lock_wait(vfs_t *vfsp) 210 { 211 } 212 213 /* ARGSUSED */ 214 void 215 vfs_rlock_wait(vfs_t *vfsp) 216 { 217 } 218 219 /* ARGSUSED */ 220 void 221 vfs_unlock(vfs_t *vfsp) 222 { 223 } 224 225 226 static u_longlong_t fs_caller_id; 227 u_longlong_t 228 fs_new_caller_id(void) 229 { 230 return (++fs_caller_id); 231 } 232 233 static sysid_t lm_sysid; 234 sysid_t 235 lm_alloc_sysidt(void) 236 { 237 return (++lm_sysid); 238 } 239 240 /* ARGSUSED */ 241 void 242 lm_free_sysidt(sysid_t id) 243 { 244 } 245