1*7c478bd9Sstevel@tonic-gate /* 2*7c478bd9Sstevel@tonic-gate * CDDL HEADER START 3*7c478bd9Sstevel@tonic-gate * 4*7c478bd9Sstevel@tonic-gate * The contents of this file are subject to the terms of the 5*7c478bd9Sstevel@tonic-gate * Common Development and Distribution License, Version 1.0 only 6*7c478bd9Sstevel@tonic-gate * (the "License"). You may not use this file except in compliance 7*7c478bd9Sstevel@tonic-gate * with the License. 8*7c478bd9Sstevel@tonic-gate * 9*7c478bd9Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10*7c478bd9Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing. 11*7c478bd9Sstevel@tonic-gate * See the License for the specific language governing permissions 12*7c478bd9Sstevel@tonic-gate * and limitations under the License. 13*7c478bd9Sstevel@tonic-gate * 14*7c478bd9Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each 15*7c478bd9Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16*7c478bd9Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the 17*7c478bd9Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying 18*7c478bd9Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner] 19*7c478bd9Sstevel@tonic-gate * 20*7c478bd9Sstevel@tonic-gate * CDDL HEADER END 21*7c478bd9Sstevel@tonic-gate */ 22*7c478bd9Sstevel@tonic-gate /* 23*7c478bd9Sstevel@tonic-gate * Copyright (c) 1990-1996 by Sun Microsystems, Inc. 24*7c478bd9Sstevel@tonic-gate * All rights reserved. 25*7c478bd9Sstevel@tonic-gate */ 26*7c478bd9Sstevel@tonic-gate 27*7c478bd9Sstevel@tonic-gate #ident "%Z%%M% %I% %E% SMI" 28*7c478bd9Sstevel@tonic-gate 29*7c478bd9Sstevel@tonic-gate #include <unistd.h> 30*7c478bd9Sstevel@tonic-gate #include <sys/errno.h> 31*7c478bd9Sstevel@tonic-gate #include <sys/fcntl.h> 32*7c478bd9Sstevel@tonic-gate #include <sys/filio.h> 33*7c478bd9Sstevel@tonic-gate #include <sys/ioccom.h> 34*7c478bd9Sstevel@tonic-gate #include <sys/syscall.h> 35*7c478bd9Sstevel@tonic-gate 36*7c478bd9Sstevel@tonic-gate 37*7c478bd9Sstevel@tonic-gate /* The following is an array of fcntl commands. The numbers listed 38*7c478bd9Sstevel@tonic-gate * below are from SVR4. Array is indexed with SunOS 4.1 numbers to 39*7c478bd9Sstevel@tonic-gate * obtain the SVR4 numbers. 40*7c478bd9Sstevel@tonic-gate */ 41*7c478bd9Sstevel@tonic-gate int cmd_op[14] = {0, 1, 2, 3, 4, 23, 24, 14, 6, 7, 21, 20, -1, 22}; 42*7c478bd9Sstevel@tonic-gate 43*7c478bd9Sstevel@tonic-gate /* SVR4/SunOS 5.0 equivalent modes */ 44*7c478bd9Sstevel@tonic-gate #define N_O_NDELAY 0x04 45*7c478bd9Sstevel@tonic-gate #define N_O_SYNC 0x10 46*7c478bd9Sstevel@tonic-gate #define N_O_NONBLOCK 0x80 47*7c478bd9Sstevel@tonic-gate #define N_O_CREAT 0x100 48*7c478bd9Sstevel@tonic-gate #define N_O_TRUNC 0x200 49*7c478bd9Sstevel@tonic-gate #define N_O_EXCL 0x400 50*7c478bd9Sstevel@tonic-gate 51*7c478bd9Sstevel@tonic-gate #define S5_FASYNC 0x1000 52*7c478bd9Sstevel@tonic-gate 53*7c478bd9Sstevel@tonic-gate /* from SVR4 stropts.h */ 54*7c478bd9Sstevel@tonic-gate #define S5_S_RDNORM 0x0040 55*7c478bd9Sstevel@tonic-gate #define S5_S_WRNORM 0x0004 56*7c478bd9Sstevel@tonic-gate #define S5_S_RDBAND 0x0080 57*7c478bd9Sstevel@tonic-gate #define S5_S_BANDURG 0x0200 58*7c478bd9Sstevel@tonic-gate #define S5_I_SETSIG (('S'<<8)|011) 59*7c478bd9Sstevel@tonic-gate #define S5_I_GETSIG (('S'<<8)|012) 60*7c478bd9Sstevel@tonic-gate 61*7c478bd9Sstevel@tonic-gate /* Mask corresponding to the bits above in SunOS 4.x */ 62*7c478bd9Sstevel@tonic-gate #define FLAGS_MASK (O_SYNC|O_NONBLOCK|O_CREAT|O_TRUNC|O_EXCL \ 63*7c478bd9Sstevel@tonic-gate |O_NDELAY|FNBIO|FASYNC) 64*7c478bd9Sstevel@tonic-gate #define N_FLAGS_MASK (N_O_NDELAY|N_O_SYNC|N_O_NONBLOCK|N_O_CREAT \ 65*7c478bd9Sstevel@tonic-gate |N_O_TRUNC|N_O_EXCL|S5_FASYNC) 66*7c478bd9Sstevel@tonic-gate 67*7c478bd9Sstevel@tonic-gate struct n_flock { 68*7c478bd9Sstevel@tonic-gate short l_type; 69*7c478bd9Sstevel@tonic-gate short l_whence; 70*7c478bd9Sstevel@tonic-gate long l_start; 71*7c478bd9Sstevel@tonic-gate long l_len; /* len == 0 means until end of file */ 72*7c478bd9Sstevel@tonic-gate long l_sysid; 73*7c478bd9Sstevel@tonic-gate long l_pid; 74*7c478bd9Sstevel@tonic-gate long pad[4]; /* reserve area */ 75*7c478bd9Sstevel@tonic-gate } ; 76*7c478bd9Sstevel@tonic-gate 77*7c478bd9Sstevel@tonic-gate 78*7c478bd9Sstevel@tonic-gate int fcntl(fd, cmd, arg) 79*7c478bd9Sstevel@tonic-gate int fd, cmd, arg; 80*7c478bd9Sstevel@tonic-gate { 81*7c478bd9Sstevel@tonic-gate return(bc_fcntl(fd, cmd, arg)); 82*7c478bd9Sstevel@tonic-gate } 83*7c478bd9Sstevel@tonic-gate 84*7c478bd9Sstevel@tonic-gate 85*7c478bd9Sstevel@tonic-gate int bc_fcntl(fd, cmd, arg) 86*7c478bd9Sstevel@tonic-gate int fd, cmd, arg; 87*7c478bd9Sstevel@tonic-gate { 88*7c478bd9Sstevel@tonic-gate int fds, ret; 89*7c478bd9Sstevel@tonic-gate struct flock *savarg; 90*7c478bd9Sstevel@tonic-gate struct n_flock nfl; 91*7c478bd9Sstevel@tonic-gate extern int errno; 92*7c478bd9Sstevel@tonic-gate int i, narg; 93*7c478bd9Sstevel@tonic-gate 94*7c478bd9Sstevel@tonic-gate if ((cmd == F_SETOWN) || (cmd == F_GETOWN)) { 95*7c478bd9Sstevel@tonic-gate ret = _s_fcntl(fd, cmd_op[cmd], arg); 96*7c478bd9Sstevel@tonic-gate if ((ret != -1) || (errno != EINVAL)) 97*7c478bd9Sstevel@tonic-gate return (ret); 98*7c478bd9Sstevel@tonic-gate else { 99*7c478bd9Sstevel@tonic-gate if (cmd == F_GETOWN) { 100*7c478bd9Sstevel@tonic-gate if (_ioctl(fd, S5_I_GETSIG, &i) < 0) { 101*7c478bd9Sstevel@tonic-gate if (errno == EINVAL) 102*7c478bd9Sstevel@tonic-gate i = 0; 103*7c478bd9Sstevel@tonic-gate else 104*7c478bd9Sstevel@tonic-gate return (-1); 105*7c478bd9Sstevel@tonic-gate } 106*7c478bd9Sstevel@tonic-gate if (i & (S5_S_RDBAND|S5_S_BANDURG| 107*7c478bd9Sstevel@tonic-gate S5_S_RDNORM|S5_S_WRNORM)) 108*7c478bd9Sstevel@tonic-gate return (getpid()); 109*7c478bd9Sstevel@tonic-gate return (0); 110*7c478bd9Sstevel@tonic-gate } else { /* cmd == F_SETOWN */ 111*7c478bd9Sstevel@tonic-gate i = S5_S_RDNORM|S5_S_WRNORM|S5_S_RDBAND|S5_S_BANDURG; 112*7c478bd9Sstevel@tonic-gate return (ioctl(fd, S5_I_SETSIG, i)); 113*7c478bd9Sstevel@tonic-gate } 114*7c478bd9Sstevel@tonic-gate } 115*7c478bd9Sstevel@tonic-gate } 116*7c478bd9Sstevel@tonic-gate if (cmd == F_SETFL) { 117*7c478bd9Sstevel@tonic-gate if (arg & FLAGS_MASK) { 118*7c478bd9Sstevel@tonic-gate narg = arg & ~FLAGS_MASK; 119*7c478bd9Sstevel@tonic-gate if (arg & FASYNC) 120*7c478bd9Sstevel@tonic-gate narg |= S5_FASYNC; 121*7c478bd9Sstevel@tonic-gate if (arg & O_SYNC) 122*7c478bd9Sstevel@tonic-gate narg |= N_O_SYNC; 123*7c478bd9Sstevel@tonic-gate if (arg & O_CREAT) 124*7c478bd9Sstevel@tonic-gate narg |= N_O_CREAT; 125*7c478bd9Sstevel@tonic-gate if (arg & O_TRUNC) 126*7c478bd9Sstevel@tonic-gate narg |= N_O_TRUNC; 127*7c478bd9Sstevel@tonic-gate if (arg & O_EXCL) 128*7c478bd9Sstevel@tonic-gate narg |= N_O_EXCL; 129*7c478bd9Sstevel@tonic-gate if (arg & (O_NDELAY)) 130*7c478bd9Sstevel@tonic-gate narg |= N_O_NDELAY; 131*7c478bd9Sstevel@tonic-gate if (arg & O_NONBLOCK) 132*7c478bd9Sstevel@tonic-gate narg |= N_O_NONBLOCK; 133*7c478bd9Sstevel@tonic-gate if (arg & FNBIO) 134*7c478bd9Sstevel@tonic-gate narg |= N_O_NDELAY; 135*7c478bd9Sstevel@tonic-gate arg = narg; 136*7c478bd9Sstevel@tonic-gate } 137*7c478bd9Sstevel@tonic-gate } else if (cmd == F_SETLK || cmd == F_SETLKW || cmd == F_GETLK) { 138*7c478bd9Sstevel@tonic-gate if (arg == 0 || arg == -1) { 139*7c478bd9Sstevel@tonic-gate errno = EFAULT; 140*7c478bd9Sstevel@tonic-gate return(-1); 141*7c478bd9Sstevel@tonic-gate } 142*7c478bd9Sstevel@tonic-gate savarg = (struct flock *)arg; 143*7c478bd9Sstevel@tonic-gate arg = (int) &nfl; 144*7c478bd9Sstevel@tonic-gate nfl.l_type = savarg->l_type; 145*7c478bd9Sstevel@tonic-gate nfl.l_whence = savarg->l_whence; 146*7c478bd9Sstevel@tonic-gate nfl.l_start = savarg->l_start; 147*7c478bd9Sstevel@tonic-gate nfl.l_len = savarg->l_len; 148*7c478bd9Sstevel@tonic-gate nfl.l_pid = savarg->l_pid; 149*7c478bd9Sstevel@tonic-gate } 150*7c478bd9Sstevel@tonic-gate 151*7c478bd9Sstevel@tonic-gate ret = _s_fcntl(fd, cmd_op[cmd], arg); 152*7c478bd9Sstevel@tonic-gate 153*7c478bd9Sstevel@tonic-gate if (ret != -1) { 154*7c478bd9Sstevel@tonic-gate if (cmd == F_DUPFD) { 155*7c478bd9Sstevel@tonic-gate if ((fds = fd_get(fd)) != -1) 156*7c478bd9Sstevel@tonic-gate fd_add(ret, fds); 157*7c478bd9Sstevel@tonic-gate } else if (cmd == F_GETFL) { 158*7c478bd9Sstevel@tonic-gate if (ret & N_FLAGS_MASK) { 159*7c478bd9Sstevel@tonic-gate narg = ret & ~N_FLAGS_MASK; 160*7c478bd9Sstevel@tonic-gate if (ret & S5_FASYNC) 161*7c478bd9Sstevel@tonic-gate narg |= FASYNC; 162*7c478bd9Sstevel@tonic-gate if (ret & N_O_SYNC) 163*7c478bd9Sstevel@tonic-gate narg |= O_SYNC; 164*7c478bd9Sstevel@tonic-gate if (ret & N_O_NONBLOCK) 165*7c478bd9Sstevel@tonic-gate narg |= O_NONBLOCK; 166*7c478bd9Sstevel@tonic-gate if (ret & N_O_CREAT) 167*7c478bd9Sstevel@tonic-gate narg |= O_CREAT; 168*7c478bd9Sstevel@tonic-gate if (ret & N_O_TRUNC) 169*7c478bd9Sstevel@tonic-gate narg |= O_TRUNC; 170*7c478bd9Sstevel@tonic-gate if (ret & N_O_EXCL) 171*7c478bd9Sstevel@tonic-gate narg |= O_EXCL; 172*7c478bd9Sstevel@tonic-gate if (ret & (N_O_NDELAY)) 173*7c478bd9Sstevel@tonic-gate narg |= O_NDELAY; 174*7c478bd9Sstevel@tonic-gate ret = narg; 175*7c478bd9Sstevel@tonic-gate } 176*7c478bd9Sstevel@tonic-gate } else if (cmd == F_SETLK || cmd == F_SETLKW || 177*7c478bd9Sstevel@tonic-gate cmd == F_GETLK) { 178*7c478bd9Sstevel@tonic-gate savarg->l_type = nfl.l_type; 179*7c478bd9Sstevel@tonic-gate savarg->l_whence = nfl.l_whence; 180*7c478bd9Sstevel@tonic-gate savarg->l_start = nfl.l_start; 181*7c478bd9Sstevel@tonic-gate savarg->l_len = nfl.l_len; 182*7c478bd9Sstevel@tonic-gate savarg->l_pid = nfl.l_pid; 183*7c478bd9Sstevel@tonic-gate arg = (int) savarg; 184*7c478bd9Sstevel@tonic-gate } 185*7c478bd9Sstevel@tonic-gate } 186*7c478bd9Sstevel@tonic-gate return(ret); 187*7c478bd9Sstevel@tonic-gate } 188