1 /* vfs_vnops.c 6.4 85/03/18 */ 2 3 #include "../machine/reg.h" 4 5 #include "param.h" 6 #include "systm.h" 7 #include "dir.h" 8 #include "user.h" 9 #include "fs.h" 10 #include "file.h" 11 #include "conf.h" 12 #include "inode.h" 13 #include "acct.h" 14 #include "mount.h" 15 #include "socket.h" 16 #include "socketvar.h" 17 #include "proc.h" 18 19 /* 20 * Check mode permission on inode pointer. 21 * Mode is READ, WRITE or EXEC. 22 * In the case of WRITE, the 23 * read-only status of the file 24 * system is checked. 25 * Also in WRITE, prototype text 26 * segments cannot be written. 27 * The mode is shifted to select 28 * the owner/group/other fields. 29 * The super user is granted all 30 * permissions. 31 */ 32 access(ip, mode) 33 register struct inode *ip; 34 int mode; 35 { 36 register m; 37 register gid_t *gp; 38 39 m = mode; 40 if (m == IWRITE) { 41 /* 42 * Disallow write attempts on read-only 43 * file systems; unless the file is a block 44 * or character device resident on the 45 * file system. 46 */ 47 if (ip->i_fs->fs_ronly != 0) { 48 if ((ip->i_mode & IFMT) != IFCHR && 49 (ip->i_mode & IFMT) != IFBLK) { 50 u.u_error = EROFS; 51 return (1); 52 } 53 } 54 /* 55 * If there's shared text associated with 56 * the inode, try to free it up once. If 57 * we fail, we can't allow writing. 58 */ 59 if (ip->i_flag&ITEXT) 60 xrele(ip); 61 if (ip->i_flag & ITEXT) { 62 u.u_error = ETXTBSY; 63 return (1); 64 } 65 } 66 /* 67 * If you're the super-user, 68 * you always get access. 69 */ 70 if (u.u_uid == 0) 71 return (0); 72 /* 73 * Access check is based on only 74 * one of owner, group, public. 75 * If not owner, then check group. 76 * If not a member of the group, then 77 * check public access. 78 */ 79 if (u.u_uid != ip->i_uid) { 80 m >>= 3; 81 if (u.u_gid == ip->i_gid) 82 goto found; 83 gp = u.u_groups; 84 for (; gp < &u.u_groups[NGROUPS] && *gp != NOGROUP; gp++) 85 if (ip->i_gid == *gp) 86 goto found; 87 m >>= 3; 88 found: 89 ; 90 } 91 if ((ip->i_mode&m) != 0) 92 return (0); 93 u.u_error = EACCES; 94 return (1); 95 } 96 97 /* 98 * Look up a pathname and test if 99 * the resultant inode is owned by the 100 * current user. 101 * If not, try for super-user. 102 * If permission is granted, 103 * return inode pointer. 104 */ 105 struct inode * 106 owner(fname, follow) 107 caddr_t fname; 108 int follow; 109 { 110 register struct inode *ip; 111 register struct nameidata *ndp = &u.u_nd; 112 113 ndp->ni_nameiop = LOOKUP | follow; 114 ndp->ni_segflg = UIO_USERSPACE; 115 ndp->ni_dirp = fname; 116 ip = namei(ndp); 117 if (ip == NULL) 118 return (NULL); 119 if (u.u_uid == ip->i_uid) 120 return (ip); 121 if (suser()) 122 return (ip); 123 iput(ip); 124 return (NULL); 125 } 126 127 /* 128 * Test if the current user is the 129 * super user. 130 */ 131 suser() 132 { 133 134 if (u.u_uid == 0) { 135 u.u_acflag |= ASU; 136 return (1); 137 } 138 u.u_error = EPERM; 139 return (0); 140 } 141