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/i386/ibcs2/ibcs2_fcntl.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  * Copyright (c) 1995 Scott Bartram
    3  * All rights reserved.
    4  *
    5  * Redistribution and use in source and binary forms, with or without
    6  * modification, are permitted provided that the following conditions
    7  * are met:
    8  * 1. Redistributions of source code must retain the above copyright
    9  *    notice, this list of conditions and the following disclaimer.
   10  * 2. Redistributions in binary form must reproduce the above copyright
   11  *    notice, this list of conditions and the following disclaimer in the
   12  *    documentation and/or other materials provided with the distribution.
   13  * 3. The name of the author may not be used to endorse or promote products
   14  *    derived from this software without specific prior written permission
   15  *
   16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
   17  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
   18  * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
   19  * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
   20  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
   21  * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
   22  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
   23  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
   24  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
   25  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
   26  */
   27 
   28 #include <sys/cdefs.h>
   29 __FBSDID("$FreeBSD: releng/5.2/sys/i386/ibcs2/ibcs2_fcntl.c 115684 2003-06-02 06:48:51Z obrien $");
   30 
   31 #include "opt_spx_hack.h"
   32 
   33 #include <sys/param.h>
   34 #include <sys/systm.h>
   35 #include <sys/fcntl.h>
   36 #include <sys/file.h>
   37 #include <sys/filedesc.h>
   38 #include <sys/lock.h>
   39 #include <sys/mutex.h>
   40 #include <sys/sysproto.h>
   41 #include <sys/ttycom.h>
   42 
   43 #include <i386/ibcs2/ibcs2_fcntl.h>
   44 #include <i386/ibcs2/ibcs2_signal.h>
   45 #include <i386/ibcs2/ibcs2_proto.h>
   46 #include <i386/ibcs2/ibcs2_util.h>
   47 
   48 static void cvt_iflock2flock(struct ibcs2_flock *, struct flock *);
   49 static void cvt_flock2iflock(struct flock *, struct ibcs2_flock *);
   50 static int  cvt_o_flags(int);
   51 static int  oflags2ioflags(int);
   52 static int  ioflags2oflags(int);
   53 
   54 static int
   55 cvt_o_flags(flags)
   56         int flags;
   57 {
   58         int r = 0;
   59 
   60         /* convert mode into NetBSD mode */
   61         if (flags & IBCS2_O_WRONLY) r |= O_WRONLY;
   62         if (flags & IBCS2_O_RDWR)   r |= O_RDWR;
   63         if (flags & (IBCS2_O_NDELAY | IBCS2_O_NONBLOCK)) r |= O_NONBLOCK;
   64         if (flags & IBCS2_O_APPEND) r |= O_APPEND;
   65         if (flags & IBCS2_O_SYNC)   r |= O_FSYNC;
   66         if (flags & IBCS2_O_CREAT)  r |= O_CREAT;
   67         if (flags & IBCS2_O_TRUNC)  r |= O_TRUNC /* | O_CREAT ??? */;
   68         if (flags & IBCS2_O_EXCL)   r |= O_EXCL;
   69         if (flags & IBCS2_O_RDONLY) r |= O_RDONLY;
   70         if (flags & IBCS2_O_PRIV)   r |= O_EXLOCK;
   71         if (flags & IBCS2_O_NOCTTY) r |= O_NOCTTY;
   72         return r;
   73 }
   74 
   75 static void
   76 cvt_flock2iflock(flp, iflp)
   77         struct flock *flp;
   78         struct ibcs2_flock *iflp;
   79 {
   80         switch (flp->l_type) {
   81         case F_RDLCK:
   82                 iflp->l_type = IBCS2_F_RDLCK;
   83                 break;
   84         case F_WRLCK:
   85                 iflp->l_type = IBCS2_F_WRLCK;
   86                 break;
   87         case F_UNLCK:
   88                 iflp->l_type = IBCS2_F_UNLCK;
   89                 break;
   90         }
   91         iflp->l_whence = (short)flp->l_whence;
   92         iflp->l_start = (ibcs2_off_t)flp->l_start;
   93         iflp->l_len = (ibcs2_off_t)flp->l_len;
   94         iflp->l_sysid = 0;
   95         iflp->l_pid = (ibcs2_pid_t)flp->l_pid;
   96 }
   97 
   98 #ifdef DEBUG_IBCS2
   99 static void
  100 print_flock(struct flock *flp)
  101 {
  102   printf("flock: start=%x len=%x pid=%d type=%d whence=%d\n",
  103          (int)flp->l_start, (int)flp->l_len, (int)flp->l_pid,
  104          flp->l_type, flp->l_whence);
  105 }
  106 #endif
  107 
  108 static void
  109 cvt_iflock2flock(iflp, flp)
  110         struct ibcs2_flock *iflp;
  111         struct flock *flp;
  112 {
  113         flp->l_start = (off_t)iflp->l_start;
  114         flp->l_len = (off_t)iflp->l_len;
  115         flp->l_pid = (pid_t)iflp->l_pid;
  116         switch (iflp->l_type) {
  117         case IBCS2_F_RDLCK:
  118                 flp->l_type = F_RDLCK;
  119                 break;
  120         case IBCS2_F_WRLCK:
  121                 flp->l_type = F_WRLCK;
  122                 break;
  123         case IBCS2_F_UNLCK:
  124                 flp->l_type = F_UNLCK;
  125                 break;
  126         }
  127         flp->l_whence = iflp->l_whence;
  128 }
  129 
  130 /* convert iBCS2 mode into NetBSD mode */
  131 static int
  132 ioflags2oflags(flags)
  133         int flags;
  134 {
  135         int r = 0;
  136         
  137         if (flags & IBCS2_O_RDONLY) r |= O_RDONLY;
  138         if (flags & IBCS2_O_WRONLY) r |= O_WRONLY;
  139         if (flags & IBCS2_O_RDWR) r |= O_RDWR;
  140         if (flags & IBCS2_O_NDELAY) r |= O_NONBLOCK;
  141         if (flags & IBCS2_O_APPEND) r |= O_APPEND;
  142         if (flags & IBCS2_O_SYNC) r |= O_FSYNC;
  143         if (flags & IBCS2_O_NONBLOCK) r |= O_NONBLOCK;
  144         if (flags & IBCS2_O_CREAT) r |= O_CREAT;
  145         if (flags & IBCS2_O_TRUNC) r |= O_TRUNC;
  146         if (flags & IBCS2_O_EXCL) r |= O_EXCL;
  147         if (flags & IBCS2_O_NOCTTY) r |= O_NOCTTY;
  148         return r;
  149 }
  150 
  151 /* convert NetBSD mode into iBCS2 mode */
  152 static int
  153 oflags2ioflags(flags)
  154         int flags;
  155 {
  156         int r = 0;
  157         
  158         if (flags & O_RDONLY) r |= IBCS2_O_RDONLY;
  159         if (flags & O_WRONLY) r |= IBCS2_O_WRONLY;
  160         if (flags & O_RDWR) r |= IBCS2_O_RDWR;
  161         if (flags & O_NDELAY) r |= IBCS2_O_NONBLOCK;
  162         if (flags & O_APPEND) r |= IBCS2_O_APPEND;
  163         if (flags & O_FSYNC) r |= IBCS2_O_SYNC;
  164         if (flags & O_NONBLOCK) r |= IBCS2_O_NONBLOCK;
  165         if (flags & O_CREAT) r |= IBCS2_O_CREAT;
  166         if (flags & O_TRUNC) r |= IBCS2_O_TRUNC;
  167         if (flags & O_EXCL) r |= IBCS2_O_EXCL;
  168         if (flags & O_NOCTTY) r |= IBCS2_O_NOCTTY;
  169         return r;
  170 }
  171 
  172 int
  173 ibcs2_open(td, uap)
  174         struct thread *td;
  175         struct ibcs2_open_args *uap;
  176 {
  177         struct proc *p = td->td_proc;
  178         int noctty = uap->flags & IBCS2_O_NOCTTY;
  179         int ret;
  180         caddr_t sg = stackgap_init();
  181 
  182         uap->flags = cvt_o_flags(uap->flags);
  183         if (uap->flags & O_CREAT)
  184                 CHECKALTCREAT(td, &sg, uap->path);
  185         else
  186                 CHECKALTEXIST(td, &sg, uap->path);
  187         ret = open(td, (struct open_args *)uap);
  188 
  189 #ifdef SPX_HACK
  190         if (ret == ENXIO) {
  191                 if (!strcmp(uap->path, "/compat/ibcs2/dev/spx"))
  192                         ret = spx_open(td, uap);
  193         } else
  194 #endif /* SPX_HACK */
  195         PROC_LOCK(p);
  196         if (!ret && !noctty && SESS_LEADER(p) && !(p->p_flag & P_CONTROLT)) {
  197                 struct file *fp;
  198                 int error;
  199 
  200                 error = fget(td, td->td_retval[0], &fp);
  201                 PROC_UNLOCK(p);
  202                 if (error)
  203                         return (EBADF);
  204 
  205                 /* ignore any error, just give it a try */
  206                 if (fp->f_type == DTYPE_VNODE)
  207                         fo_ioctl(fp, TIOCSCTTY, (caddr_t) 0, td->td_ucred,
  208                             td);
  209                 fdrop(fp, td);
  210         } else
  211                 PROC_UNLOCK(p);
  212         return ret;
  213 }
  214 
  215 int
  216 ibcs2_creat(td, uap)
  217         struct thread *td;  
  218         struct ibcs2_creat_args *uap;
  219 {       
  220         struct open_args cup;   
  221         caddr_t sg = stackgap_init();
  222 
  223         CHECKALTCREAT(td, &sg, uap->path);
  224         cup.path = uap->path;
  225         cup.mode = uap->mode;
  226         cup.flags = O_WRONLY | O_CREAT | O_TRUNC;
  227         return open(td, &cup);
  228 }       
  229 
  230 int
  231 ibcs2_access(td, uap)
  232         struct thread *td;
  233         struct ibcs2_access_args *uap;
  234 {
  235         struct access_args cup;
  236         caddr_t sg = stackgap_init();
  237 
  238         CHECKALTEXIST(td, &sg, uap->path);
  239         cup.path = uap->path;
  240         cup.flags = uap->flags;
  241         return access(td, &cup);
  242 }
  243 
  244 int
  245 ibcs2_fcntl(td, uap)
  246         struct thread *td;
  247         struct ibcs2_fcntl_args *uap;
  248 {
  249         int error;
  250         struct fcntl_args fa;
  251         struct flock *flp;
  252         struct ibcs2_flock ifl;
  253         
  254         switch(uap->cmd) {
  255         case IBCS2_F_DUPFD:
  256                 fa.fd = uap->fd;
  257                 fa.cmd = F_DUPFD;
  258                 fa.arg = (/* XXX */ int)uap->arg;
  259                 return fcntl(td, &fa);
  260         case IBCS2_F_GETFD:
  261                 fa.fd = uap->fd;
  262                 fa.cmd = F_GETFD;
  263                 fa.arg = (/* XXX */ int)uap->arg;
  264                 return fcntl(td, &fa);
  265         case IBCS2_F_SETFD:
  266                 fa.fd = uap->fd;
  267                 fa.cmd = F_SETFD;
  268                 fa.arg = (/* XXX */ int)uap->arg;
  269                 return fcntl(td, &fa);
  270         case IBCS2_F_GETFL:
  271                 fa.fd = uap->fd;
  272                 fa.cmd = F_GETFL;
  273                 fa.arg = (/* XXX */ int)uap->arg;
  274                 error = fcntl(td, &fa);
  275                 if (error)
  276                         return error;
  277                 td->td_retval[0] = oflags2ioflags(td->td_retval[0]);
  278                 return error;
  279         case IBCS2_F_SETFL:
  280                 fa.fd = uap->fd;
  281                 fa.cmd = F_SETFL;
  282                 fa.arg = (/* XXX */ int)
  283                                   ioflags2oflags((int)uap->arg);
  284                 return fcntl(td, &fa);
  285 
  286         case IBCS2_F_GETLK:
  287             {
  288                 caddr_t sg = stackgap_init();
  289                 flp = stackgap_alloc(&sg, sizeof(*flp));
  290                 error = copyin((caddr_t)uap->arg, (caddr_t)&ifl,
  291                                ibcs2_flock_len);
  292                 if (error)
  293                         return error;
  294                 cvt_iflock2flock(&ifl, flp);
  295                 fa.fd = uap->fd;
  296                 fa.cmd = F_GETLK;
  297                 fa.arg = (/* XXX */ int)flp;
  298                 error = fcntl(td, &fa);
  299                 if (error)
  300                         return error;
  301                 cvt_flock2iflock(flp, &ifl);
  302                 return copyout((caddr_t)&ifl, (caddr_t)uap->arg,
  303                                ibcs2_flock_len);
  304             }
  305 
  306         case IBCS2_F_SETLK:
  307             {
  308                 caddr_t sg = stackgap_init();
  309                 flp = stackgap_alloc(&sg, sizeof(*flp));
  310                 error = copyin((caddr_t)uap->arg, (caddr_t)&ifl,
  311                                ibcs2_flock_len);
  312                 if (error)
  313                         return error;
  314                 cvt_iflock2flock(&ifl, flp);
  315                 fa.fd = uap->fd;
  316                 fa.cmd = F_SETLK;
  317                 fa.arg = (/* XXX */ int)flp;
  318 
  319                 return fcntl(td, &fa);
  320             }
  321 
  322         case IBCS2_F_SETLKW:
  323             {
  324                 caddr_t sg = stackgap_init();
  325                 flp = stackgap_alloc(&sg, sizeof(*flp));
  326                 error = copyin((caddr_t)uap->arg, (caddr_t)&ifl,
  327                                ibcs2_flock_len);
  328                 if (error)
  329                         return error;
  330                 cvt_iflock2flock(&ifl, flp);
  331                 fa.fd = uap->fd;
  332                 fa.cmd = F_SETLKW;
  333                 fa.arg = (/* XXX */ int)flp;
  334                 return fcntl(td, &fa);
  335             }
  336         }
  337         return ENOSYS;
  338 }

Cache object: 29e070b304eb953520755a1a67a50037


[ 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.